using Aitex.Core.Common; using Aitex.Core.UI.MVVM; using MECF.Framework.Common.DataCenter; using MECF.Framework.Common.Equipment; using MECF.Framework.Common.OperationCenter; using MECF.Framework.Common.SubstrateTrackings; using MECF.Framework.Common.Utilities; using MECF.Framework.Common.WaferHolder; using Prism.Mvvm; using System; using System.Collections.Generic; using System.Collections.ObjectModel; using System.Linq; using System.Net.NetworkInformation; using System.Windows; using System.Windows.Input; using System.Windows.Threading; namespace CyberX8_MainPages.ViewModels { public class MaterialMovementViewModel : BindableBase { #region 常量 private const int DATAGRIP_ROW_NUM = 24; #endregion #region 内部变量 #region system /// /// rt查询key /// private List _rtDataKeys = new List(); /// /// 时钟 /// DispatcherTimer _timer; /// /// rt查询数据 /// private Dictionary _rtDataValueDic = new Dictionary(); /// /// LayoutCell列表 /// private ObservableCollection _locationLst; #endregion #region Common /// /// Module /// private string _module; /// /// MaterialData Collection /// private List _materialDatas; /// /// MaterialData Sub Collection1 /// private ObservableCollection _materialSubdatas1; /// /// MaterialData Sub Collection2 /// private ObservableCollection _materialSubdatas2; /// /// MaterialData Sub Collection Buffer1 /// private List _materialSubdatasBuffer1; /// /// MaterialData Sub Collection Buffer2 /// private List _materialSubdatasBuffer2; /// /// Pre MaterialDatas1 /// private List _preMaterialDatas1 = new List(); /// /// Pre MaterialDatas2 /// private List _preMaterialDatas2 = new List(); /// ; /// /// From Loaction选择 /// private string _fromLocation; /// /// To Location选择 /// private string _toLocation; /// /// ProcessTransporter是否Busy /// private bool _isProcessTransBusy; /// /// LoaderTransporter是否Busy /// private bool _isLoaderTransBusy; /// /// 是否在Auto模式下 /// private bool _isAutoMode; /// /// UpdateLocation按钮是否启用 /// private bool _isMoveEnable; /// /// Remove按钮是否启用 /// private bool _isRemoveEnable; /// /// Selected MaterialData /// private ModuleMaterial _selectedMaterialData; /// /// Pre Selected MaterialData /// private ModuleMaterial _preSelectedMaterialData; /// /// Selected MaterialData1 /// private ModuleMaterial _selectedMaterialData1; /// /// Selected MaterialData2 /// private ModuleMaterial _selectedMaterialData2; /// /// Selected ModuleName /// private string _selectedModuleName; /// /// WaferMove FromSlot列表 /// private ObservableCollection _fromSlotLst = new ObservableCollection(); /// /// WaferMove ToSlot列表 /// private ObservableCollection _toSlotLst = new ObservableCollection(); /// /// WaferMove Modules列表 /// private ObservableCollection _moduleLst = new ObservableCollection(); /// /// WaferMove From Module /// private ModuleName _fromModule; /// /// WaferMove To Module /// private ModuleName _toModule; /// /// WaferMove To Slot /// private int _toSlot; /// /// WaferMove From Slot /// private int _fromSlot; /// /// WaferMove Update按钮是否启用 /// private bool _isWaferMoveEnable; /// /// MaterialDataBuffer /// private ModuleMaterial _materialDataBuffer; /// /// Grid Selection /// private bool _gridSelection; #endregion #endregion #region 属性 #region Common /// /// MaterialData Collection /// public List MaterialDatas { get { return _materialDatas; } set { SetProperty(ref _materialDatas, value); } } /// /// MaterialData Sub Collection1 /// public ObservableCollection MaterialSubdatas1 { get { return _materialSubdatas1; } set { SetProperty(ref _materialSubdatas1, value); } } /// /// MaterialData Sub Collection2 /// public ObservableCollection MaterialSubdatas2 { get { return _materialSubdatas2; } set { SetProperty(ref _materialSubdatas2, value); } } /// /// Selected MaterialData /// public ModuleMaterial SelectedMaterialData { get { return _selectedMaterialData; } set { SetProperty(ref _selectedMaterialData, value); } } /// /// Selected MaterialData1 /// public ModuleMaterial SelectedMaterialData1 { get { return _selectedMaterialData1; } set { SetProperty(ref _selectedMaterialData1, value); } } /// /// Selected MaterialData2 /// public ModuleMaterial SelectedMaterialData2 { get { return _selectedMaterialData2; } set { SetProperty(ref _selectedMaterialData2, value); } } /// /// Selected ModuleName /// public string SelectedModuleName { get { return _selectedModuleName; ; } set { SetProperty(ref _selectedModuleName, value); } } /// /// LayoutCell列表 /// public ObservableCollection LocationLst { get { return _locationLst; } set { SetProperty(ref _locationLst, value); } } /// /// From Location /// public string FromLocation { get { return _fromLocation; } set { SetProperty(ref _fromLocation, value); } } /// /// To Location /// public string ToLocation { get { return _toLocation; } set { SetProperty(ref _toLocation, value); } } /// /// UpdateLocation按钮是否启用 /// public bool IsMoveEnable { get { return _isMoveEnable; } set { SetProperty(ref _isMoveEnable, value); } } /// /// Remove按钮是否启用 /// public bool IsRemoveEnable { get { return _isRemoveEnable; } set { SetProperty(ref _isRemoveEnable, value); } } /// /// WaferMove FromSlot列表 /// public ObservableCollection FromSlotLst { get { return _fromSlotLst; } set { SetProperty(ref _fromSlotLst, value); } } /// /// WaferMove ToSlot列表 /// public ObservableCollection ToSlotLst { get { return _toSlotLst; } set { SetProperty(ref _toSlotLst, value); } } /// /// WaferMove Modules列表 /// public ObservableCollection ModuleLst { get { return _moduleLst; } set { SetProperty(ref _moduleLst, value); } } /// /// WaferMove From Module /// public ModuleName FromModule { get { return _fromModule; } set { SetProperty(ref _fromModule, value); } } /// /// WaferMove To Module /// public ModuleName ToModule { get { return _toModule; } set { SetProperty(ref _toModule, value); } } /// /// WaferMove To Slot /// public int ToSlot { get { return _toSlot; } set { SetProperty(ref _toSlot, value); } } /// /// WaferMove To Slot /// public int FromSlot { get { return _fromSlot; } set { SetProperty(ref _fromSlot, value); } } /// /// WaferMove按钮是否启用 /// public bool IsWaferMoveEnable { get { return _isWaferMoveEnable; } set { SetProperty(ref _isWaferMoveEnable, value); } } #endregion #endregion #region 命令 public ICommand UpdateLocationCommand { get; private set; } public ICommand UpdateWaferCommand { get; private set; } public ICommand RemoveCommand { get; private set; } public ICommand ModuleChangeCommand { get; private set; } public ICommand SelectionChangeCommand { get; private set; } public ICommand ResetWafersCommand { get; private set; } #endregion /// /// 构造函数 /// public MaterialMovementViewModel() { _materialDatas = new List(); _materialSubdatas1 = new ObservableCollection(); _materialSubdatas2 = new ObservableCollection(); _materialSubdatasBuffer1 = new List(); _materialSubdatasBuffer2 = new List(); UpdateLocationCommand = new DelegateCommand(UpdateLocationAction); UpdateWaferCommand = new DelegateCommand(UpdateWaferAction); RemoveCommand = new DelegateCommand(RemoveAction); ModuleChangeCommand = new DelegateCommand(ModuleChangeAction); SelectionChangeCommand = new DelegateCommand(SelectionChangeAction); ResetWafersCommand = new DelegateCommand(ResetWafersAction); ModuleLst.Clear(); ModuleLst.Add(ModuleName.EfemRobot); ModuleLst.Add(ModuleName.LP1); ModuleLst.Add(ModuleName.LP2); ModuleLst.Add(ModuleName.LP3); ModuleLst.Add(ModuleName.Aligner1); ModuleLst.Add(ModuleName.PUF1); ModuleLst.Add(ModuleName.PUF2); ModuleLst.Add(ModuleName.Dummy1); ModuleLst.Add(ModuleName.Dummy2); ModuleLst.Add(ModuleName.Loader1); ModuleChangeAction("From"); ModuleChangeAction("To"); IsMoveEnable = false; IsRemoveEnable = false; IsWaferMoveEnable = false; } /// /// 加载数据 /// /// public void LoadData(string systemName) { _module = systemName; _rtDataKeys.Clear(); _rtDataKeys.Add("System.LayoutCellItems"); _rtDataKeys.Add("System.ModuleMaterials"); _rtDataKeys.Add($"Transporter1.IsBusy"); _rtDataKeys.Add($"Transporter2.IsBusy"); _rtDataKeys.Add("System.IsAutoMode"); if (_rtDataKeys.Count != 0) { _rtDataValueDic = QueryDataClient.Instance.Service.PollData(_rtDataKeys); if (_rtDataValueDic != null) { LocationLst = new ObservableCollection(CommonFunction.GetValue>(_rtDataValueDic, "System.LayoutCellItems")); LocationLst.Add("Loader"); LocationLst.Add(ModuleName.Transporter1.ToString()); LocationLst.Add(ModuleName.Transporter2.ToString()); } } if (_timer == null) { _timer = new DispatcherTimer(); _timer.Interval = TimeSpan.FromMilliseconds(200); _timer.Tick += Timer_Tick; } _timer.Start(); } /// /// 时钟 /// /// /// private void Timer_Tick(object sender, EventArgs e) { IsMoveEnable = (FromLocation != null && ToLocation != null) ? true : false; IsRemoveEnable = string.IsNullOrEmpty(SelectedModuleName) ? false : true; IsWaferMoveEnable = (FromModule != ModuleName.System && ToModule != ModuleName.System && FromSlot != 0 && ToSlot != 0) ? true : false; if (_rtDataKeys.Count != 0) { _rtDataValueDic = QueryDataClient.Instance.Service.PollData(_rtDataKeys); if (_rtDataValueDic != null) { _isProcessTransBusy = CommonFunction.GetValue(_rtDataValueDic, $"Transporter1.IsBusy"); _isLoaderTransBusy = CommonFunction.GetValue(_rtDataValueDic, $"Transporter2.IsBusy"); _isAutoMode = CommonFunction.GetValue(_rtDataValueDic, $"System.IsAutoMode"); MaterialDatas = CommonFunction.GetValue>(_rtDataValueDic, "System.ModuleMaterials"); int i = 0; _materialSubdatasBuffer1.Clear(); _materialSubdatasBuffer2.Clear(); for (i = 0; i < DATAGRIP_ROW_NUM; i++) { _materialSubdatasBuffer1.Add(MaterialDatas[i]); } for (; i < MaterialDatas.Count(); i++) { _materialSubdatasBuffer2.Add(MaterialDatas[i]); } //若数据变化则刷新数据 if ((_preMaterialDatas1.Count == 0) || (_preMaterialDatas1.Count != 0 && !CompareList(_preMaterialDatas1, _materialSubdatasBuffer1))) { MaterialSubdatas1 = new ObservableCollection(_materialSubdatasBuffer1); _preMaterialDatas1 = new List(_materialSubdatasBuffer1); } if ((_preMaterialDatas2.Count == 0) || (_preMaterialDatas2.Count != 0 && !CompareList(_preMaterialDatas2, _materialSubdatasBuffer2))) { MaterialSubdatas2 = new ObservableCollection(_materialSubdatasBuffer2); _preMaterialDatas2 = new List(_materialSubdatasBuffer2); } //记忆SelectedItem if (SelectedMaterialData != null) { if (_gridSelection) { SelectedMaterialData1 = MaterialSubdatas1.ToList().Find(t => t.ModuleName == SelectedMaterialData.ModuleName); SelectedMaterialData2 = null; } else { SelectedMaterialData2 = MaterialSubdatas2.ToList().Find(t => t.ModuleName == SelectedMaterialData.ModuleName); SelectedMaterialData1 = null; } } } } } /// /// 隐藏 /// public void Hide() { if (_timer != null) { _timer.Stop(); } } #region 命令方法 private void UpdateLocationAction(object param) { WaferHolderInfo waferHolderInfo = WaferHolderDataClient.Instance.Service.GetWaferHolderDataByLocation(FromLocation); if (waferHolderInfo == null) return; if (!string.IsNullOrEmpty(FromLocation) && !string.IsNullOrEmpty(ToLocation)) { if (!_isLoaderTransBusy && !_isProcessTransBusy && !_isAutoMode) { InvokeClient.Instance.Service.DoOperation($"WaferHolder.TransferWaferHolder", $"{FromLocation}", $"{ToLocation}"); } else if (_isAutoMode) { MessageBox.Show("Auto mode can't do this operation", "Update", MessageBoxButton.OK, MessageBoxImage.Error); } else { MessageBox.Show("Loader or Process Transporter is in Busy state", "Update", MessageBoxButton.OK, MessageBoxImage.Error); } } } /// /// 删除信息 /// /// private void RemoveAction(object param) { if (SelectedMaterialData == null) { MessageBox.Show("please select one data", "Delete", MessageBoxButton.OK, MessageBoxImage.Error); return; } if (string.IsNullOrEmpty(SelectedMaterialData.WaferHolderId) && SelectedMaterialData.SideAWaferStatus == 0 && SelectedMaterialData.SideBWaferStatus == 0) { MessageBox.Show("The data is Empt", "Delete", MessageBoxButton.OK, MessageBoxImage.Error); return; } if (MessageBox.Show("do you want to delete selected data", "Delete", MessageBoxButton.YesNo, MessageBoxImage.Question) == MessageBoxResult.Yes) { if ((LocationLst.Contains(SelectedMaterialData.ModuleName) || SelectedMaterialData.ModuleName.Contains("Transporter") || SelectedMaterialData.ModuleName.Contains("Loader")) && SelectedMaterialData.WaferHolderId != "") { WaferHolderDataClient.Instance.Service.DeleteWaferHolderData(SelectedMaterialData.WaferHolderId); } else if (ModuleHelper.IsSRD(ModuleHelper.Converter(SelectedMaterialData.ModuleName)) || ModuleHelper.IsPUF(ModuleHelper.Converter(SelectedMaterialData.ModuleName))) { if (SelectedMaterialData.SideAWaferId != "") InvokeClient.Instance.Service.DoOperation("WaferManager.DeleteWafer", SelectedMaterialData.SideAWaferId); if (SelectedMaterialData.SideBWaferId != "") InvokeClient.Instance.Service.DoOperation("WaferManager.DeleteWafer", SelectedMaterialData.SideBWaferId); } else { return; } } } /// /// WaferMove 更新Slot列表 /// /// private void ModuleChangeAction(object obj) { var value = obj.ToString(); switch (value) { case "From": FromSlotLst.Clear(); switch (FromModule) { case ModuleName.EfemRobot: FromSlotLst.Add(1); break; case ModuleName.LP1: case ModuleName.LP2: case ModuleName.LP3: for (int i = 1; i < 26; i++) { FromSlotLst.Add(i); } break; case ModuleName.Aligner1: FromSlotLst.Add(1); break; case ModuleName.PUF1: case ModuleName.PUF2: FromSlotLst.Add(1); FromSlotLst.Add(2); break; case ModuleName.Dummy1: case ModuleName.Dummy2: for (int i = 1; i < 17; i++) { FromSlotLst.Add(i); } break; case ModuleName.Loader1: FromSlotLst.Add(1); FromSlotLst.Add(2); break; default: break; } break; case "To": ToSlotLst.Clear(); switch (ToModule) { case ModuleName.EfemRobot: ToSlotLst.Add(1); break; case ModuleName.LP1: case ModuleName.LP2: case ModuleName.LP3: for (int i = 1; i < 26; i++) { ToSlotLst.Add(i); } break; case ModuleName.Aligner1: ToSlotLst.Add(1); break; case ModuleName.PUF1: case ModuleName.PUF2: ToSlotLst.Add(1); ToSlotLst.Add(2); break; case ModuleName.Dummy1: case ModuleName.Dummy2: for (int i = 1; i < 17; i++) { ToSlotLst.Add(i); } break; case ModuleName.Loader1: ToSlotLst.Add(1); ToSlotLst.Add(2); break; default: break; } break; default: break; } } /// /// 更新Wafer位置 /// /// private void UpdateWaferAction(object param) { if(ToModule == ModuleName.Loader1) { WaferHolderInfo waferHolderInfo = WaferHolderDataClient.Instance.Service.GetWaferHolderDataByLocation("Loader"); if(waferHolderInfo == null) { MessageBox.Show("Loader don't have wafer shuttle, can't move wafer!", "Delete", MessageBoxButton.OK, MessageBoxImage.Error); return; } InvokeClient.Instance.Service.DoOperation($"WaferManager.MoveWafer", FromModule, FromSlot - 1, ToModule, ToSlot - 1, waferHolderInfo.Id); } else if (FromModule == ModuleName.Loader1) { WaferHolderInfo waferHolderInfo = WaferHolderDataClient.Instance.Service.GetWaferHolderDataByLocation("Loader"); if (waferHolderInfo == null) { MessageBox.Show("Loader don't have wafer shuttle, can't move wafer!", "Delete", MessageBoxButton.OK, MessageBoxImage.Error); return; } InvokeClient.Instance.Service.DoOperation($"WaferManager.MoveWafer", FromModule, FromSlot - 1, ToModule, ToSlot - 1, waferHolderInfo.Id); } else { InvokeClient.Instance.Service.DoOperation($"WaferManager.MoveWafer", FromModule, FromSlot - 1, ToModule, ToSlot - 1); } } /// /// Selection Change /// /// private void SelectionChangeAction(object param) { string dg = param.ToString(); if(dg == "DataGrid1") { if (SelectedMaterialData1 != null) { _gridSelection = true; SelectedModuleName = SelectedMaterialData1.ModuleName; SelectedMaterialData = SelectedMaterialData1; } } else { if (SelectedMaterialData2 != null) { _gridSelection = false; SelectedModuleName = SelectedMaterialData2.ModuleName; SelectedMaterialData = SelectedMaterialData2; } } } /// /// 重置Wafers /// /// private void ResetWafersAction(object param) { InvokeClient.Instance.Service.DoOperation("WaferHolder.ResetLayoutWafers"); } private bool CompareList(List list1, List list2) { for(int i = 0; i < list1.Count; i++) { if (list1[i].WaferHolderId != list2[i].WaferHolderId || list1[i].SideAWaferId != list2[i].SideAWaferId || list1[i].SideAWaferType != list2[i].SideAWaferType || list1[i].SideAWaferStatus != list2[i].SideAWaferStatus || list1[i].SideBWaferId != list2[i].SideBWaferId || list1[i].SideBWaferType != list2[i].SideBWaferType || list1[i].SideBWaferStatus != list2[i].SideBWaferStatus || list1[i].ModuleName != list2[i].ModuleName) { return false; } } return true; } #endregion } }