桌面端快检记录新增列表及同步mes
This commit is contained in:
@@ -10,9 +10,12 @@ using Prism.Events;
|
||||
|
||||
using Prism.Mvvm;
|
||||
|
||||
using Prism.Navigation;
|
||||
|
||||
using SkiaSharp;
|
||||
|
||||
using System.Collections.ObjectModel;
|
||||
using System.Threading;
|
||||
|
||||
using YY.Admin.Core;
|
||||
|
||||
@@ -165,11 +168,11 @@ public class QuickTestInspectRowViewModel : BindableBase
|
||||
|
||||
/// <summary>胶料快检记录操作台 ViewModel(密炼计划、实验标准均读本地缓存)</summary>
|
||||
|
||||
public class RubberQuickTestOperationViewModel : BaseViewModel
|
||||
public class RubberQuickTestOperationViewModel : BaseViewModel, INavigationAware
|
||||
|
||||
{
|
||||
|
||||
private readonly IRubberQuickTestOperationService _operationService;
|
||||
private readonly IRubberQuickTestRecordService _recordService;
|
||||
|
||||
private readonly IMixingProductionPlanService _planService;
|
||||
|
||||
@@ -177,6 +180,12 @@ public class RubberQuickTestOperationViewModel : BaseViewModel
|
||||
|
||||
private readonly Random _rnd = new();
|
||||
|
||||
private bool _saveInProgress;
|
||||
|
||||
private string? _loadedDetailLocalId;
|
||||
private string? _loadedDetailMesId;
|
||||
private int _navigationApplyVersion;
|
||||
|
||||
private List<MesXslMixingProductionPlan> _allPlans = new();
|
||||
|
||||
private List<MesXslRubberQuickTestStd> _allStds = new();
|
||||
@@ -200,7 +209,7 @@ public class RubberQuickTestOperationViewModel : BaseViewModel
|
||||
|
||||
public RubberQuickTestOperationViewModel(
|
||||
|
||||
IRubberQuickTestOperationService operationService,
|
||||
IRubberQuickTestRecordService recordService,
|
||||
|
||||
IMixingProductionPlanService planService,
|
||||
|
||||
@@ -212,7 +221,7 @@ public class RubberQuickTestOperationViewModel : BaseViewModel
|
||||
|
||||
{
|
||||
|
||||
_operationService = operationService;
|
||||
_recordService = recordService;
|
||||
|
||||
_planService = planService;
|
||||
|
||||
@@ -228,7 +237,7 @@ public class RubberQuickTestOperationViewModel : BaseViewModel
|
||||
|
||||
RemoveInspectRowCommand = new DelegateCommand(() => RemoveInspectRow(SelectedInspectRow), () => SelectedInspectRow != null);
|
||||
|
||||
SaveCommand = new DelegateCommand(async () => await SaveAsync(), () => InspectRows.Count > 0);
|
||||
SaveCommand = new DelegateCommand(async () => await SaveAsync(), () => CanSave);
|
||||
|
||||
RefreshPlansCommand = new DelegateCommand(async () => await LoadLocalDataAsync(showSuccess: true));
|
||||
|
||||
@@ -259,13 +268,104 @@ public class RubberQuickTestOperationViewModel : BaseViewModel
|
||||
_stdChangedToken = _eventAggregator.GetEvent<RubberQuickTestStdChangedEvent>()
|
||||
.Subscribe(async _ => await ReloadLocalDataQuietAsync(), ThreadOption.UIThread);
|
||||
|
||||
|
||||
|
||||
_ = LoadLocalDataAsync(showSuccess: false);
|
||||
|
||||
RecalculateOverallInspectResult();
|
||||
}
|
||||
|
||||
private bool _isReadOnly;
|
||||
public bool IsReadOnly
|
||||
{
|
||||
get => _isReadOnly;
|
||||
private set
|
||||
{
|
||||
if (!SetProperty(ref _isReadOnly, value)) return;
|
||||
RaisePropertyChanged(nameof(IsEditable));
|
||||
RaisePropertyChanged(nameof(ShowSaveButton));
|
||||
NotifySaveStateChanged();
|
||||
InspectColumnsChanged?.Invoke();
|
||||
}
|
||||
}
|
||||
|
||||
public bool IsEditable => !IsReadOnly;
|
||||
public bool ShowSaveButton => !IsReadOnly;
|
||||
public bool CanSave => InspectRows.Count > 0 && !_saveInProgress && !IsReadOnly;
|
||||
|
||||
private void NotifySaveStateChanged()
|
||||
{
|
||||
RaisePropertyChanged(nameof(CanSave));
|
||||
SaveCommand.RaiseCanExecuteChanged();
|
||||
}
|
||||
|
||||
protected override void OnIsLoadingChanged()
|
||||
{
|
||||
base.OnIsLoadingChanged();
|
||||
NotifySaveStateChanged();
|
||||
}
|
||||
|
||||
public void OnNavigatedTo(NavigationContext navigationContext)
|
||||
{
|
||||
_ = ApplyNavigationAsync(navigationContext.Parameters);
|
||||
}
|
||||
|
||||
private async Task ApplyNavigationAsync(INavigationParameters parameters)
|
||||
{
|
||||
var version = Interlocked.Increment(ref _navigationApplyVersion);
|
||||
|
||||
if (parameters.TryGetValue<bool>("readOnly", out var readOnly) && readOnly)
|
||||
{
|
||||
if (parameters.TryGetValue<string>("localId", out var localId) && !string.IsNullOrWhiteSpace(localId))
|
||||
{
|
||||
_loadedDetailLocalId = localId;
|
||||
_loadedDetailMesId = null;
|
||||
await LoadFromLocalItemAsync(localId);
|
||||
return;
|
||||
}
|
||||
|
||||
if (parameters.TryGetValue<string>("mesId", out var mesId) && !string.IsNullOrWhiteSpace(mesId))
|
||||
{
|
||||
_loadedDetailMesId = mesId;
|
||||
_loadedDetailLocalId = null;
|
||||
await LoadFromMesIdAsync(mesId);
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
if (version != _navigationApplyVersion) return;
|
||||
|
||||
_loadedDetailLocalId = null;
|
||||
_loadedDetailMesId = null;
|
||||
IsReadOnly = false;
|
||||
ResetFormForNewEntry();
|
||||
await LoadLocalDataAsync(showSuccess: false);
|
||||
}
|
||||
|
||||
public bool IsNavigationTarget(NavigationContext navigationContext)
|
||||
{
|
||||
var parameters = navigationContext.Parameters;
|
||||
if (parameters.TryGetValue<bool>("readOnly", out var readOnly) && readOnly)
|
||||
{
|
||||
if (parameters.TryGetValue<string>("localId", out var localId) && !string.IsNullOrWhiteSpace(localId))
|
||||
return IsReadOnly && string.Equals(_loadedDetailLocalId, localId, StringComparison.OrdinalIgnoreCase);
|
||||
|
||||
if (parameters.TryGetValue<string>("mesId", out var mesId) && !string.IsNullOrWhiteSpace(mesId))
|
||||
return IsReadOnly && string.Equals(_loadedDetailMesId, mesId, StringComparison.OrdinalIgnoreCase);
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
return !IsReadOnly && _loadedDetailLocalId == null && _loadedDetailMesId == null;
|
||||
}
|
||||
|
||||
private void ResetFormForNewEntry()
|
||||
{
|
||||
RecordNo = null;
|
||||
TrainNo = null;
|
||||
InspectTimesText = "1";
|
||||
ClearPlanAndStdSelection();
|
||||
RecalculateOverallInspectResult();
|
||||
NotifySaveStateChanged();
|
||||
}
|
||||
public void OnNavigatedFrom(NavigationContext navigationContext) { }
|
||||
|
||||
|
||||
|
||||
private static string ResolveInspectorDisplay()
|
||||
@@ -648,8 +748,8 @@ public class RubberQuickTestOperationViewModel : BaseViewModel
|
||||
|
||||
|
||||
private async Task ReloadLocalDataQuietAsync()
|
||||
|
||||
{
|
||||
if (IsReadOnly) return;
|
||||
|
||||
try
|
||||
|
||||
@@ -1070,7 +1170,7 @@ public class RubberQuickTestOperationViewModel : BaseViewModel
|
||||
|
||||
InspectRows.Add(row);
|
||||
|
||||
SaveCommand.RaiseCanExecuteChanged();
|
||||
NotifySaveStateChanged();
|
||||
|
||||
RecalculateOverallInspectResult();
|
||||
|
||||
@@ -1090,7 +1190,7 @@ public class RubberQuickTestOperationViewModel : BaseViewModel
|
||||
|
||||
RenumberInspectRows();
|
||||
|
||||
SaveCommand.RaiseCanExecuteChanged();
|
||||
NotifySaveStateChanged();
|
||||
|
||||
RecalculateOverallInspectResult();
|
||||
|
||||
@@ -1099,145 +1199,90 @@ public class RubberQuickTestOperationViewModel : BaseViewModel
|
||||
|
||||
|
||||
private async Task SaveAsync()
|
||||
|
||||
{
|
||||
if (_saveInProgress) return;
|
||||
|
||||
if (string.IsNullOrWhiteSpace(TrainNo))
|
||||
|
||||
{
|
||||
|
||||
Growl.Warning("请填写车次");
|
||||
|
||||
return;
|
||||
|
||||
}
|
||||
|
||||
if (SelectedPlan == null)
|
||||
|
||||
{
|
||||
|
||||
Growl.Warning("请选择密炼计划");
|
||||
|
||||
return;
|
||||
|
||||
}
|
||||
|
||||
if (string.IsNullOrWhiteSpace(RubberMaterialName))
|
||||
|
||||
{
|
||||
|
||||
Growl.Warning("请先选择密炼计划以带出胶料名称");
|
||||
|
||||
return;
|
||||
|
||||
}
|
||||
|
||||
if (SelectedStd == null || _currentStd == null)
|
||||
|
||||
{
|
||||
|
||||
Growl.Warning("请选择实验标准");
|
||||
|
||||
return;
|
||||
|
||||
}
|
||||
|
||||
|
||||
|
||||
if (InspectRows.Any(r => r.InspectResultText == "待填写" || string.IsNullOrWhiteSpace(r.InspectResultText)))
|
||||
|
||||
{
|
||||
|
||||
Growl.Warning("请手填全部检验行的检测值后再保存");
|
||||
|
||||
return;
|
||||
|
||||
}
|
||||
|
||||
|
||||
|
||||
if (!TryParseInspectTimes(out var inspectTimes, out var inspectTimesError))
|
||||
|
||||
{
|
||||
|
||||
Growl.Warning(inspectTimesError);
|
||||
|
||||
return;
|
||||
|
||||
}
|
||||
|
||||
|
||||
|
||||
var lineList = BuildAveragedLineList();
|
||||
|
||||
if (lineList.Count == 0)
|
||||
|
||||
{
|
||||
|
||||
Growl.Warning("无法根据试验结果计算明细数据");
|
||||
|
||||
return;
|
||||
|
||||
}
|
||||
|
||||
|
||||
|
||||
var rawLineList = BuildRawLineList();
|
||||
|
||||
if (rawLineList.Count == 0)
|
||||
|
||||
{
|
||||
|
||||
Growl.Warning("无法生成试验结果原始数据");
|
||||
|
||||
return;
|
||||
|
||||
}
|
||||
|
||||
|
||||
|
||||
var user = AppSession.CurrentUser;
|
||||
|
||||
IsLoading = true;
|
||||
_saveInProgress = true;
|
||||
NotifySaveStateChanged();
|
||||
|
||||
try
|
||||
|
||||
{
|
||||
if (string.IsNullOrWhiteSpace(TrainNo))
|
||||
{
|
||||
Growl.Warning("请填写车次");
|
||||
return;
|
||||
}
|
||||
|
||||
var record = BuildSaveRecord(lineList, rawLineList, inspectTimes, user);
|
||||
if (SelectedPlan == null)
|
||||
{
|
||||
Growl.Warning("请选择密炼计划");
|
||||
return;
|
||||
}
|
||||
|
||||
var recordNo = await _operationService.SaveRecordAsync(record);
|
||||
if (string.IsNullOrWhiteSpace(RubberMaterialName))
|
||||
{
|
||||
Growl.Warning("请先选择密炼计划以带出胶料名称");
|
||||
return;
|
||||
}
|
||||
|
||||
RecordNo = recordNo;
|
||||
if (SelectedStd == null || _currentStd == null)
|
||||
{
|
||||
Growl.Warning("请选择实验标准");
|
||||
return;
|
||||
}
|
||||
|
||||
Growl.Success(string.IsNullOrWhiteSpace(recordNo)
|
||||
if (InspectRows.Any(r => r.InspectResultText == "待填写" || string.IsNullOrWhiteSpace(r.InspectResultText)))
|
||||
{
|
||||
Growl.Warning("请手填全部检验行的检测值后再保存");
|
||||
return;
|
||||
}
|
||||
|
||||
? "胶料快检记录已保存到 MES"
|
||||
if (!TryParseInspectTimes(out var inspectTimes, out var inspectTimesError))
|
||||
{
|
||||
Growl.Warning(inspectTimesError);
|
||||
return;
|
||||
}
|
||||
|
||||
: $"胶料快检记录已保存,单号:{recordNo}");
|
||||
var rawLineList = BuildRawLineList();
|
||||
if (rawLineList.Count == 0)
|
||||
{
|
||||
Growl.Warning("无法生成试验结果原始数据");
|
||||
return;
|
||||
}
|
||||
|
||||
var stdLineList = BuildStdLineList();
|
||||
if (stdLineList.Count == 0)
|
||||
{
|
||||
Growl.Warning("无法生成数据标准明细");
|
||||
return;
|
||||
}
|
||||
|
||||
var chartPointList = BuildChartPointList();
|
||||
var user = AppSession.CurrentUser;
|
||||
|
||||
IsLoading = true;
|
||||
var record = BuildSaveRecord(stdLineList, rawLineList, chartPointList, inspectTimes, user);
|
||||
var saved = await _recordService.SaveAsync(record);
|
||||
RecordNo = saved.Record.RecordNo;
|
||||
|
||||
var syncHint = saved.SyncStatus == "Synced" ? "并已同步到 MES" : "(MES 同步待重试)";
|
||||
Growl.Success(string.IsNullOrWhiteSpace(RecordNo)
|
||||
? $"胶料快检记录已保存到本地{syncHint}"
|
||||
: $"胶料快检记录已保存,快检记录号:{RecordNo}{syncHint}");
|
||||
|
||||
InspectRows.Clear();
|
||||
|
||||
SaveCommand.RaiseCanExecuteChanged();
|
||||
|
||||
NotifySaveStateChanged();
|
||||
}
|
||||
|
||||
catch (Exception ex)
|
||||
|
||||
{
|
||||
|
||||
Growl.Error($"保存失败:{ex.Message}");
|
||||
|
||||
}
|
||||
|
||||
finally
|
||||
|
||||
{
|
||||
|
||||
IsLoading = false;
|
||||
|
||||
_saveInProgress = false;
|
||||
NotifySaveStateChanged();
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
|
||||
@@ -1432,10 +1477,12 @@ public class RubberQuickTestOperationViewModel : BaseViewModel
|
||||
|
||||
private MesXslRubberQuickTestRecord BuildSaveRecord(
|
||||
|
||||
List<MesXslRubberQuickTestRecordLine> lineList,
|
||||
List<MesXslRubberQuickTestRecordStdLine> stdLineList,
|
||||
|
||||
List<MesXslRubberQuickTestRecordRawLine> rawLineList,
|
||||
|
||||
List<MesXslRubberQuickTestRecordChartPoint> chartPointList,
|
||||
|
||||
int inspectTimes,
|
||||
|
||||
SysUser? user)
|
||||
@@ -1446,13 +1493,19 @@ public class RubberQuickTestOperationViewModel : BaseViewModel
|
||||
|
||||
{
|
||||
|
||||
LineList = lineList,
|
||||
StdLineList = stdLineList,
|
||||
|
||||
RawLineList = rawLineList,
|
||||
|
||||
ChartPointList = chartPointList,
|
||||
|
||||
InspectTime = DateTime.Now,
|
||||
|
||||
InspectResult = OverallInspectResultCode
|
||||
CreateTime = DateTime.Now,
|
||||
|
||||
InspectResult = OverallInspectResultCode,
|
||||
|
||||
RecordNo = _recordService.GenerateRecordNo(RubberMaterialName ?? string.Empty)
|
||||
|
||||
};
|
||||
|
||||
@@ -1470,6 +1523,26 @@ public class RubberQuickTestOperationViewModel : BaseViewModel
|
||||
|
||||
record.StdId = _currentStd.Id;
|
||||
|
||||
if (!string.IsNullOrWhiteSpace(_currentStd?.StdName))
|
||||
|
||||
record.StdName = _currentStd.StdName;
|
||||
|
||||
if (!string.IsNullOrWhiteSpace(_currentStd?.TestMethodId))
|
||||
|
||||
record.TestMethodId = _currentStd.TestMethodId;
|
||||
|
||||
if (!string.IsNullOrWhiteSpace(TestMethodName))
|
||||
|
||||
record.TestMethodName = TestMethodName;
|
||||
|
||||
if (!string.IsNullOrWhiteSpace(_currentStd?.QuickTestTypeId))
|
||||
|
||||
record.QuickTestTypeId = _currentStd.QuickTestTypeId;
|
||||
|
||||
if (!string.IsNullOrWhiteSpace(_currentStd?.QuickTestTypeName))
|
||||
|
||||
record.QuickTestTypeName = _currentStd.QuickTestTypeName;
|
||||
|
||||
|
||||
|
||||
if (!string.IsNullOrWhiteSpace(_selectedPlan?.MachineId))
|
||||
@@ -1502,9 +1575,9 @@ public class RubberQuickTestOperationViewModel : BaseViewModel
|
||||
|
||||
|
||||
|
||||
if (!string.IsNullOrWhiteSpace(_selectedPlan?.PlanMaterialNo))
|
||||
if (!string.IsNullOrWhiteSpace(_selectedPlan?.PlanNo))
|
||||
|
||||
record.ProductionPlanNo = _selectedPlan.PlanMaterialNo;
|
||||
record.ProductionPlanNo = _selectedPlan.PlanNo;
|
||||
|
||||
|
||||
|
||||
@@ -1528,6 +1601,169 @@ public class RubberQuickTestOperationViewModel : BaseViewModel
|
||||
|
||||
}
|
||||
|
||||
private List<MesXslRubberQuickTestRecordStdLine> BuildStdLineList()
|
||||
{
|
||||
var lines = new List<MesXslRubberQuickTestRecordStdLine>();
|
||||
int sort = 0;
|
||||
foreach (var col in DataPointColumns)
|
||||
{
|
||||
lines.Add(new MesXslRubberQuickTestRecordStdLine
|
||||
{
|
||||
DataPointId = col.DataPointId,
|
||||
PointName = col.PointName,
|
||||
LowerLimit = col.LowerLimit,
|
||||
LowerWarn = col.LowerWarn,
|
||||
TargetValue = col.TargetValue,
|
||||
UpperWarn = col.UpperWarn,
|
||||
UpperLimit = col.UpperLimit,
|
||||
SortNo = sort++
|
||||
});
|
||||
}
|
||||
return lines;
|
||||
}
|
||||
|
||||
private List<MesXslRubberQuickTestRecordChartPoint> BuildChartPointList()
|
||||
{
|
||||
var points = new List<MesXslRubberQuickTestRecordChartPoint>();
|
||||
int sort = 0;
|
||||
for (int i = 0; i < ChartPointCount && i < UpperTempValues.Count; i++)
|
||||
{
|
||||
points.Add(new MesXslRubberQuickTestRecordChartPoint
|
||||
{
|
||||
TimeMin = (decimal)(UpperTempValues[i].X ?? ChartTimeMinutes[i]),
|
||||
UpperTemp = UpperTempValues[i].Y.HasValue ? (decimal)UpperTempValues[i].Y!.Value : null,
|
||||
LowerTemp = i < LowerTempValues.Count && LowerTempValues[i].Y.HasValue ? (decimal)LowerTempValues[i].Y!.Value : null,
|
||||
TorqueS = i < TorqueValues.Count && TorqueValues[i].Y.HasValue ? (decimal)TorqueValues[i].Y!.Value : null,
|
||||
SortNo = sort++
|
||||
});
|
||||
}
|
||||
return points;
|
||||
}
|
||||
|
||||
private async Task LoadFromLocalItemAsync(string localId)
|
||||
{
|
||||
var item = _recordService.GetByLocalId(localId);
|
||||
if (item == null)
|
||||
{
|
||||
Growl.Warning("未找到快检记录");
|
||||
return;
|
||||
}
|
||||
|
||||
await ApplyRecordDetailAsync(item.Record);
|
||||
}
|
||||
|
||||
private async Task LoadFromMesIdAsync(string mesId)
|
||||
{
|
||||
var record = await _recordService.GetByIdAsync(mesId);
|
||||
if (record == null)
|
||||
{
|
||||
Growl.Warning("未找到快检记录");
|
||||
return;
|
||||
}
|
||||
|
||||
await ApplyRecordDetailAsync(record);
|
||||
}
|
||||
|
||||
private async Task ApplyRecordDetailAsync(MesXslRubberQuickTestRecord r)
|
||||
{
|
||||
IsReadOnly = true;
|
||||
RecordNo = r.RecordNo;
|
||||
MixingDate = r.ProductionDate ?? DateTime.Today;
|
||||
SelectedMachine = r.ProdEquipmentName;
|
||||
TrainNo = r.TrainNo;
|
||||
InspectTimesText = r.InspectTimes?.ToString() ?? "1";
|
||||
InspectorDisplay = r.InspectorRealname ?? ResolveInspectorDisplay();
|
||||
OverallInspectResultCode = r.InspectResult ?? "0";
|
||||
OverallInspectResultDisplay = string.Equals(r.InspectResult, "1", StringComparison.Ordinal) ? "合格" : "不合格";
|
||||
TestMethodName = r.TestMethodName;
|
||||
|
||||
MachineOptions.Clear();
|
||||
if (!string.IsNullOrWhiteSpace(r.ProdEquipmentName))
|
||||
MachineOptions.Add(r.ProdEquipmentName);
|
||||
|
||||
ShiftOptions.Clear();
|
||||
var shift = new WorkShiftOption(r.WorkShift ?? "", r.WorkShift ?? "");
|
||||
ShiftOptions.Add(shift);
|
||||
SelectedShift = shift;
|
||||
|
||||
PlanOptions.Clear();
|
||||
var plan = new MesXslMixingProductionPlan
|
||||
{
|
||||
PlanNo = r.ProductionPlanNo,
|
||||
MaterialName = r.RubberMaterialName,
|
||||
MachineName = r.ProdEquipmentName
|
||||
};
|
||||
PlanOptions.Add(plan);
|
||||
_selectedPlan = plan;
|
||||
RaisePropertyChanged(nameof(SelectedPlan));
|
||||
RaisePropertyChanged(nameof(MachineName));
|
||||
RaisePropertyChanged(nameof(RubberMaterialName));
|
||||
|
||||
StdOptions.Clear();
|
||||
var std = new MesXslRubberQuickTestStd { Id = r.StdId, StdName = r.StdName, TestMethodName = r.TestMethodName };
|
||||
StdOptions.Add(std);
|
||||
_selectedStd = std;
|
||||
RaisePropertyChanged(nameof(SelectedStd));
|
||||
|
||||
DataPointColumns.Clear();
|
||||
InspectRows.Clear();
|
||||
foreach (var sl in (r.StdLineList ?? new List<MesXslRubberQuickTestRecordStdLine>()).OrderBy(x => x.SortNo ?? 0))
|
||||
{
|
||||
DataPointColumns.Add(new MesXslRubberQuickTestStdLine
|
||||
{
|
||||
DataPointId = sl.DataPointId,
|
||||
PointName = sl.PointName,
|
||||
LowerLimit = sl.LowerLimit,
|
||||
LowerWarn = sl.LowerWarn,
|
||||
TargetValue = sl.TargetValue,
|
||||
UpperWarn = sl.UpperWarn,
|
||||
UpperLimit = sl.UpperLimit,
|
||||
SortNo = sl.SortNo
|
||||
});
|
||||
}
|
||||
InspectColumnsChanged?.Invoke();
|
||||
|
||||
var grouped = (r.RawLineList ?? new List<MesXslRubberQuickTestRecordRawLine>())
|
||||
.GroupBy(x => x.RowNo ?? string.Empty)
|
||||
.OrderBy(g => g.Key, StringComparer.Ordinal);
|
||||
foreach (var g in grouped)
|
||||
{
|
||||
var row = new QuickTestInspectRowViewModel { RowNo = g.Key };
|
||||
for (int i = 0; i < DataPointColumns.Count; i++)
|
||||
{
|
||||
var col = DataPointColumns[i];
|
||||
var raw = g.FirstOrDefault(x => x.DataPointId == col.DataPointId || x.InspectItem == col.PointName);
|
||||
var cell = new QuickTestInspectCellViewModel
|
||||
{
|
||||
DataPointId = col.DataPointId,
|
||||
PointName = col.PointName ?? string.Empty,
|
||||
LowerLimit = col.LowerLimit,
|
||||
UpperLimit = col.UpperLimit,
|
||||
Value = raw?.InspectValue
|
||||
};
|
||||
row.Cells.Add(cell);
|
||||
}
|
||||
row.RecalculateResult();
|
||||
InspectRows.Add(row);
|
||||
}
|
||||
|
||||
UpperTempValues.Clear();
|
||||
LowerTempValues.Clear();
|
||||
TorqueValues.Clear();
|
||||
foreach (var pt in (r.ChartPointList ?? new List<MesXslRubberQuickTestRecordChartPoint>()).OrderBy(x => x.SortNo ?? 0))
|
||||
{
|
||||
var time = (double)(pt.TimeMin ?? 0);
|
||||
if (pt.UpperTemp != null) UpperTempValues.Add(new ObservablePoint(time, (double)pt.UpperTemp.Value));
|
||||
if (pt.LowerTemp != null) LowerTempValues.Add(new ObservablePoint(time, (double)pt.LowerTemp.Value));
|
||||
if (pt.TorqueS != null) TorqueValues.Add(new ObservablePoint(time, (double)pt.TorqueS.Value));
|
||||
}
|
||||
if (UpperTempValues.Count > 0) UpperMoldTemp = UpperTempValues[^1].Y ?? 0;
|
||||
if (LowerTempValues.Count > 0) LowerMoldTemp = LowerTempValues[^1].Y ?? 0;
|
||||
if (TorqueValues.Count > 0) TorqueS = TorqueValues[^1].Y ?? 0;
|
||||
|
||||
await Task.CompletedTask;
|
||||
}
|
||||
|
||||
|
||||
|
||||
private static Axis[] BuildTimeAxis() => new[]
|
||||
|
||||
@@ -0,0 +1,104 @@
|
||||
using LiveChartsCore;
|
||||
using LiveChartsCore.Defaults;
|
||||
using LiveChartsCore.SkiaSharpView;
|
||||
using Prism.Mvvm;
|
||||
using System.Collections.ObjectModel;
|
||||
using YY.Admin.Core.Entity;
|
||||
|
||||
namespace YY.Admin.ViewModels.RubberQuickTest;
|
||||
|
||||
public class RubberQuickTestRecordDetailDialogViewModel : BindableBase
|
||||
{
|
||||
private MesXslRubberQuickTestRecord? _record;
|
||||
public MesXslRubberQuickTestRecord? Record
|
||||
{
|
||||
get => _record;
|
||||
private set => SetProperty(ref _record, value);
|
||||
}
|
||||
|
||||
private string? _inspectResultDisplay;
|
||||
public string? InspectResultDisplay
|
||||
{
|
||||
get => _inspectResultDisplay;
|
||||
private set => SetProperty(ref _inspectResultDisplay, value);
|
||||
}
|
||||
|
||||
public ObservableCollection<MesXslRubberQuickTestRecordStdLine> StdLines { get; } = new();
|
||||
public ObservableCollection<MesXslRubberQuickTestRecordRawLine> RawLines { get; } = new();
|
||||
|
||||
public ObservableCollection<ISeries> TemperatureSeries { get; }
|
||||
public ObservableCollection<ISeries> TorqueSeries { get; }
|
||||
public ObservableCollection<ObservablePoint> UpperTempValues { get; } = new();
|
||||
public ObservableCollection<ObservablePoint> LowerTempValues { get; } = new();
|
||||
public ObservableCollection<ObservablePoint> TorqueValues { get; } = new();
|
||||
|
||||
public Axis[] TemperatureXAxes { get; } = BuildTimeAxis();
|
||||
public Axis[] TemperatureYAxes { get; } = BuildTempYAxis();
|
||||
public Axis[] TorqueXAxes { get; } = BuildTimeAxis();
|
||||
public Axis[] TorqueYAxes { get; } = BuildTorqueYAxis();
|
||||
|
||||
public RubberQuickTestRecordDetailDialogViewModel()
|
||||
{
|
||||
TemperatureSeries = new ObservableCollection<ISeries>
|
||||
{
|
||||
new LineSeries<ObservablePoint> { Name = "上模温度", Values = UpperTempValues, GeometrySize = 4, LineSmoothness = 0.3 },
|
||||
new LineSeries<ObservablePoint> { Name = "下模温度", Values = LowerTempValues, GeometrySize = 4, LineSmoothness = 0.3 }
|
||||
};
|
||||
TorqueSeries = new ObservableCollection<ISeries>
|
||||
{
|
||||
new LineSeries<ObservablePoint> { Name = "S'(dNm)", Values = TorqueValues, GeometrySize = 4, LineSmoothness = 0.3 }
|
||||
};
|
||||
}
|
||||
|
||||
public void Initialize(MesXslRubberQuickTestRecord record)
|
||||
{
|
||||
Record = record;
|
||||
InspectResultDisplay = record.InspectResult switch
|
||||
{
|
||||
"1" => "合格",
|
||||
"0" => "不合格",
|
||||
_ => record.InspectResultText ?? record.InspectResult ?? ""
|
||||
};
|
||||
StdLines.Clear();
|
||||
foreach (var line in record.StdLineList ?? [])
|
||||
StdLines.Add(line);
|
||||
|
||||
RawLines.Clear();
|
||||
foreach (var line in record.RawLineList ?? [])
|
||||
RawLines.Add(line);
|
||||
|
||||
UpperTempValues.Clear();
|
||||
LowerTempValues.Clear();
|
||||
TorqueValues.Clear();
|
||||
foreach (var p in (record.ChartPointList ?? []).OrderBy(x => x.SortNo ?? 0))
|
||||
{
|
||||
var time = (double)(p.TimeMin ?? 0);
|
||||
UpperTempValues.Add(new ObservablePoint(time, (double)(p.UpperTemp ?? 0)));
|
||||
LowerTempValues.Add(new ObservablePoint(time, (double)(p.LowerTemp ?? 0)));
|
||||
TorqueValues.Add(new ObservablePoint(time, (double)(p.TorqueS ?? 0)));
|
||||
}
|
||||
}
|
||||
|
||||
private static Axis[] BuildTimeAxis() => new[]
|
||||
{
|
||||
new Axis { Name = "时间(min)", MinLimit = 0, MaxLimit = 2, Labeler = v => v.ToString("0.0#") }
|
||||
};
|
||||
|
||||
private static Axis[] BuildTempYAxis() => new[]
|
||||
{
|
||||
new Axis { Name = "温度(℃)", MinLimit = 189, MaxLimit = 201 }
|
||||
};
|
||||
|
||||
private static readonly double[] TorqueYTicks = { 0.0, 3.0, 5.9, 8.9, 11.8, 14.8 };
|
||||
|
||||
private static Axis[] BuildTorqueYAxis() => new[]
|
||||
{
|
||||
new Axis
|
||||
{
|
||||
Name = "S'(dNm)",
|
||||
MinLimit = 0,
|
||||
MaxLimit = 14.8,
|
||||
CustomSeparators = TorqueYTicks
|
||||
}
|
||||
};
|
||||
}
|
||||
@@ -0,0 +1,227 @@
|
||||
using HandyControl.Controls;
|
||||
using Prism.Events;
|
||||
using Prism.Navigation;
|
||||
using System.Collections.ObjectModel;
|
||||
using System.Diagnostics;
|
||||
using YY.Admin.Core;
|
||||
using YY.Admin.Core.Entity;
|
||||
using YY.Admin.Core.Events;
|
||||
using YY.Admin.Core.Helper;
|
||||
using YY.Admin.Core.Services;
|
||||
using YY.Admin.Event;
|
||||
using YY.Admin.Module;
|
||||
using YY.Admin.Services.Service;
|
||||
|
||||
namespace YY.Admin.ViewModels.RubberQuickTest;
|
||||
|
||||
public class RubberQuickTestRecordListViewModel : BaseViewModel
|
||||
{
|
||||
private readonly IRubberQuickTestRecordService _recordService;
|
||||
private readonly IJeecgDictSyncService _dictSyncService;
|
||||
private SubscriptionToken? _changedToken;
|
||||
|
||||
private ObservableCollection<RubberQuickTestRecordListRow> _records = new();
|
||||
public ObservableCollection<RubberQuickTestRecordListRow> Records
|
||||
{
|
||||
get => _records;
|
||||
set => SetProperty(ref _records, value);
|
||||
}
|
||||
|
||||
private long _total;
|
||||
public long Total { get => _total; set => SetProperty(ref _total, value); }
|
||||
|
||||
private int _pageNo = 1;
|
||||
public int PageNo { get => _pageNo; set => SetProperty(ref _pageNo, value); }
|
||||
|
||||
private int _pageSize = 20;
|
||||
public int PageSize { get => _pageSize; set => SetProperty(ref _pageSize, value); }
|
||||
|
||||
private string? _filterRecordNo;
|
||||
public string? FilterRecordNo { get => _filterRecordNo; set => SetProperty(ref _filterRecordNo, value); }
|
||||
|
||||
private string? _filterRubberMaterialName;
|
||||
public string? FilterRubberMaterialName { get => _filterRubberMaterialName; set => SetProperty(ref _filterRubberMaterialName, value); }
|
||||
|
||||
private string? _filterPlanNo;
|
||||
public string? FilterPlanNo { get => _filterPlanNo; set => SetProperty(ref _filterPlanNo, value); }
|
||||
|
||||
public DelegateCommand SearchCommand { get; }
|
||||
public DelegateCommand ResetCommand { get; }
|
||||
public DelegateCommand AddCommand { get; }
|
||||
public DelegateCommand<RubberQuickTestRecordListRow> ViewDetailCommand { get; }
|
||||
public DelegateCommand<RubberQuickTestRecordListRow> DeleteCommand { get; }
|
||||
public DelegateCommand PrevPageCommand { get; }
|
||||
public DelegateCommand NextPageCommand { get; }
|
||||
|
||||
public RubberQuickTestRecordListViewModel(
|
||||
IRubberQuickTestRecordService recordService,
|
||||
IJeecgDictSyncService dictSyncService,
|
||||
IContainerExtension container,
|
||||
IRegionManager regionManager) : base(container, regionManager)
|
||||
{
|
||||
_recordService = recordService;
|
||||
_dictSyncService = dictSyncService;
|
||||
|
||||
SearchCommand = new DelegateCommand(async () => { PageNo = 1; await LoadAsync(); });
|
||||
ResetCommand = new DelegateCommand(async () =>
|
||||
{
|
||||
FilterRecordNo = null;
|
||||
FilterRubberMaterialName = null;
|
||||
FilterPlanNo = null;
|
||||
PageNo = 1;
|
||||
await LoadAsync();
|
||||
});
|
||||
AddCommand = new DelegateCommand(OpenAddPage);
|
||||
ViewDetailCommand = new DelegateCommand<RubberQuickTestRecordListRow>(async r => await ShowDetailAsync(r));
|
||||
DeleteCommand = new DelegateCommand<RubberQuickTestRecordListRow>(
|
||||
async r => await DeleteAsync(r),
|
||||
r => r != null && r.CanDelete);
|
||||
PrevPageCommand = new DelegateCommand(async () => { if (PageNo > 1) { PageNo--; await LoadAsync(); } });
|
||||
NextPageCommand = new DelegateCommand(async () => { if ((long)PageNo * PageSize < Total) { PageNo++; await LoadAsync(); } });
|
||||
|
||||
_changedToken = _eventAggregator.GetEvent<RubberQuickTestRecordChangedEvent>()
|
||||
.Subscribe(async _ => await LoadAsync(), ThreadOption.UIThread);
|
||||
|
||||
_ = InitializeAsync();
|
||||
}
|
||||
|
||||
private async Task InitializeAsync()
|
||||
{
|
||||
try
|
||||
{
|
||||
await UIHelper.WaitForRenderAsync();
|
||||
await LoadAsync();
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
Debug.WriteLine($"快检记录列表初始化失败: {ex.Message}");
|
||||
}
|
||||
}
|
||||
|
||||
public async Task LoadAsync()
|
||||
{
|
||||
try
|
||||
{
|
||||
IsLoading = true;
|
||||
var result = await _recordService.PageAsync(
|
||||
PageNo, PageSize, FilterRecordNo, FilterRubberMaterialName, FilterPlanNo);
|
||||
|
||||
var shiftMap = (await _dictSyncService.GetDictOptionsAsync("xslmes_rubber_quick_test_work_shift", includeAll: false))
|
||||
.ToDictionary(x => x.Value, x => x.Key);
|
||||
foreach (var r in result.Records)
|
||||
{
|
||||
if (!string.IsNullOrWhiteSpace(r.WorkShiftDisplay) && shiftMap.TryGetValue(r.WorkShiftDisplay, out var txt))
|
||||
r.WorkShiftDisplay = txt;
|
||||
}
|
||||
|
||||
Records = new ObservableCollection<RubberQuickTestRecordListRow>(result.Records);
|
||||
Total = result.Total;
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
Growl.Error($"加载快检记录失败:{ex.Message}");
|
||||
}
|
||||
finally
|
||||
{
|
||||
IsLoading = false;
|
||||
}
|
||||
}
|
||||
|
||||
private void OpenAddPage()
|
||||
{
|
||||
_eventAggregator.GetEvent<TabSourceSelectedEvent>().Publish(new TabSource
|
||||
{
|
||||
Name = "新增胶料快检记录",
|
||||
Icon = "\ue7de",
|
||||
ViewName = "RubberQuickTestOperationView"
|
||||
});
|
||||
}
|
||||
|
||||
private async Task DeleteAsync(RubberQuickTestRecordListRow? row)
|
||||
{
|
||||
if (row == null || !row.CanDelete || string.IsNullOrWhiteSpace(row.LocalId))
|
||||
return;
|
||||
|
||||
var label = row.RecordNo ?? row.LocalId;
|
||||
var confirm = System.Windows.MessageBox.Show(
|
||||
$"确定删除同步失败的快检记录「{label}」?\n此操作仅删除本地记录,不可恢复。",
|
||||
"确认删除",
|
||||
System.Windows.MessageBoxButton.YesNo,
|
||||
System.Windows.MessageBoxImage.Warning);
|
||||
if (confirm != System.Windows.MessageBoxResult.Yes)
|
||||
return;
|
||||
|
||||
try
|
||||
{
|
||||
if (_recordService.DeleteFailedLocal(row.LocalId))
|
||||
{
|
||||
Growl.Success("删除成功");
|
||||
await LoadAsync();
|
||||
}
|
||||
else
|
||||
{
|
||||
Growl.Warning("仅同步失败的本地记录可删除");
|
||||
}
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
Growl.Error($"删除失败:{ex.Message}");
|
||||
}
|
||||
}
|
||||
|
||||
private async Task ShowDetailAsync(RubberQuickTestRecordListRow? row)
|
||||
{
|
||||
if (row == null) return;
|
||||
try
|
||||
{
|
||||
if (!string.IsNullOrWhiteSpace(row.LocalId))
|
||||
{
|
||||
if (_recordService.GetByLocalId(row.LocalId) == null)
|
||||
{
|
||||
Growl.Warning("未找到快检记录详情");
|
||||
return;
|
||||
}
|
||||
}
|
||||
else if (!string.IsNullOrWhiteSpace(row.MesId))
|
||||
{
|
||||
var remote = await _recordService.GetByIdAsync(row.MesId);
|
||||
if (remote == null)
|
||||
{
|
||||
Growl.Warning("未找到快检记录详情");
|
||||
return;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
Growl.Warning("无法定位快检记录");
|
||||
return;
|
||||
}
|
||||
|
||||
var parameters = new NavigationParameters { { "readOnly", true } };
|
||||
if (!string.IsNullOrWhiteSpace(row.LocalId))
|
||||
parameters.Add("localId", row.LocalId);
|
||||
else
|
||||
parameters.Add("mesId", row.MesId!);
|
||||
|
||||
var title = row.RecordNo ?? row.LocalId ?? row.MesId ?? "详情";
|
||||
_eventAggregator.GetEvent<TabSourceSelectedEvent>().Publish(new TabSource
|
||||
{
|
||||
Name = $"快检记录 {title}",
|
||||
Icon = "\ue7de",
|
||||
ViewName = "RubberQuickTestOperationView",
|
||||
NavigationParameter = parameters
|
||||
});
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
Growl.Error($"打开详情失败:{ex.Message}");
|
||||
}
|
||||
}
|
||||
|
||||
protected override void CleanUp()
|
||||
{
|
||||
base.CleanUp();
|
||||
if (_changedToken != null)
|
||||
_eventAggregator.GetEvent<RubberQuickTestRecordChangedEvent>().Unsubscribe(_changedToken);
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user