终端一体化运控平台
Vous ne pouvez pas sélectionner plus de 25 sujets Les noms de sujets doivent commencer par une lettre ou un nombre, peuvent contenir des tirets ('-') et peuvent comporter jusqu'à 35 caractères.
 
 
 

225 lignes
8.5 KiB

  1. using BPASmartClient.Helper;
  2. using BPASmartClient.Modbus;
  3. using BPASmartClient.DosingSystem.ViewModel;
  4. using System;
  5. using System.Collections.Concurrent;
  6. using System.Collections.Generic;
  7. using System.Diagnostics;
  8. using System.Linq;
  9. using System.Net.NetworkInformation;
  10. using System.Text;
  11. using System.Threading;
  12. using System.Threading.Tasks;
  13. using BPASmartClient.CustomResource.UserControls.MessageShow;
  14. using BPASmartClient.CustomResource.Pages.Model;
  15. namespace BPASmartClient.DosingSystem.Model
  16. {
  17. public class DeviceInquire
  18. {
  19. private volatile static DeviceInquire _Instance;
  20. public static DeviceInquire GetInstance => _Instance ?? (_Instance = new DeviceInquire());
  21. private DeviceInquire() { }
  22. string IPSegment = "192.168.0.";
  23. ConcurrentDictionary<string, DeviceStatus> DeviceLists = new ConcurrentDictionary<string, DeviceStatus>();
  24. List<string> InvalidIP = new List<string>();//无效 IP 集合
  25. List<string> IPLists = new List<string>();//启动 Ping 任务IP集合
  26. ConcurrentQueue<string> IPQueues = new ConcurrentQueue<string>();//pincomplete 完成队列
  27. public void Init()
  28. {
  29. IpAddressLines();
  30. ThreadManage.GetInstance().StartLong(new Action(() =>
  31. {
  32. if (IPQueues.Count >= IPLists.Count)
  33. IpAddressLines();
  34. Thread.Sleep(5000);
  35. }), "配料机设备上线监听", true);
  36. }
  37. public void Rescan()
  38. {
  39. InvalidIP.Clear();
  40. }
  41. public DeviceStatus GetDevice(string ip)
  42. {
  43. if (ip != null)
  44. {
  45. var res = DeviceLists.Values.FirstOrDefault(p => p.IpAddress == ip);
  46. if (res != null) return res;
  47. }
  48. return new DeviceStatus();
  49. }
  50. private void IpAddressLines()
  51. {
  52. IPLists.Clear();
  53. IPQueues.Clear();
  54. for (int i = 1; i <= 255; i++)
  55. {
  56. if (!InvalidIP.Contains($"{IPSegment}{i}") && !DeviceLists.ContainsKey($"{IPSegment}{i}"))
  57. {
  58. IPLists.Add($"{IPSegment}{i}");
  59. }
  60. }
  61. IPLists.ForEach((item) =>
  62. {
  63. Ping myPing = new Ping();
  64. myPing.PingCompleted += new PingCompletedEventHandler(_myPing_PingCompleted);
  65. myPing.SendAsync(item, 1000, null);
  66. });
  67. }
  68. private void _myPing_PingCompleted(object sender, PingCompletedEventArgs e)
  69. {
  70. if (e.Reply.Status == IPStatus.Success)
  71. {
  72. string ip = e.Reply.Address.ToString();
  73. if (!DeviceLists.ContainsKey(ip))
  74. {
  75. DeviceStatus DS = new DeviceStatus();
  76. DS.modbusTcp.IsReconnect = false;
  77. DS.modbusTcp.ConnectOk = new Action(() =>
  78. {
  79. string DeviceName = DS.modbusTcp.GetString(DeviceAddress.DeviceName, 20);//读取设备名称
  80. if (DeviceName.Length > 0)
  81. {
  82. DeviceLists.TryAdd(ip, DS);
  83. DeviceLists[ip].Init(DeviceName);
  84. DeviceLists[ip].modbusTcp.IsReconnect = false;
  85. App.Current.Dispatcher.Invoke(new Action(() =>
  86. {
  87. DeviceListViewModel.devices.Add(new Devices()
  88. {
  89. DeviceName = DeviceName,
  90. IpAddress = ip
  91. });//加入连接的(有名称的)设备列表
  92. for (int i = 0; i < Json<LocaPar>.Data.Recipes.Count; i++)
  93. {
  94. for (int m = 0; m < Json<LocaPar>.Data.Recipes.ElementAt(i).RawMaterials.Count; m++)
  95. {
  96. if (Json<LocaPar>.Data.Recipes.ElementAt(i).RawMaterials.ElementAt(m).DeviceIp == ip)
  97. {
  98. Json<LocaPar>.Data.Recipes.ElementAt(i).RawMaterials.ElementAt(m).RawMaterialName = DeviceName;
  99. }
  100. }
  101. }
  102. if (!NewRecipeViewModel.RawMaterialNames.Contains(DeviceName))
  103. NewRecipeViewModel.RawMaterialNames.Add(DeviceName);
  104. }));
  105. }
  106. else
  107. {
  108. if (!InvalidIP.Contains(ip)) InvalidIP.Add(ip);
  109. }
  110. });
  111. DS.modbusTcp.ConnectFail = new Action(() =>
  112. {
  113. if (!InvalidIP.Contains(ip)) InvalidIP.Add(ip);
  114. //MessageLog.GetInstance.ShowAlarmLog($"设备{ip}连接失败");
  115. });
  116. DS.modbusTcp.Disconnect = new Action(() =>
  117. {
  118. if (InvalidIP.Contains(ip)) InvalidIP.Remove(ip);
  119. var res = DeviceListViewModel.devices.FirstOrDefault(P => P.IpAddress == ip);
  120. if (res != null && DeviceListViewModel.devices.Contains(res))
  121. App.Current.Dispatcher.Invoke(new Action(() =>
  122. {
  123. DeviceListViewModel.devices.Remove(res);
  124. if (NewRecipeViewModel.RawMaterialNames.Contains(res.DeviceName))
  125. NewRecipeViewModel.RawMaterialNames.Remove(res.DeviceName);
  126. }));
  127. if (DeviceLists.ContainsKey(ip)) DeviceLists[ip].Dispose();
  128. });
  129. Task.Run(new Action(() =>
  130. {
  131. DS.modbusTcp.ModbusTcpConnect(ip, 502);//PLC连接
  132. IPQueues.Enqueue(e.Reply.Address.ToString());
  133. }));
  134. }
  135. else IPQueues.Enqueue(e.Reply.Address.ToString());
  136. }
  137. else IPQueues.Enqueue(e.Reply.Address.ToString());
  138. }
  139. }
  140. public class DeviceStatus
  141. {
  142. #region 对象属性声明
  143. public string DeviceName = String.Empty;
  144. public string IpAddress => modbusTcp.IPAdress;
  145. /// <summary>
  146. /// 设备状态
  147. /// </summary>
  148. public RawMaterialDeviceStatus deviceStatus { get; set; } = new RawMaterialDeviceStatus();
  149. public ModbusTcp modbusTcp = new ModbusTcp();
  150. public bool IsConnected => modbusTcp.Connected;
  151. #endregion
  152. public void Init(string DeviceName)
  153. {
  154. this.DeviceName = DeviceName;
  155. if (modbusTcp.Connected)
  156. {
  157. ThreadManage.GetInstance().StartLong(new Action(() =>
  158. {
  159. //获取设备运行状态
  160. var res = this.modbusTcp.Read(DeviceAddress.RunStatus);
  161. if (res != null && res is ushort[] ushortValue)
  162. {
  163. if (ushortValue.Length >= 1) deviceStatus.RunStatus = ushortValue[0];
  164. }
  165. //获取设备料仓剩余重量
  166. deviceStatus.WeightFeedback = this.modbusTcp.GetUint(DeviceAddress.WeightFeedback) * 10;
  167. deviceStatus.CutWeightFeedback = this.modbusTcp.GetUint(DeviceAddress.CutWeightFeedback) * 10;
  168. Thread.Sleep(100);
  169. }), $"{DeviceName} 开始监听", true);
  170. }
  171. }
  172. public void SetDeviceName(string name)
  173. {
  174. this.modbusTcp.Write(DeviceAddress.DeviceName, new ushort[20]);
  175. this.modbusTcp.SetString(DeviceAddress.DeviceName, name);
  176. }
  177. public void StatusReset()
  178. {
  179. this.modbusTcp.Write(DeviceAddress.RunStatus, (ushort)0);
  180. }
  181. public void Dispose()
  182. {
  183. ThreadManage.GetInstance().StopTask($"{DeviceName} 开始监听");
  184. }
  185. public void Start(uint Value)
  186. {
  187. if (modbusTcp.Connected)
  188. {
  189. modbusTcp.SetUint(DeviceAddress.WeightSet, Value);//写入配方量
  190. modbusTcp.Write(DeviceAddress.Start, (ushort)1);//设备启动写入
  191. }
  192. }
  193. }
  194. }