天津投入产出系统后端
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

563 lines
23 KiB

using System;
using System.Collections.Generic;
using System.Linq;
using System.Web;
using QMAPP.FJC.Entity.Basic;
using QMAPP.ServicesAgent;
using System.Configuration;
using OPCPLC;
using QMAPP.FJC.Entity;
using OpcHost.Concrete;
using System.Threading;
using OpcHost.Common;
using OPCAutomation;
namespace OpcHost.Init
{
public static class ParaInit
{
//用来存储工控机发起连接服务器建立双通道连接的设备信息
public static List<string> connectMachineList;
//用来存储生产设备信息
public static List<MachineInfo> machineList;
//用来存储OPC配置参数与服务端句柄的对应关系
//key:OPC配置参数,样式为 设备号+"-"+模具号+"-"+数据库字段
//value:服务端句柄
public static Dictionary<string, int> parameterValueDict = new Dictionary<string, int>();
/// <summary>
/// 用来存储客户端句柄与设备参数对应关系
/// key:客户端句柄值
/// value:OPC配置参数,样式为 设备号+"-"+模具号+"-"+数据库字段
/// </summary>
public static Dictionary<int, string> clientHandleDict = new Dictionary<int, string>();
//OPC配置参数列表静态变量
public static List<ParameterConfig> paraConfigList;
//设备模具参数信息静态变量
public static List<ParameterConfig> moldList;
//OPC连接字典静态变量
public static Dictionary<string, OPCPLCAutomation> opcplcConnectionList = new Dictionary<string, OPCPLCAutomation>();
public static int clientHandleMaxValue = 0;
private static Dictionary<string, string> colunmConDict = new Dictionary<string, string>();
#region 初始化
/// <summary>
/// 初始化相关信息
/// </summary>
public static void InitParameter()
{
moldList = new List<ParameterConfig>();
machineList = new List<MachineInfo>();
//获取数据库中所有的生产设备信息
ServiceAgent wcfAgent = GetServiceAgent();
//opcServer服务器IP
string opcServerIP = ConfigurationManager.AppSettings.Get("OPCServerIP");
//opcServer服务名称
string opcServerName = ConfigurationManager.AppSettings.Get("OPCServerName");
try
{
#region 获取数据库中所有的生产设备信息
machineList = wcfAgent.InvokeServiceFunction<List<MachineInfo>>(QMAPP.ServicesAgent.B9BasicService.MachineInfoBLL_GetAllList.ToString(), new MachineInfo());
#endregion
#region 获取所有的配置信息
paraConfigList = wcfAgent.InvokeServiceFunction<List<ParameterConfig>>(QMAPP.ServicesAgent.B9BasicService.ParameterConfigBLL_GetList.ToString(), new MachineInfo());
#endregion
#region 获取设备模块信息
//对加工参数配置信息按照设备及模具信息进行分组
var objlist = from pc in paraConfigList
group pc by new { pc.MACHINECODDE, pc.MOLDNUMBER, pc.CONNECTIONSTRING } into g
select new ParameterConfig { MACHINECODDE = g.Key.MACHINECODDE, MOLDNUMBER = g.Key.MOLDNUMBER, CONNECTIONSTRING = g.Key.CONNECTIONSTRING };
//添加到静态变量中
foreach (var ob in objlist)
{
moldList.Add(new ParameterConfig() { MACHINECODDE = ob.MACHINECODDE, MOLDNUMBER = ob.MOLDNUMBER });
}
//按照设备进行排序
moldList = moldList.OrderBy(o => o.MACHINECODDE).ToList<ParameterConfig>();
#endregion
#region 加载模块下的加工参数配置信息
//变量所有的模具信息
foreach (var m in moldList)
{
MachineInfo machineEntity = machineList.First(o => o.MACHINECODDE == m.MACHINECODDE);
OPCPLCAutomation gtxConnection = new OPCPLC.OPCPLCAutomation();
gtxConnection.GetListOPCServers(opcServerIP);
gtxConnection.ConnectRemoteServer(opcServerName, opcServerIP);
//创建组信息
gtxConnection.CreateGroup(m.MACHINECODDE + m.MOLDNUMBER);
//获取该模具对应的OPC配置信息
List<ParameterConfig> machineParaConList = paraConfigList
.Where(o => o.MACHINECODDE == m.MACHINECODDE && o.MOLDNUMBER == m.MOLDNUMBER).ToList<ParameterConfig>();
//遍历该模具下的OPC配置信息
foreach (var pc in machineParaConList)
{
//初始化字典名称: 设备名称+模块编号+字段名称
string dicKeyStr = machineEntity.MACHINECODDE + "-" + m.MOLDNUMBER + "-" + pc.COLUMNCODE;
//初始化字段信息值为0
parameterValueDict.Add(dicKeyStr, 0);
//获取opc中tagName
string itemName = pc.CONNECTIONSTRING;
//将字典中的与PLC内存地址向绑定
parameterValueDict[dicKeyStr] = gtxConnection.AddKepItem(itemName);
}
//添加PLC连接信息
opcplcConnectionList.Add(m.MACHINECODDE + m.MOLDNUMBER, gtxConnection);
}
#endregion
#region 开始对所有的生产设备进行轮询监控
//获取所有的生产设备
List<MachineInfo> produceMachineList = machineList
.Where(o => o.OPERATETYPE == EnumGeter.OPERATETYPE.PRODUCE.GetHashCode().ToString())
.ToList<MachineInfo>();
//初始化工厂类
OperateFactory factory = new OperateFactory();
//按照机器来创建监控线程
foreach (MachineInfo pm in produceMachineList)
{
//通过设备的生产类型获取操作类别
EquipOperate opclass = factory.GetConcreteOperateClass(pm);
//添加监控线程
Thread t = new Thread(opclass.GetMachineData);
t.Start();
}
#endregion
}
catch (Exception)
{
throw;
}
}
public static void InitParameterMonitor()
{
moldList = new List<ParameterConfig>();
machineList = new List<MachineInfo>();
//获取数据库中所有的生产设备信息
ServiceAgent wcfAgent = GetServiceAgent();
try
{
#region 获取数据库中所有的生产设备信息
machineList = wcfAgent.InvokeServiceFunction<List<MachineInfo>>(QMAPP.ServicesAgent.B9BasicService.MachineInfoBLL_GetAllList.ToString(), new MachineInfo());
#endregion
#region 获取OPC配置信息
paraConfigList = wcfAgent.InvokeServiceFunction<List<ParameterConfig>>(QMAPP.ServicesAgent.B9BasicService.ParameterConfigBLL_GetList.ToString(), new MachineInfo());
#endregion
#region 获取设备模块信息
//对加工参数配置信息按照设备及模具信息进行分组
var objlist = from pc in paraConfigList
group pc by new { pc.MACHINECODDE, pc.MOLDNUMBER } into g
select new ParameterConfig { MACHINECODDE = g.Key.MACHINECODDE, MOLDNUMBER = g.Key.MOLDNUMBER };
//添加到静态变量中
foreach (var ob in objlist)
{
moldList.Add(new ParameterConfig() { MACHINECODDE = ob.MACHINECODDE, MOLDNUMBER = ob.MOLDNUMBER });
}
//按照设备进行排序
moldList = moldList.OrderBy(o => o.MACHINECODDE).OrderBy(o => o.MOLDNUMBER).ToList<ParameterConfig>();
#endregion
//opcServer服务器IP
string opcServerIP = ConfigurationManager.AppSettings.Get("OPCServerIP");
//opcServer服务名称
string opcServerName = ConfigurationManager.AppSettings.Get("OPCServerName");
#region 加载每个模具下的OPC配置参数信息
//遍历该模具下的OPC配置信息
foreach (var m in moldList)
{
//获取设备信息
MachineInfo machineEntity = machineList.First(o => o.MACHINECODDE == m.MACHINECODDE);
#region 添加设备模具下加工参数
List<ParameterConfig> paraAndOperateList = paraConfigList.Where(o => (o.MACHINECODDE == m.MACHINECODDE && m.MOLDNUMBER == m.MOLDNUMBER)
&& (m.COLUMNTYPE == OpcHostEnumGeter.COLUMNTYPE.PARAMETER.GetHashCode().ToString())
).ToList<ParameterConfig>();
if (paraAndOperateList.Count > 0)
{
//初始化该模具下的OPC连接信息
OPCPLCAutomation paraAndOpeCon = new OPCPLC.OPCPLCAutomation();
paraAndOpeCon.GetListOPCServers(opcServerIP);
paraAndOpeCon.ConnectRemoteServer(opcServerName, opcServerIP);
paraAndOpeCon.CreateGroup(m.MACHINECODDE + "-" + m.MOLDNUMBER + "-GetData");
foreach (var pc in paraAndOperateList)
{
//初始化字典名称: 设备名称+模块编号+字段名称
string dicKeyStr = pc.MACHINECODDE + "-" + pc.MOLDNUMBER + "-" + pc.COLUMNCODE;
//初始化OPC配置参数与服务端句柄字典信息
parameterValueDict.Add(dicKeyStr, 0);
//获取OPC中的tagName
string itemName = pc.CONNECTIONSTRING;
//累计客户端句柄值
clientHandleMaxValue++;
//添加到客户端句柄与设备参数字典表中
clientHandleDict.Add(clientHandleMaxValue, dicKeyStr);
//通过OPC设备连接信息和客户端句柄获取服务端句柄
//并且将服务句柄与OPC配置信息进行绑定
parameterValueDict[dicKeyStr] = paraAndOpeCon.AddKepItem(itemName, clientHandleMaxValue);
colunmConDict.Add(dicKeyStr, m.MACHINECODDE + "-" + m.MOLDNUMBER + "-GetData");
}
//添加PLC连接信息
opcplcConnectionList.Add(m.MACHINECODDE + m.MOLDNUMBER + "-GetData", paraAndOpeCon);
}
#endregion
#region 添加设备模具下加工参数
List<ParameterConfig> writeList = paraConfigList
.Where(o => o.MACHINECODDE == m.MACHINECODDE && o.MOLDNUMBER == m.MOLDNUMBER && o.COLUMNTYPE == "2")
.ToList<ParameterConfig>();
if (writeList.Count > 0)
{
OPCPLCAutomation gtxConnection = new OPCPLC.OPCPLCAutomation();
gtxConnection.GetListOPCServers(opcServerIP);
//连接Opc服务
gtxConnection.ConnectRemoteServer(opcServerName, opcServerIP);
gtxConnection.CreateGroup(m.MACHINECODDE + "-" + m.MOLDNUMBER + "-WriteData");
//变该模块下的所有参数信息
foreach (var pc in writeList)
{
//初始化字典名称: 设备名称+模块编号+字段名称
string dicKeyStr = machineEntity.MACHINECODDE + "-" + m.MOLDNUMBER + "-" + pc.COLUMNCODE;
//初始化字段信息值为0
parameterValueDict.Add(dicKeyStr, 0);
//获取opc中tagName
string itemName = pc.CONNECTIONSTRING;
clientHandleMaxValue++;
clientHandleDict.Add(clientHandleMaxValue, dicKeyStr);
//将字典中的与PLC内存地址向绑定
parameterValueDict[dicKeyStr] = gtxConnection.AddKepItem(itemName, clientHandleMaxValue);
colunmConDict.Add(dicKeyStr, m.MACHINECODDE + "-" + m.MOLDNUMBER + "-WriteData");
}
//添加PLC连接信息
opcplcConnectionList.Add(m.MACHINECODDE + "-" + m.MOLDNUMBER + "-WriteData", gtxConnection);
}
#endregion
#region 添加模具下的加工完成标记和设备读取条码OPC配置信息
List<ParameterConfig> monitorList = paraConfigList.Where(o => (o.MACHINECODDE == m.MACHINECODDE && m.MOLDNUMBER == m.MOLDNUMBER)
&& (m.COLUMNTYPE == OpcHostEnumGeter.COLUMNTYPE.COMPLETEFLAG.GetHashCode().ToString() || m.COLUMNTYPE == OpcHostEnumGeter.COLUMNTYPE.EQUIPSCANCODE.GetHashCode().ToString())
).ToList<ParameterConfig>();
//存在加工完成标记和设备读取条码配置信息
if (monitorList.Count > 0)
{
//初始化该模具下的OPC连接信息
OPCPLCAutomation monitorCon = new OPCPLC.OPCPLCAutomation();
monitorCon.GetListOPCServers(opcServerIP);
monitorCon.ConnectRemoteServer(opcServerName, opcServerIP);
//创建监控组
monitorCon.CreateGroup(m.MACHINECODDE + "-" + m.MOLDNUMBER + "-Monitor");
monitorCon.KepGroups.DefaultGroupIsActive = true;//激活组。
monitorCon.KepGroups.DefaultGroupDeadband = 0;// 死区值,设为0时,服务器端该组内任何数据变化都通知组。
monitorCon.KepGroups.DefaultGroupUpdateRate = 200;//默认组群的刷新频率为200ms
monitorCon.KepGroup.UpdateRate = 100;//刷新频率为1秒。
monitorCon.KepGroup.IsSubscribed = true;//使用订阅功能,即可以异步,默认false
monitorCon.KepGroup.DataChange += new DIOPCGroupEvent_DataChangeEventHandler(KepGroup_DataChange);
//gtxConnection.KepGroup.AsyncWriteComplete += new DIOPCGroupEvent_AsyncWriteCompleteEventHandler(KepGroup_AsyncWriteComplete);
foreach (var pc in monitorList)
{
//初始化字典名称: 设备名称+模块编号+字段名称
string dicKeyStr = pc.MACHINECODDE + "-" + pc.MOLDNUMBER + "-" + pc.COLUMNCODE;
//初始化OPC配置参数与服务端句柄字典信息
parameterValueDict.Add(dicKeyStr, 0);
//获取OPC中的tagName
string itemName = pc.CONNECTIONSTRING;
//累计客户端句柄值
clientHandleMaxValue++;
//添加到客户端句柄与设备参数字典表中
clientHandleDict.Add(clientHandleMaxValue, dicKeyStr);
//通过OPC设备连接信息和客户端句柄获取服务端句柄
//并且将服务句柄与OPC配置信息进行绑定
parameterValueDict[dicKeyStr] = monitorCon.AddKepItem(itemName, clientHandleMaxValue);
colunmConDict.Add(dicKeyStr, m.MACHINECODDE + "-" + m.MOLDNUMBER + "-Monitor");
}
//添加到OPC连接字典中
opcplcConnectionList.Add(m.MACHINECODDE + "-" + m.MOLDNUMBER + "-Monitor", monitorCon);
}
#endregion
}
#endregion
}
catch (Exception)
{
throw;
}
}
#endregion
/// <summary>
/// 初始化代理信息
/// </summary>
/// <returns></returns>
public static ServiceAgent GetServiceAgent()
{
try
{
//创建代理
ServiceAgent agent = new ServiceAgent();
//设置凭据
//agent.ClientCredential.CredentialID = ConfigurationManager.AppSettings["ServiceCredentialID"];
return agent;
}
catch (Exception ex)
{
throw ex;
}
}
private static void KepGroup_DataChange(int TransactionID, int NumItems, ref Array ClientHandles, ref Array ItemValues, ref Array Qualities, ref Array TimeStamps)
{
try
{
//延迟半秒
Thread.Sleep(500);
for (int i = 1; i <= NumItems; i++)
{
//获取写入的值
var itemValue = ItemValues.GetValue(i);
//获取客户端句柄
int chvalue = Convert.ToInt32(ClientHandles.GetValue(i));
//获取服务端字典key值
string dicKeyStr = clientHandleDict[chvalue];
//获取设备信息
string machCode = dicKeyStr.Substring(0, dicKeyStr.IndexOf('-'));
string moldAndColumn = dicKeyStr.Substring(dicKeyStr.IndexOf('-') + 1);
//获取模块信息
string moldNumber = moldAndColumn.Substring(0, moldAndColumn.IndexOf('-'));
//获取字段名称
string columnCode = dicKeyStr.Substring(dicKeyStr.LastIndexOf('-') + 1);
//获取该标记信息
ParameterConfig currentPC = paraConfigList.First(o => o.MACHINECODDE == machCode && o.MOLDNUMBER == moldNumber && o.COLUMNCODE == columnCode);
#region 完成标记
if (currentPC.COLUMNTYPE == OpcHostEnumGeter.COLUMNTYPE.COMPLETEFLAG.GetHashCode().ToString())
{
//如果完成标记表示更新了加 工参数
//获取所有的加工参数
if ((Boolean)itemValue == true)
{
#region 获取该模块下的加工参数
List<ParameterConfig> paraList = paraConfigList
.Where(o => o.MACHINECODDE == machCode && o.MOLDNUMBER == moldNumber && o.COLUMNTYPE == OpcHostEnumGeter.COLUMNTYPE.PARAMETER.GetHashCode().ToString())
.ToList<ParameterConfig>();
//获取所有的加工参数
foreach (var parameter in paraList)
{
string item = parameter.MACHINECODDE + "-" + parameter.MOLDNUMBER + "-" + parameter.COLUMNCODE;
string conListKey = colunmConDict[item];
OPCPLCAutomation con = opcplcConnectionList[conListKey];
var result = con.ReadtagValue(parameterValueDict[item]);
if (result != null)
{
parameter.PARAVALUE = result;
}
}
#endregion
#region 处理已经读取完加工参数标记
//获取该设备模具下对应的设备操作就绪配置信息
ParameterConfig writeConfig = paraConfigList.First(o => o.MACHINECODDE == currentPC.MACHINECODDE
&& o.MOLDNUMBER == currentPC.MOLDNUMBER && o.COLUMNTYPE == OpcHostEnumGeter.COLUMNTYPE.PARAMETERREADED.GetHashCode().ToString());
//获取对应的OPC操作对象
//获取对应的服务端句柄
//向服务端句柄写入
opcplcConnectionList[writeConfig.MACHINECODDE + "-" + writeConfig.MOLDNUMBER + "-WriteData"].WritetagValue(parameterValueDict[writeConfig.MACHINECODDE + "-" + writeConfig.MOLDNUMBER + "-" + writeConfig.COLUMNCODE], true);
#endregion
//将参数信息传递到web服务中
}
}
#endregion
#region 设备扫描枪扫描条码
if (currentPC.COLUMNTYPE == OpcHostEnumGeter.COLUMNTYPE.EQUIPSCANCODE.GetHashCode().ToString())
{
//在双攻通信的条件下,将扫描的条码信息传送到工控机上
PLCService plcService = new PLCService();
plcService.ReturnProductCodeToMachine(itemValue.ToString(), machCode);
}
#endregion
}
}
catch (Exception ex)
{
Console.WriteLine("系统出现异常:" + ex.Message);
}
}
/// <summary>
/// 向设备发送可以操作的指令信息
/// </summary>
/// <param name="config"></param>
public static void SendOperateReadyOrder(ParameterConfig config)
{
try
{
//获取该设备模具下对应的设备操作就绪配置信息
ParameterConfig writeConfig = paraConfigList.First(o => o.MACHINECODDE == config.MACHINECODDE
&& o.MOLDNUMBER == config.MOLDNUMBER && o.COLUMNTYPE == OpcHostEnumGeter.COLUMNTYPE.OPERATEFLAG.GetHashCode().ToString());
//获取对应的OPC操作对象
//获取对应的服务端句柄
//向服务端句柄写入
opcplcConnectionList[writeConfig.MACHINECODDE + "-" + writeConfig.MOLDNUMBER + "-WriteData"].WritetagValue(parameterValueDict[writeConfig.MACHINECODDE + "-" + writeConfig.MOLDNUMBER + "-" + writeConfig.COLUMNCODE], true);
}
catch (Exception)
{
throw;
}
}
}
}