srgv通信
This commit is contained in:
@@ -18,69 +18,40 @@ import lombok.NoArgsConstructor;
|
||||
public class DeviceSrgv extends BaseEntity
|
||||
{
|
||||
private static final long serialVersionUID = 1L;
|
||||
/*
|
||||
* 实时数据
|
||||
* */
|
||||
private int taskNo;//任务号
|
||||
private String srcSite;//原地址
|
||||
private String tarSite;//目标地址
|
||||
private String currSite;//当期地址
|
||||
|
||||
/** $column.columnComment */
|
||||
private Long id;
|
||||
private int taskType;//任务类型
|
||||
|
||||
/** 设备唯一编码 */
|
||||
@Excel(name = "设备唯一编码")
|
||||
private String deviceCode ;
|
||||
private int battery;//电量
|
||||
private int workMode;//工作模式
|
||||
private int alarm;//报警
|
||||
private int status;//车状态
|
||||
private int finish;//接收完成标志 1接收完成
|
||||
private int chargeFlag;//充电标志 todo 充电状态值确认
|
||||
private int workPhase;//工作阶段
|
||||
private int errorMsg;//异常信息
|
||||
private int deviceRequest;//输送机对接请求
|
||||
private int changeLayer;//换层标志
|
||||
private int cargoFlag;//载货 0未知 1空载 2载货
|
||||
private int manualCharge;//手动充电 0未知 1充电
|
||||
|
||||
/** 设备名称 */
|
||||
@Excel(name = "设备名称")
|
||||
private String name ;
|
||||
private int undefined1;//
|
||||
private int undefined2;//
|
||||
|
||||
/** 类型 */
|
||||
@Excel(name = "类型")
|
||||
private String type;
|
||||
private String path;//路径
|
||||
|
||||
/** 设备IP */
|
||||
@Excel(name = "设备IP")
|
||||
private String ipAddress;
|
||||
//其他属性
|
||||
private int currFloor;//当前层
|
||||
|
||||
/** PLC读取地址 */
|
||||
@Excel(name = "PLC读取地址")
|
||||
private String plcDbReadAddress;
|
||||
private String spaceArea;//当前库存 01小库 02大库
|
||||
|
||||
/** 0-F 1-T */
|
||||
@Excel(name = "0-F 1-T")
|
||||
private String isActive;
|
||||
|
||||
/** PLC写入地址 */
|
||||
@Excel(name = "PLC写入地址")
|
||||
private String plcDbWriteAddress;
|
||||
|
||||
/** 入库请求 */
|
||||
@Excel(name = "入库请求")
|
||||
private int rkqq;
|
||||
|
||||
/** 空闲 */
|
||||
@Excel(name = "空闲")
|
||||
private int kx;
|
||||
|
||||
/** 到位 */
|
||||
@Excel(name = "到位")
|
||||
private int dw;
|
||||
|
||||
/** 条码 */
|
||||
@Excel(name = "条码")
|
||||
private String trayCode;
|
||||
|
||||
/** 任务号 */
|
||||
@Excel(name = "任务号")
|
||||
private int taskNo;
|
||||
|
||||
@Excel(name = "异常")
|
||||
private int exception;
|
||||
|
||||
@Excel(name = "托盘尺寸")
|
||||
private int traySize;
|
||||
|
||||
@Excel(name="允许放货")
|
||||
private int allowPut;
|
||||
|
||||
@Excel(name="输送线模式 1-入库 2-出库")
|
||||
private int model;
|
||||
private int allowSend;//1允许下发
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -17,7 +17,7 @@ import lombok.extern.slf4j.Slf4j;
|
||||
import java.util.concurrent.ConcurrentHashMap;
|
||||
|
||||
@Slf4j
|
||||
public class PlcDdjRead extends Thread {
|
||||
public class PlcDdjRead implements Runnable {
|
||||
public static ConcurrentHashMap<String, MsgDdj> deviceDdjMap;
|
||||
public volatile boolean isRun = true;
|
||||
|
||||
|
||||
@@ -0,0 +1,33 @@
|
||||
package com.ruoyi.schedule.plcRead.srgv;
|
||||
|
||||
public class FloorUtils {
|
||||
|
||||
/**
|
||||
* 从cur值中提取楼层信息
|
||||
* @param cur 原始楼层值
|
||||
* @return 处理后的楼层值,如果小于等于0则返回0
|
||||
*/
|
||||
public static int extractFloor(Integer cur) {
|
||||
// 处理null值
|
||||
if (cur == null) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
// 获取后两位(处理负数情况)
|
||||
int floor = Math.abs(cur) % 100;
|
||||
|
||||
// 如果结果小于等于0,返回默认值0
|
||||
return floor <= 0 ? 0 : floor;
|
||||
}
|
||||
|
||||
/**
|
||||
* 重载方法,处理int类型
|
||||
*/
|
||||
public static int extractFloor(int cur) {
|
||||
// 获取后两位(处理负数情况)
|
||||
int floor = Math.abs(cur) % 100;
|
||||
|
||||
// 如果结果小于等于0,返回默认值0
|
||||
return floor <= 0 ? 0 : floor;
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,197 @@
|
||||
package com.ruoyi.schedule.plcRead.srgv;
|
||||
|
||||
import HslCommunication.Core.Net.IReadWriteNet;
|
||||
import HslCommunication.Core.Transfer.DataFormat;
|
||||
import HslCommunication.Core.Transfer.IByteTransform;
|
||||
import HslCommunication.Core.Types.OperateResult;
|
||||
import HslCommunication.Core.Types.OperateResultExOne;
|
||||
import HslCommunication.ModBus.ModbusTcpNet;
|
||||
import com.ruoyi.common.domain.HslRead;
|
||||
import com.ruoyi.common.domain.PlcConnectInfo;
|
||||
import com.ruoyi.device.srgv.domain.DeviceSrgv;
|
||||
import lombok.extern.slf4j.Slf4j;
|
||||
|
||||
import java.util.List;
|
||||
import java.util.concurrent.ConcurrentHashMap;
|
||||
@Slf4j
|
||||
public class PlcSrgvRead implements Runnable{
|
||||
|
||||
public static ConcurrentHashMap<String, DeviceSrgv> deviceSrgvMap;
|
||||
private ModbusTcpNet modbusTcpNet;
|
||||
public static IReadWriteNet readWriteNet = null;
|
||||
public volatile boolean isRun = true;
|
||||
private final String ip;
|
||||
private final int port;
|
||||
private byte station;
|
||||
private Integer layer;
|
||||
private boolean success = false;
|
||||
private IByteTransform byteTransform = null;
|
||||
|
||||
public PlcSrgvRead(ConcurrentHashMap<String, DeviceSrgv> deviceSrgvMap, PlcConnectInfo plcConnectInfo){
|
||||
PlcSrgvRead.deviceSrgvMap = deviceSrgvMap;
|
||||
this.ip = plcConnectInfo.getIp();
|
||||
this.port = plcConnectInfo.getPort();
|
||||
this.station=(byte)1;
|
||||
}
|
||||
public static int WriteToSSJ(String address, byte[] data) {
|
||||
int a = 0;
|
||||
if (readWriteNet != null) {
|
||||
a = HslRead.WriteResultRender(readWriteNet.Write(address, data), address);
|
||||
}
|
||||
return a;
|
||||
}
|
||||
|
||||
|
||||
|
||||
@Override
|
||||
public void run() {
|
||||
while (isRun) {
|
||||
try {
|
||||
if (IsConnect()) {
|
||||
for(String srgvId:deviceSrgvMap.keySet()){
|
||||
DeviceSrgv deviceSrgv = deviceSrgvMap.get(srgvId);
|
||||
if(deviceSrgv!=null){
|
||||
readSrgvPlc(deviceSrgv);
|
||||
}
|
||||
}
|
||||
|
||||
Thread.sleep(1000);
|
||||
} else {
|
||||
reConnect();
|
||||
}
|
||||
}catch (InterruptedException e) {
|
||||
// 捕获中断异常,退出循环
|
||||
Thread.currentThread().interrupt(); // 重新设置中断标志
|
||||
return;
|
||||
} catch (Exception e) {
|
||||
log.info("********IP:" + this.ip + " port:" + this.port + "读取数据异常 " + e.getMessage());
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
private void readSrgvPlc(DeviceSrgv deviceSrgv){
|
||||
OperateResultExOne<byte[]> read1 = modbusTcpNet.Read("2400",(short)15);//2400-2414
|
||||
if (read1.IsSuccess) {
|
||||
setValueByByte1(read1.Content,deviceSrgv);
|
||||
}
|
||||
|
||||
//读取双字
|
||||
OperateResultExOne<byte[]> read2 = modbusTcpNet.Read("4800",(short)8);// 4800-4807任务号、原点、目标点、当前
|
||||
if(read2.IsSuccess){
|
||||
setValueByByte2(read2.Content,deviceSrgv);
|
||||
}
|
||||
|
||||
//读取双字,路径
|
||||
OperateResultExOne<byte[]> read3 = modbusTcpNet.Read("5000",(short)800);// 5000-5799 路径 400个
|
||||
setValueByByte3(read3.Content,deviceSrgv);
|
||||
}
|
||||
|
||||
//单字
|
||||
private void setValueByByte1(byte[] content , DeviceSrgv agvData) {
|
||||
agvData.setTaskType(byteTransform.TransInt16(content,0));
|
||||
agvData.setBattery(byteTransform.TransInt16(content,2));
|
||||
agvData.setWorkMode(byteTransform.TransInt16(content,4));
|
||||
agvData.setAlarm(byteTransform.TransInt16(content,6));
|
||||
agvData.setStatus(byteTransform.TransInt16(content,8));
|
||||
agvData.setFinish(byteTransform.TransInt16(content,10));
|
||||
agvData.setChargeFlag(byteTransform.TransInt16(content,12));
|
||||
agvData.setWorkPhase(byteTransform.TransInt16(content,14));
|
||||
agvData.setErrorMsg(byteTransform.TransInt16(content,16));
|
||||
agvData.setDeviceRequest(byteTransform.TransInt16(content,18));
|
||||
agvData.setChangeLayer(byteTransform.TransInt16(content,20));
|
||||
agvData.setCargoFlag(byteTransform.TransInt16(content,22));
|
||||
agvData.setManualCharge(byteTransform.TransInt16(content,24));
|
||||
agvData.setUndefined1(byteTransform.TransInt16(content,26));
|
||||
agvData.setAllowSend(byteTransform.TransInt16(content,16));
|
||||
|
||||
|
||||
}
|
||||
|
||||
private void setValueByByte2(byte[] content, DeviceSrgv agvData) {
|
||||
byteTransform.setDataFormat(DataFormat.CDAB);
|
||||
// TODO 注意双字反转
|
||||
agvData.setTaskNo(byteTransform.TransInt32(content,0));
|
||||
agvData.setSrcSite(String.format("%06d", byteTransform.TransInt32(content,4)));
|
||||
agvData.setTarSite(String.format("%06d", byteTransform.TransInt32(content,8)));
|
||||
agvData.setCurrSite(String.format("%06d", byteTransform.TransInt32(content,12)));
|
||||
|
||||
//设置库区
|
||||
String currSite = agvData.getCurrSite();
|
||||
String l = currSite.substring(2, 4);
|
||||
int li = Integer.parseInt(l);//列
|
||||
if(li<23){
|
||||
agvData.setSpaceArea("01");
|
||||
}else {
|
||||
agvData.setSpaceArea("02");
|
||||
}
|
||||
|
||||
//截取cur的后俩位,获取当前楼层
|
||||
int floor = FloorUtils.extractFloor(Integer.parseInt(agvData.getCurrSite()));
|
||||
this.layer = floor;
|
||||
agvData.setCurrFloor(floor);
|
||||
}
|
||||
|
||||
private void setValueByByte3(byte[] content, DeviceSrgv agvData) {
|
||||
|
||||
StringBuilder sb = new StringBuilder();
|
||||
for (int i = 0; i < content.length; i += 4) {
|
||||
// 检查剩余字节是否足够4个
|
||||
if (i + 4 > content.length) break;
|
||||
// TODO 注意双字反转
|
||||
int value = byteTransform.TransInt32(content, i);
|
||||
|
||||
// 如果值为0,终止循环
|
||||
if (value == 0) {
|
||||
break;
|
||||
}
|
||||
sb.append(String.format("%06d", value)).append(","); // 用逗号分隔每个int值
|
||||
}
|
||||
|
||||
// 移除最后多余的 ","
|
||||
if (sb.length() > 0) {
|
||||
sb.setLength(sb.length() - 1);
|
||||
}
|
||||
agvData.setPath(sb.toString());
|
||||
}
|
||||
|
||||
public void ConnectServer(){
|
||||
ModbusTcpNet modbusTcpNet = new ModbusTcpNet();//创建一个Modbus对象
|
||||
try{
|
||||
modbusTcpNet.setIpAddress(this.ip);
|
||||
modbusTcpNet.setPort(this.port);
|
||||
modbusTcpNet.setStation(station);
|
||||
this.byteTransform=modbusTcpNet.getByteTransform();
|
||||
OperateResult connect = modbusTcpNet.ConnectServer();
|
||||
if (connect.IsSuccess) {
|
||||
setIsConnect(true);
|
||||
readWriteNet = modbusTcpNet;
|
||||
}
|
||||
}catch (Exception ex) {
|
||||
log.info("********IP:" + this.ip + " port:" + this.port + "连接失败 " + ex.getMessage());
|
||||
}
|
||||
}
|
||||
public void setIsConnect(boolean bflag) {
|
||||
if (!success) {
|
||||
success = bflag;
|
||||
}
|
||||
}
|
||||
|
||||
public boolean IsConnect() {
|
||||
if (success) {
|
||||
return success;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
void reConnect() {
|
||||
closeServer();
|
||||
ConnectServer();
|
||||
log.info("重新连接 SSJ-PLC");
|
||||
}
|
||||
|
||||
void closeServer() {
|
||||
if (readWriteNet != null) {
|
||||
readWriteNet.ConnectClose();
|
||||
}
|
||||
setIsConnect(false);
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user