En este ejemplo aprenderá a habilitar el Addin OPC UA y convertir RoboDK en un servidor OPC UA. Examinaremos algunos ajustes utilizando el software UaExpert y Beckhoff TwinCAT3 TF6100.
El Addin OPC UA le permite configurar algunos parámetros, como el puerto del servidor. También puede optar por activar el servidor, desactivarlo o iniciarlo automáticamente con RoboDK.
Con el Addin OPC UA activado, seleccione Ajustes OPC UA-OPC-UA para configurar sus ajustes OPC UA.
La pantalla de configuración de OPC UA se muestra en el lado izquierdo como se muestra en la siguiente imagen.
Si ve un mensaje como "Servidor OPC UA de RoboDK ejecutándose en el puerto 4840" significa que el servidor OPC UA de RoboDK se ha iniciado.
Puede probar la conectividad OPC UA con cualquier estación RoboDK que tenga uno o varios robots.
Puede utilizar el software UaExpert para probar la conectividad con el servidor OPC UA de RoboDK.
Puede descargar la versión gratuita del software UaExpert de la página web de Unified Automation: https://www.unified-automation.com/downloads/opc-ua-clients.html.
Inicie UaExpert y haga clic en el botón "+" para añadir el servidor OPC UA de RoboDK.
Expanda el descubrimiento personalizado y seleccione la opción <Doble clic para añadir servidor.> para añadir el servidor OPC UA de RoboDK.
Introduzca la URL del servidor OPC UA, opc.tcp://127.0.0.1:48440 que configuró en el paso anterior.
Conecte el servidor OPC UA con seguridad "Ninguna".
El servidor está configurado.
Ahora puede conectarse al servidor OPC UA de RoboDK desde UaExpert.
Podrá ver los Nodos y Métodos cuando se establezca la conexión.
Existen algunos nodos dentro del servidor OPC UA de RoboDK que le permiten intercambiar información básica sobre su estación.
El nodo RoboDK es un nodo que proporciona la versión real de su software RoboDK.
En este ejemplo se ha utilizado la versión RoboDK 64 Bit v5.5.3.23031.
Velocidad de simulación es un nodo que muestra la velocidad de simulación actual y permite al usuario sobrescribir la velocidad de simulación actual.
El valor del nodo está referenciado a la barra de deslizamiento de la velocidad de simulación.
La simulación actual puede leerse desde este nodo y puede sobrescribir la velocidad de simulación.
El Nodo Estación es un nodo que permite al usuario obtener el nombre actual de la Estación en RoboDK.
Como puede ver a continuación, el nodo Estación hace referencia a su "Nombre de estación" en RoboDK.
El Parámetro de la Estación y el Valor de la Estación son un Nodo conjunto de pares que permite al usuario obtener o establecer cualquier parámetro dentro de su Estación. El Servidor OPC UA de RoboDK monitorizará continuamente el valor real de "StationParameter" y devolverá el Valor de ese "StationParameter", desde el Nodo Valor de la Estación.
Puede ver los parámetros de su estación haciendo clic con el botón derecho del ratón en su estación RoboDK>Parámetros de la estación.
En el campo Parámetros constantes puede ver los parámetros por defecto de la estación y su valor.
El parámetro de la estación se refiere al campo "Parámetro" y el valor de la estación al campo "Valor".
Y podemos crear nuestros propios Parámetros haciendo clic en el botón "Añadir".
Se añade un nuevo parámetro Estación.
Introduzca el nombre y el valor del parámetro y pulse Aplicar para guardarlo.
También puede obtener su propio parámetro de estación.
El nodo hora es un nodo que permite obtener la hora actual de la RoboDK Station.
Se devuelve un valor con formato DataTime.
Y este Nodo se actualiza continuamente.
El servidor OPC UA de RoboDK también dispone de algunos métodos que permiten al usuario acceder a los datos de la estación RoboDK de forma dinámica.
Podemos hacer clic con el botón derecho del ratón en Método>Llamada para ejecutar el método.
getItem es un Método que permite al usuario obtener el puntero de su Item.
Para los InputArguments, Nombre del Dispositivo es necesario, puede imagen el Nombre del Dispositivo es el Nombre de su Estación,Nombre del Robot..etc.. Y Item ID es el OutputArguments que devuelve el Puntero de ese Dispositivo.
En este Ejemplo, recibí el Item ID (Puntero) de mi Robot ABB que se llama como "ABB_RB1".
Se devuelve 0 si el Nombre del artículo no es válido o no existe dentro de su estación.
getJonits es un método que permite al usuario obtener el valor de la articulación del robot desde la estación, basándose en el ID del elemento.
El ID del elemento es el valor del puntero de su elemento, y puede obtenerlo del método getItem().
Obtendremos el ID del artículo con este nombre de artículo "ABB_RB1", y se devuelve un valor UInt64.
El valor de las juntas se devuelve al pasar el ID del artículo en el método que obtuvimos en el anterior.
getJointsStr es un método que permite al usuario obtener el valor de las Juntas basándose en un valor de cadena.
Podemos pasar el nombre del Robot (String) en este método.
En Mi estación, ABB_RB1 es el nombre de mi robot.
Basta con pasar "ABB_RB1" en el parámetro Nombre del robot y llamar al método - Se devuelve el valor de la articulación en formato String.
setJointsStr es un método que permite al usuario establecer el valor de las Juntas del Robot, basándose en un Valor de Cadena.
En el nombre del Robot, se pasa ABB_RB1, y podemos pasar simplemente una cadena con el valor de la articulación en el parámetro Articulaciones.
For example:-0.000000,0.000000,-0.000000,-0.000000,-0.0,-0.000000
Puede utilizar el software TwinCAT 3 de Beckhoff para probar la conectividad con el servidor OPC UA de RoboDK.
Puede empezar creando el cliente OPC UA seleccionando E/S>Dispositivos>Añadir nuevo elemento.
Seleccione Dispositivo OPC UA virtual de OPC >OK.
Se inserta OPC UA Virtual.
Necesitamos añadir un cliente OPC UA para acceder al servidor OPC UA de RoboDK.
Seleccione Dispositivo 1 >Clic derecho >Añadir nuevo elemento.
Seleccione "Cliente OPC UA (Módulo)" y Aceptar.
Se inserta el Cliente OPC UA.
Abra el cliente OPC UA >Vaya a la pestaña Configuración>haga clic en "Seleccionar punto final" para configurar el punto final del servidor OPC UA al que desea acceder.
Introduzca la URL del servidor OPC UA de RoboDK y Actualícelo.
Pulse "Añadir nodos" para examinar el nodo que se encuentra dentro del servidor OPC UA.
Si se establece la conexión entre TwinCAT y el servidor OPC UA, puede examinar los detalles del servidor OPC UA.
Seleccione todos los Métodos y Ok.
Los métodos se insertan en su Configuración.
Configure el prefijo de su nombre en este campo.
Pulse "Crear Código Plc" para crear el Código PLC desde TwinCAT.
Se crea una carpeta OpcUaClient en su proyecto y todos los métodos de RoboDK se crean en formato de bloque de función IEC61131-3.
Esta sección muestra un programa de ejemplo de un PLC TwinCAT de Beckhoff que se comunica con el servidor OPC UA de RoboDK.
PROGRAMA PRINCIPAL
VAR
bConectado :BOOL;
StationPointer :DINT;
iPaso :INT;
bStart :BOOL;;
i :INT;
TON :TON
bReset :BOOL;
bEscribir :BOOL;
TON2 :TON
bShow :BOOL:=TRUE;
bVis :BOOL:=Verdadero;
FIN_VAR
VAR
Nombre_robot :CADENA(80):='ABB_RB1';
ID_artículo :ULINT;
arrJoints :ARRAY[0..11]DE LREAL;
strJoints :CADENA(80):='';
arrJointsFromStr:ARRAY[1..11]OF LREAL;
sSeparador :CADENA(1) := ',';
arrJointsComando:ARRAY[1..11]OF LREAL;
strJointsComando:STRING(80);
FIN_VAR
VAR CONSTANTE
cStepWaitCmd :INT:=0;
cStepInit INT:=5;
cStepGetItem INT:=10;
cStepGetItemReset INT:=20;
cStepGetItemError :INT:=990;
cStepGetJoints INT:=30;
cStepGetJointsReset INT:=40;
cStepGetJointsError INT:=991;
cStepGetJointsStr :INT:=50;
cStepGetJointsStrReset:INT:=60;
cStepGetJointsStrError:INT:=992;
cStepSetJointStrDelay :INT:=69;
cStepSetJointsStr :INT:=70;
cStepSetJointsStrReset:INT:=80;
cStepSetJointsStrError:INT:=993;
cStepEnd INT:=300;
cStepWaitReset :INT:=999;
FIN_VAR
VAR
aSplit :ARRAY[1..11] OF STRING(80);
bResultadoSplit :BOOL;
depurar :BOOL;
URL :STRING:='http://192.168.3.42:8091';
FIN_VAR
bConectado:=OPCUA_VirtualClient_RoboDK_Station.bConectado;
CASO iStep DE
cStepWaitCmd:
IF bStart THEN
iPaso:=cPasoInicio;
bInicio:=FALSE;
FIN_IF
cStepInit:
PunteroEstación:=0;
FOR i :=1 TO 11 DO
arrJoints[i]:=0,0;
arrJointsFromStr[i]:=0.0;
aSplit[i]:='';
FIN_FOR
IF NOT OPCUA_VirtualClient_RoboDK_Station.getItem.bBusy
AND NOT OPCUA_VirtualClient_RoboDK_Station.getItem.bError
AND NOT OPCUA_VirtualClient_RoboDK_Station.getJoints.bBusy
AND NOT OPCUA_VirtualClient_RoboDK_Station.getJoints.bError
AND NOT OPCUA_VirtualClient_RoboDK_Station.getJointsStr.bBusy
AND NOT OPCUA_VirtualClient_RoboDK_Station.getJointsStr.bError
AND NOT OPCUA_VirtualClient_RoboDK_Station.setJoints.bBusy
AND NOT OPCUA_VirtualClient_RoboDK_Station.setJoints.bError
AND NOT OPCUA_VirtualClient_RoboDK_Station.setJointsStr.bBusy
AND NOT OPCUA_VirtualClient_RoboDK_Station.setJointsStr.bError
ENTONCES
iPaso:=cPasoGetItem;
FIN_IF
iPaso:=cPasoGetItem;
cStepGetItem:
IF OPCUA_VirtualClient_RoboDK_Station.getItem.bDone THEN
iPaso:=cPasoGetItemReset;
Item_ID:=OPCUA_VirtualClient_RoboDK_Station.getItem.Item_ID;
ELSIF OPCUA_VirtualClient_RoboDK_Station.getItem.bError THEN
iStep:=cStepGetItemError;
FIN_IF
cStepGetItemReset:
IF NOT OPCUA_VirtualClient_RoboDK_Station.getItem.bError
AND NOT OPCUA_VirtualClient_RoboDK_Station.getItem.bBusy
ENTONCES
iPaso:=cPasoGetJoints;
FIN_IF
cStepGetJoints:
IF OPCUA_VirtualClient_RoboDK_Station.getJoints.bDone
AND NOT OPCUA_VirtualClient_RoboDK_Station.getJoints.bBusy
ENTONCES
iStep:=cStepGetJointsReset;
ELSIF OPCUA_VirtualClient_RoboDK_Station.getJoints.bError THEN
iPaso:=991;
FIN_IF
cStepGetJointsReset:
IF NOT OPCUA_VirtualClient_RoboDK_Station.getItem.bError
AND NOT OPCUA_VirtualClient_RoboDK_Station.getItem.bBusy
ENTONCES
iStep:=cStepGetJointsStr;
FIN_IF;
cStepGetJointsStr:
IF OPCUA_VirtualClient_RoboDK_Station.getJointsStr.bDone
AND NOT OPCUA_VirtualClient_RoboDK_Station.getJointsStr.bBusy
ENTONCES
iStep:=cStepGetJointsStrReset;
ELSIF OPCUA_VirtualClient_RoboDK_Station.getJointsStr.bError THEN
iStep:=cStepGetJointsStrError;
FIN_IF
cStepGetJointsStrReset:
IF NOT OPCUA_VirtualClient_RoboDK_Station.getJointsStr.bError
AND NOT OPCUA_VirtualClient_RoboDK_Station.getJointsStr.bBusy
ENTONCES
iPaso:=cPasoSetJointStrDelay;
FIN_IF;
cStepSetJointStrDelay:
strJointsComando:=''; strJointsComando:=CONCAT(LREAL_TO_STRING(arrJointsComando[1]),strJointsComando);
strJointsComando:=CONCAT(strJointsComando,',');
strJointsComando:=CONCAT(strJointsComando,LREAL_TO_STRING(arrJointsComando[2]));
strJointsComando:=CONCAT(strJointsComando,',');
strJointsComando:=CONCAT(strJointsComando,LREAL_TO_STRING(arrJointsComando[3]));
strJointsComando:=CONCAT(strJointsComando,',');
strJointsComando:=CONCAT(strJointsComando,LREAL_TO_STRING(arrJointsComando[4]));
strJointsComando:=CONCAT(strJointsComando,',');
strJointsComando:=CONCAT(strJointsComando,LREAL_TO_STRING(arrJointsComando[5]));
strJointsComando:=CONCAT(strJointsComando,',');
strJointsComando:=CONCAT(strJointsComando,LREAL_TO_STRING(arrJointsComando[6]));
TON2(IN:=VERDADERO,PT:=T#0,2S);
IF TON2.Q THEN
TON2(IN:=FALSO);
iPaso:=cPasoSetJointsStr;
FIN_IF
cStepSetJointsStr:
SI (
OPCUA_VirtualClient_RoboDK_Station.setJointsStr.bDone
Y NO
OPCUA_VirtualClient_RoboDK_Station.setJointsStr.bBusy
)
OR NOT bEscribir
ENTONCES
iPaso:=cPasoSetJointsStrReset;
ELSIF OPCUA_VirtualClient_RoboDK_Station.setJointsStr.bError
ENTONCES
iStep:=cStepSetJointsStrError;
FIN_IF
cStepSetJointsStrReset:
bEscribir:=FALSE;
OPCUA_VirtualClient_RoboDK_Station.setJointsStr.bExecute:=FALSE;
IF NOT OPCUA_VirtualClient_RoboDK_Station.setJointsStr.bError
AND NOT OPCUA_VirtualClient_RoboDK_Station.setJointsStr.bBusy
ENTONCES
iPaso:=cFinPaso;
FIN_IF;
cStepEnd:
TON(IN:=VERDADERO,PT:=T#0,1S);
IF TON.Q THEN
TON(IN:=FALSE);
IF NOT debug THEN
iPaso:=10;
ELSE
iPaso:=cPasoSetJointStrDelay;
FIN_IF;
FIN_IF
cStepGetItemError:
Item_ID:=0;
iPaso:=cPasoEsperarReinicio;
cStepGetJointsError:
FOR i :=0 TO 11 DO
arrJoints[i]:=-99999.99;
FIN_FOR
iPaso:=cPasoEsperarReinicio;
cStepGetJointsStrError:
strJoints:='';
iPaso:=cPasoEsperarReinicio;
cStepWaitReset:
IF bReset THEN
iPaso:=cPasoInicio;
bReinicio:=FALSE;
FIN_IF;
FIN_CASE
aSplit[1] := strJoints;
FOR i:=1 TO 7 DO
bResultadoSplit := BuscarYSplit(
pSeparador := ADR(sSeparador)
,pSrcString := ADR(aSplit[i])
,pCadenaIzquierda:= ADR(aSplit[i])
,nTamañoIzquierda := TAMAÑO(aSplit[i])
,pCadenaDerecha:= ADR(aSplit[i+1])
,nTamañoDerecho := SIZEOF(aSplit[i+1])
,bBuscarDesdeDerecha := FALSE );
IF NOT bResultadoSplit THEN
SALIDA
FIN_IF
FIN_FOR
PARA i :=1 A 6 HACER
arrJointsFromStr[i]:=STRING_TO_LREAL(aSplit[i]);
FIN_FOR;
//
OPCUA_VirtualClient_RoboDK_Station.getItem(
bExecute:=iStep=cStepGetItem
,Nombre_del_artículo:=Nombre_del_robot
);
OPCUA_VirtualClient_RoboDK_Station.getJoints(
bEjecutar:=iPaso=cPasoGetJoints
,Item_ID:=Item_ID,Juntas=>arrJuntas
);
OPCUA_VirtualClient_RoboDK_Station.getJointsStr(
bExecute:=iStep=cStepGetJointsStr
,Nombre_robot:=Nombre_robot,Juntas=>strJuntas
);
IF bWrite THEN
OPCUA_VirtualClient_RoboDK_Station.setJointsStr(
bEjecutar:=TRUE
,Nombre_robot:=Nombre_robot,Juntas:=strComandoJuntas);
FIN_IF;