using System; using System.Linq; using System.Collections.ObjectModel; using System.Collections.Generic; using System.ComponentModel; using System.Drawing.Imaging; using System.Data; using System.Drawing; using System.IO; using System.Text; using System.Threading; using System.Windows.Forms; using SmartX; using INT69DC_ImageDll; using INT69DC_7C.DialogForms; using INT69DC_7C.Controls; namespace INT69DC_7C.Forms { public partial class FormDataStatistics : Form { #region Field private int FileIndex; public string SelectFilePath; private FormMain m_ParentForm; public DataCommonList CurrentDataCommonList; private Collection CollectionWeightData; //파일에서 읽은 데이터 private Collection CollectionLaneData; //파일에서 읽은 데이터를 통계 계산 처리된 데이터 private Collection CollectionCommonLabel; private Collection CollectionLane; private Collection CollectionPassCount; private Collection CollectionPassAverage; private Collection CollectionPassPercentage; private Collection CollectionPassSD; private Collection CollectionPassMinWeight; private Collection CollectionPassMaxWeight; private Collection CollectionOverCount; private Collection CollectionOverSumWeight; private Collection CollectionOverPercentage; private Collection CollectionUnderCount; private Collection CollectionUnderSumWeight; private Collection CollectionUnderPercentage; private Collection CollectionExNgCount; private Collection CollectionExNgPercentage; private Collection CollectionTotalCount; private Collection CollectionTotalNGCount; #endregion #region Constructor public FormDataStatistics(FormMain parent) { InitializeComponent(); this.ParentForm = parent; this.InitializeDesign(); this.DefaultSetting(); this.InitializeControl(); } #endregion #region Property public FormMain ParentForm { get { return this.m_ParentForm; } private set { this.m_ParentForm = value; } } #endregion #region Method private void InitializeDesign() { ImageDll images = new ImageDll(); if (this.ParentForm.SystemConfig.Language == DataStore.LanguageID.Korean) { this.labelTitleInformation.Text = "정보"; this.labelTitleStartTime.Text = "시작시간"; this.labelTitleEndTime.Text = "종료시간"; this.labelTitleRange.Text = "범위[g]"; this.labelTitleRangeOver.Text = "상한"; this.labelTitleRangePass.Text = "기준"; this.labelTitleRangeUnder.Text = "하한"; this.labelTitleRangeTare.Text = "용기"; this.labelTitleAllCnt.Text = "수량[ea/%]"; this.labelTitleAllCntOver.Text = "상한"; this.labelTitleAllCntPass.Text = "정상"; this.labelTitleAllCntUnder.Text = "하한"; this.labelTitleAllCntExng.Text = "기타불량"; this.labelTitleAllCntTotalNg.Text = "전체불량"; this.labelTitleAllCntTotal.Text = "전체수량"; this.labelTitleAllSumWeight.Text = "누적 중량[kg]"; this.labelTitleAllSumWeightOver.Text = "상한"; this.labelTitleAllSumWeightUnder.Text = "하한"; this.labelTitleAllPass.Text = "정상[g]"; this.labelTitleAllPassAverage.Text = "평균"; this.labelTitleAllPassSd.Text = "표준편차"; this.labelTitlePassCnt.Text = "정상/수량[ea]"; this.labelTitlePassAverage.Text = "평균[g]"; this.labelTitlePassPercentage.Text = "백분율[%]"; this.labelTitlePassSd.Text = "표준편차[g]"; this.labelTitlePassMinWeight.Text = "최소중량[g]"; this.labelTitlePassMaxWeight.Text = "최대중량[g]"; this.labelTitleOverCnt.Text = "상한/수량[ea]"; this.labelTitleOverSumWeight.Text = "누적중량[kg]"; this.labelTitleOverPercentage.Text = "백분율[%]"; this.labelTitleUnderCnt.Text = "하한/수량[ea]"; this.labelTitleUnderSumWeight.Text = "누적중량[kg]"; this.labelTitleUnderPercentage.Text = "백분율[%]"; this.labelTitleExngCnt.Text = "기타불량/수량[ea]"; this.labelTitleExngPercentage.Text = "백분율[%]"; this.labelTitleTotalCnt.Text = "전체수량[ea]"; this.labelTitleTotalNgCnt.Text = "전체불량[ea]"; this.labelTitleExngCnt.Font = new Font("New Gulim", 9F, FontStyle.Bold); } else if (this.ParentForm.SystemConfig.Language == DataStore.LanguageID.English) { this.labelTitle.Text = "Data Statistics"; this.buttonSave.DisableImage = new Bitmap(images.GetImage(ImageDll.ButtonImages.engBackupDisable)); this.buttonSave.DownImage = new Bitmap(images.GetImage(ImageDll.ButtonImages.engBackupDown)); this.buttonSave.UpImage = new Bitmap(images.GetImage(ImageDll.ButtonImages.engBackupUp)); this.buttonBack.DisableImage = new Bitmap(images.GetImage(ImageDll.ButtonImages.engBackDisable)); this.buttonBack.DownImage = new Bitmap(images.GetImage(ImageDll.ButtonImages.engBackDown)); this.buttonBack.UpImage = new Bitmap(images.GetImage(ImageDll.ButtonImages.engBackUp)); } else if (this.ParentForm.SystemConfig.Language == DataStore.LanguageID.Chinese) { this.labelTitle.Text = "Data Statistics"; this.buttonSave.DisableImage = new Bitmap(images.GetImage(ImageDll.ButtonImages.chnBackupDisable)); this.buttonSave.DownImage = new Bitmap(images.GetImage(ImageDll.ButtonImages.chnBackupDown)); this.buttonSave.UpImage = new Bitmap(images.GetImage(ImageDll.ButtonImages.chnBackupUp)); this.buttonFileSelect.DisableImage = new Bitmap(images.GetImage(ImageDll.ButtonImages.chnFileSelectDisable)); this.buttonFileSelect.DownImage = new Bitmap(images.GetImage(ImageDll.ButtonImages.chnFileSelectDown)); this.buttonFileSelect.UpImage = new Bitmap(images.GetImage(ImageDll.ButtonImages.chnFileSelectUp)); this.buttonBack.DisableImage = new Bitmap(images.GetImage(ImageDll.ButtonImages.chnBackDisable)); this.buttonBack.DownImage = new Bitmap(images.GetImage(ImageDll.ButtonImages.chnBackDown)); this.buttonBack.UpImage = new Bitmap(images.GetImage(ImageDll.ButtonImages.chnBackUp)); } else if (this.ParentForm.SystemConfig.Language == DataStore.LanguageID.Czech) { this.labelTitle.Text = "Data Statistics"; this.buttonSave.DisableImage = new Bitmap(images.GetImage(ImageDll.ButtonImages.czeBackupDisable)); this.buttonSave.DownImage = new Bitmap(images.GetImage(ImageDll.ButtonImages.czeBackupDown)); this.buttonSave.UpImage = new Bitmap(images.GetImage(ImageDll.ButtonImages.czeBackupUp)); this.buttonFileSelect.DisableImage = new Bitmap(images.GetImage(ImageDll.ButtonImages.czeFileSelectDisable)); this.buttonFileSelect.DownImage = new Bitmap(images.GetImage(ImageDll.ButtonImages.czeFileSelectDown)); this.buttonFileSelect.UpImage = new Bitmap(images.GetImage(ImageDll.ButtonImages.czeFileSelectUp)); this.buttonBack.DisableImage = new Bitmap(images.GetImage(ImageDll.ButtonImages.czeBackDisable)); this.buttonBack.DownImage = new Bitmap(images.GetImage(ImageDll.ButtonImages.czeBackDown)); this.buttonBack.UpImage = new Bitmap(images.GetImage(ImageDll.ButtonImages.czeBackUp)); } else if (this.ParentForm.SystemConfig.Language == DataStore.LanguageID.German) { this.labelTitle.Text = "Data Statistics"; this.buttonSave.DisableImage = new Bitmap(images.GetImage(ImageDll.ButtonImages.gerBackupDisable)); this.buttonSave.DownImage = new Bitmap(images.GetImage(ImageDll.ButtonImages.gerBackupDown)); this.buttonSave.UpImage = new Bitmap(images.GetImage(ImageDll.ButtonImages.gerBackupUp)); this.buttonFileSelect.DisableImage = new Bitmap(images.GetImage(ImageDll.ButtonImages.gerFileSelectDisable)); this.buttonFileSelect.DownImage = new Bitmap(images.GetImage(ImageDll.ButtonImages.gerFileSelectDown)); this.buttonFileSelect.UpImage = new Bitmap(images.GetImage(ImageDll.ButtonImages.gerFileSelectUp)); this.buttonBack.DisableImage = new Bitmap(images.GetImage(ImageDll.ButtonImages.gerBackDisable)); this.buttonBack.DownImage = new Bitmap(images.GetImage(ImageDll.ButtonImages.gerBackDown)); this.buttonBack.UpImage = new Bitmap(images.GetImage(ImageDll.ButtonImages.gerBackUp)); } else { } } private void InitializeControl() { int locationX = 0; #region Label Visible for (int i = this.ParentForm.SystemConfig.EquipmentColumns; i < 12; i++) { this.CollectionLane[i].Visible = false; this.CollectionPassCount[i].Visible = false; this.CollectionPassAverage[i].Visible = false; this.CollectionPassPercentage[i].Visible = false; this.CollectionPassSD[i].Visible = false; this.CollectionPassMinWeight[i].Visible = false; this.CollectionPassMaxWeight[i].Visible = false; this.CollectionOverCount[i].Visible = false; this.CollectionOverSumWeight[i].Visible = false; this.CollectionOverPercentage[i].Visible = false; this.CollectionUnderCount[i].Visible = false; this.CollectionUnderSumWeight[i].Visible = false; this.CollectionUnderPercentage[i].Visible = false; this.CollectionExNgCount[i].Visible = false; this.CollectionExNgPercentage[i].Visible = false; this.CollectionTotalCount[i].Visible = false; this.CollectionTotalNGCount[i].Visible = false; } #endregion #region Label Location if (this.ParentForm.SystemConfig.EquipmentColumns == 7) locationX = 50; else if (this.ParentForm.SystemConfig.EquipmentColumns == 8) locationX = 40; else if (this.ParentForm.SystemConfig.EquipmentColumns == 10) locationX = 16; for (int i = 1; i < this.ParentForm.SystemConfig.EquipmentColumns; i++) { this.CollectionLane[i].Location = new Point(this.CollectionLane[i].Location.X + locationX * i, this.CollectionLane[i].Location.Y); this.CollectionPassCount[i].Location = new Point(this.CollectionPassCount[i].Location.X + locationX * i, this.CollectionPassCount[i].Location.Y); this.CollectionPassAverage[i].Location = new Point(this.CollectionPassAverage[i].Location.X + locationX * i, this.CollectionPassAverage[i].Location.Y); this.CollectionPassPercentage[i].Location = new Point(this.CollectionPassPercentage[i].Location.X + locationX * i, this.CollectionPassPercentage[i].Location.Y); this.CollectionPassSD[i].Location = new Point(this.CollectionPassSD[i].Location.X + locationX * i, this.CollectionPassSD[i].Location.Y); this.CollectionPassMinWeight[i].Location = new Point(this.CollectionPassMinWeight[i].Location.X + locationX * i, this.CollectionPassMinWeight[i].Location.Y); this.CollectionPassMaxWeight[i].Location = new Point(this.CollectionPassMaxWeight[i].Location.X + locationX * i, this.CollectionPassMaxWeight[i].Location.Y); this.CollectionOverCount[i].Location = new Point(this.CollectionOverCount[i].Location.X + locationX * i, this.CollectionOverCount[i].Location.Y); this.CollectionOverSumWeight[i].Location = new Point(this.CollectionOverSumWeight[i].Location.X + locationX * i, this.CollectionOverSumWeight[i].Location.Y); this.CollectionOverPercentage[i].Location = new Point(this.CollectionOverPercentage[i].Location.X + locationX * i, this.CollectionOverPercentage[i].Location.Y); this.CollectionUnderCount[i].Location = new Point(this.CollectionUnderCount[i].Location.X + locationX * i, this.CollectionUnderCount[i].Location.Y); this.CollectionUnderSumWeight[i].Location = new Point(this.CollectionUnderSumWeight[i].Location.X + locationX * i, this.CollectionUnderSumWeight[i].Location.Y); this.CollectionUnderPercentage[i].Location = new Point(this.CollectionUnderPercentage[i].Location.X + locationX * i, this.CollectionUnderPercentage[i].Location.Y); this.CollectionExNgCount[i].Location = new Point(this.CollectionExNgCount[i].Location.X + locationX * i, this.CollectionExNgCount[i].Location.Y); this.CollectionExNgPercentage[i].Location = new Point(this.CollectionExNgPercentage[i].Location.X + locationX * i, this.CollectionExNgPercentage[i].Location.Y); this.CollectionTotalCount[i].Location = new Point(this.CollectionTotalCount[i].Location.X + locationX * i, this.CollectionTotalCount[i].Location.Y); this.CollectionTotalNGCount[i].Location = new Point(this.CollectionTotalNGCount[i].Location.X + locationX * i, this.CollectionTotalNGCount[i].Location.Y); } #endregion } private void DefaultSetting() { this.FileIndex = 0; this.SelectFilePath = ""; this.CurrentDataCommonList = new DataCommonList(); this.CollectionWeightData = new Collection(); this.CollectionLaneData = new Collection(); this.CollectionCommonLabel = new Collection(); this.CollectionLane = new Collection(); this.CollectionPassCount = new Collection(); this.CollectionPassAverage = new Collection(); this.CollectionPassPercentage = new Collection(); this.CollectionPassSD = new Collection(); this.CollectionPassMinWeight = new Collection(); this.CollectionPassMaxWeight = new Collection(); this.CollectionOverCount = new Collection(); this.CollectionOverSumWeight = new Collection(); this.CollectionOverPercentage = new Collection(); this.CollectionUnderCount = new Collection(); this.CollectionUnderSumWeight = new Collection(); this.CollectionUnderPercentage = new Collection(); this.CollectionExNgCount = new Collection(); this.CollectionExNgPercentage = new Collection(); this.CollectionTotalCount = new Collection(); this.CollectionTotalNGCount = new Collection(); this.CollectionCommonLabel.Add(this.labelProductName); this.CollectionCommonLabel.Add(this.labelLot); this.CollectionCommonLabel.Add(this.labelStartTime); this.CollectionCommonLabel.Add(this.labelEndTime); this.CollectionCommonLabel.Add(this.labelOverRange); this.CollectionCommonLabel.Add(this.labelPassRange); this.CollectionCommonLabel.Add(this.labelUnderRange); this.CollectionCommonLabel.Add(this.labelTareRange); this.CollectionCommonLabel.Add(this.labelTotalCount); this.CollectionCommonLabel.Add(this.labelTotalNGCount); this.CollectionCommonLabel.Add(this.labelTotalPassCount); this.CollectionCommonLabel.Add(this.labelTotalOverCount); this.CollectionCommonLabel.Add(this.labelTotalUnderCount); this.CollectionCommonLabel.Add(this.labelTotalExNgCount); this.CollectionCommonLabel.Add(this.labelTotalPassAverage); this.CollectionCommonLabel.Add(this.labelTotalPassStandardDeviation); this.CollectionCommonLabel.Add(this.labelTotalOverSumWeight); this.CollectionCommonLabel.Add(this.labelTotalUnderSumWeight); for (int i = 1; i <= 12; i++) { this.CollectionLane.Add(FindByNameUtil.SmartLabel("labelLane" + i, this)); this.CollectionPassCount.Add(FindByNameUtil.SmartLabel("labelPassCount" + i, this)); this.CollectionPassAverage.Add(FindByNameUtil.SmartLabel("labelPassAverage" + i, this)); this.CollectionPassPercentage.Add(FindByNameUtil.SmartLabel("labelPassPercentage" + i, this)); this.CollectionPassSD.Add(FindByNameUtil.SmartLabel("labelPassStandardDeviation" + i, this)); this.CollectionPassMinWeight.Add(FindByNameUtil.SmartLabel("labelPassMinWeight" + i, this)); this.CollectionPassMaxWeight.Add(FindByNameUtil.SmartLabel("labelPassMaxWeight" + i, this)); this.CollectionOverCount.Add(FindByNameUtil.SmartLabel("labelOverCount" + i, this)); this.CollectionOverSumWeight.Add(FindByNameUtil.SmartLabel("labelOverSumWeight" + i, this)); this.CollectionOverPercentage.Add(FindByNameUtil.SmartLabel("labelOverPercentage" + i, this)); this.CollectionUnderCount.Add(FindByNameUtil.SmartLabel("labelUnderCount" + i, this)); this.CollectionUnderSumWeight.Add(FindByNameUtil.SmartLabel("labelUnderSumWeight" + i, this)); this.CollectionUnderPercentage.Add(FindByNameUtil.SmartLabel("labelUnderPercentage" + i, this)); this.CollectionExNgCount.Add(FindByNameUtil.SmartLabel("labelExNgCount" + i, this)); this.CollectionExNgPercentage.Add(FindByNameUtil.SmartLabel("labelExNgPercentage" + i, this)); this.CollectionTotalCount.Add(FindByNameUtil.SmartLabel("labelTotalCount" + i, this)); this.CollectionTotalNGCount.Add(FindByNameUtil.SmartLabel("labelTotalNGCount" + i, this)); } for (int i = 0; i < this.ParentForm.SystemConfig.EquipmentColumns; i++) this.CollectionLaneData.Add(new DataCollector()); this.InitializeLabels(); } private void InitializeLabels() { foreach (SmartLabel label in this.CollectionCommonLabel) label.Text = "-"; for (int i = 0; i < 12; i++) { this.CollectionPassCount[i].Text = "0"; this.CollectionPassAverage[i].Text = "0"; this.CollectionPassPercentage[i].Text = "0"; this.CollectionPassSD[i].Text = "0"; this.CollectionPassMinWeight[i].Text = "0"; this.CollectionPassMaxWeight[i].Text = "0"; this.CollectionOverCount[i].Text = "0"; this.CollectionOverSumWeight[i].Text = "0"; this.CollectionOverPercentage[i].Text = "0"; this.CollectionUnderCount[i].Text = "0"; this.CollectionUnderSumWeight[i].Text = "0"; this.CollectionUnderPercentage[i].Text = "0"; this.CollectionExNgCount[i].Text = "0"; this.CollectionExNgPercentage[i].Text = "0"; this.CollectionTotalCount[i].Text = "0"; this.CollectionTotalNGCount[i].Text = "0"; } } private void SetCommonData(Collection datas, Collection laneDatas) { double dValue1 = 0.0, dValue2 = 0.0, passSumWeight = 0.0, overSumWeight = 0.0, underSumWeight = 0.0, passAverageWeight = 0.0, passVariance = 0.0; string sValue = ""; int underCount = 0, passCount = 0, overCount = 0, exNGCount = 0; this.CurrentDataCommonList.ProductName = datas[datas.Count - 1][3]; this.CurrentDataCommonList.Lot = datas[datas.Count - 1][4]; this.CurrentDataCommonList.StartTime = string.Format("{0} {1}", datas[0][0], datas[0][1]); this.CurrentDataCommonList.EndTime = string.Format("{0} {1}", datas[datas.Count - 1][0], datas[datas.Count - 1][1]); dValue1 = double.Parse(datas[datas.Count - 1][5]); sValue = Helper.DoubleToString(dValue1, 1); this.CurrentDataCommonList.UnderRange = sValue; dValue1 = double.Parse(datas[datas.Count - 1][6]); sValue = Helper.DoubleToString(dValue1, 1); this.CurrentDataCommonList.PassRange = sValue; dValue1 = double.Parse(datas[datas.Count - 1][7]); sValue = Helper.DoubleToString(dValue1, 1); this.CurrentDataCommonList.OverRange = sValue; dValue1 = double.Parse(datas[datas.Count - 1][8]); sValue = Helper.DoubleToString(dValue1, 1); this.CurrentDataCommonList.TareRange = sValue; for (int i = 0; i < laneDatas.Count; i++) { underCount += laneDatas[i].UnderTotalCount; passCount += laneDatas[i].PassTotalCount; overCount += laneDatas[i].OverTotalCount; exNGCount += laneDatas[i].ExNgTotalCount; passSumWeight += laneDatas[i].PassSumWeight; overSumWeight += laneDatas[i].OverSumWeight; underSumWeight += laneDatas[i].UnderSumWeight; } // 전체 정량 평균 passAverageWeight = passSumWeight / passCount; // 전체 정량 분산 for (int i = 0; i < laneDatas.Count; i++) { for (int j = 0; j < laneDatas[i].PassWeightData.Count; j++) { dValue1 = passAverageWeight - laneDatas[i].PassWeightData[j]; dValue2 += dValue1 * dValue1; } } passVariance = dValue2 / passCount; this.CurrentDataCommonList.TotalUnderCount = underCount; this.CurrentDataCommonList.TotalPassCount = passCount; this.CurrentDataCommonList.TotalOverCount = overCount; this.CurrentDataCommonList.TotalExNgCount = exNGCount; this.CurrentDataCommonList.TotalPassSumWeight = passSumWeight; this.CurrentDataCommonList.TotalOverSumWeight = overSumWeight; this.CurrentDataCommonList.TotalUnderSumWeight = underSumWeight; this.CurrentDataCommonList.TotalPassAverageWeight = passAverageWeight; this.CurrentDataCommonList.TotalPassVariance = passVariance; } private void SetData(DataCollector data, string weight, DataStore.JudgmentStatus grade) { if (grade == DataStore.JudgmentStatus.Pass) data.AddPassWeight(double.Parse(weight)); else if (grade == DataStore.JudgmentStatus.Over) data.AddOverWeight(double.Parse(weight)); else if (grade == DataStore.JudgmentStatus.Under) data.AddUnderWeight(double.Parse(weight)); else data.AddExNgWeight(double.Parse(weight)); } private void UpdateDisplay(DataCommonList commonList, Collection datas) { this.SetLabelText(this.labelProductName, commonList.ProductName); this.SetLabelText(this.labelLot, commonList.Lot); this.SetLabelText(this.labelStartTime, commonList.StartTime); this.SetLabelText(this.labelEndTime, commonList.EndTime); this.SetLabelText(this.labelUnderRange, commonList.UnderRange); this.SetLabelText(this.labelPassRange, commonList.PassRange); this.SetLabelText(this.labelOverRange, commonList.OverRange); this.SetLabelText(this.labelTareRange, commonList.TareRange); this.SetLabelText(this.labelTotalCount, string.Format("{0}", commonList.TotalCount.ToString())); this.SetLabelText(this.labelTotalUnderCount, string.Format("{0} / {1}", commonList.TotalUnderCount, commonList.TotalUnderPercentage)); this.SetLabelText(this.labelTotalPassCount, string.Format("{0} / {1}", commonList.TotalPassCount, commonList.TotalPassPercentage)); this.SetLabelText(this.labelTotalOverCount, string.Format("{0} / {1}", commonList.TotalOverCount, commonList.TotalOverPercentage)); this.SetLabelText(this.labelTotalExNgCount, string.Format("{0} / {1}", commonList.TotalExNgCount, commonList.TotalExNgPercentage)); this.SetLabelText(this.labelTotalNGCount, string.Format("{0}", commonList.TotalNGCount.ToString())); this.SetLabelText(this.labelTotalPassAverage, string.Format("{0:0.000}", commonList.TotalPassAverageWeight)); this.SetLabelText(this.labelTotalPassStandardDeviation, string.Format("{0:0.00}", commonList.TotalPassStandardDeviation)); this.SetLabelText(this.labelTotalOverSumWeight, string.Format("{0}", Helper.DoubleToString(commonList.TotalOverSumWeight / 1000, 3))); this.SetLabelText(this.labelTotalUnderSumWeight, string.Format("{0}", Helper.DoubleToString(commonList.TotalUnderSumWeight / 1000, 3))); for (int i = 0; i < datas.Count; i++) { this.SetLabelText(this.CollectionPassCount[i], datas[i].PassTotalCount.ToString()); this.SetLabelText(this.CollectionPassAverage[i], string.Format("{0:0.000}", datas[i].PassAverage)); this.SetLabelText(this.CollectionPassPercentage[i], datas[i].PassPercentage.ToString()); this.SetLabelText(this.CollectionPassSD[i], string.Format("{0:0.00}", datas[i].PassStandardDeviation)); this.SetLabelText(this.CollectionPassMinWeight[i], Helper.DoubleToString(datas[i].PassMinWeight, 1)); this.SetLabelText(this.CollectionPassMaxWeight[i], Helper.DoubleToString(datas[i].PassMaxWeight, 1)); this.SetLabelText(this.CollectionOverCount[i], datas[i].OverTotalCount.ToString()); this.SetLabelText(this.CollectionOverSumWeight[i], Helper.DoubleToString(datas[i].OverSumWeight / 1000, 3)); this.SetLabelText(this.CollectionOverPercentage[i], datas[i].OverPercentage.ToString()); this.SetLabelText(this.CollectionUnderCount[i], datas[i].UnderTotalCount.ToString()); this.SetLabelText(this.CollectionUnderSumWeight[i], Helper.DoubleToString(datas[i].UnderSumWeight / 1000, 3)); this.SetLabelText(this.CollectionUnderPercentage[i], datas[i].UnderPercentage.ToString()); this.SetLabelText(this.CollectionExNgCount[i], datas[i].ExNgTotalCount.ToString()); this.SetLabelText(this.CollectionExNgPercentage[i], datas[i].ExNgPercentage.ToString()); this.SetLabelText(this.CollectionTotalCount[i], datas[i].TotalCount.ToString()); this.SetLabelText(this.CollectionTotalNGCount[i], datas[i].TotalNGCount.ToString()); } } private void SetLabelText(SmartLabel label, string value) { if (label.Text != value) label.Text = value; } private void LoadDataBackupFile(ref Collection> datas, string path, int index) { int flag = 0; long count = 0; this.ParentForm.smartFileIO.FilePathName = path; this.ParentForm.smartFileIO.Open(2000000); this.ParentForm.smartFileIO.ReadStringAllBuffer(); count = this.ParentForm.smartFileIO.GetCount(); for (int i = 0; i < count; i++) { if (flag == 100) { Thread.Sleep(5); flag = 0; } datas[index].Add(this.ParentForm.smartFileIO.ReadStringBuffer(i).Split(',')); flag++; } this.ParentForm.smartFileIO.Close(); datas[index].RemoveAt(0); } private void DataAnalysis() { #region Set Data if (this.ParentForm.SystemConfig.EquipmentColumns == 7) { for (int i = 0; i < this.CollectionWeightData.Count; i++) { this.SetData(this.CollectionLaneData[0], this.CollectionWeightData[i][9], Helper.StringToJudgmentStatusStatistics(this.CollectionWeightData[i][10])); this.SetData(this.CollectionLaneData[1], this.CollectionWeightData[i][11], Helper.StringToJudgmentStatusStatistics(this.CollectionWeightData[i][12])); this.SetData(this.CollectionLaneData[2], this.CollectionWeightData[i][13], Helper.StringToJudgmentStatusStatistics(this.CollectionWeightData[i][14])); this.SetData(this.CollectionLaneData[3], this.CollectionWeightData[i][15], Helper.StringToJudgmentStatusStatistics(this.CollectionWeightData[i][16])); this.SetData(this.CollectionLaneData[4], this.CollectionWeightData[i][17], Helper.StringToJudgmentStatusStatistics(this.CollectionWeightData[i][18])); this.SetData(this.CollectionLaneData[5], this.CollectionWeightData[i][19], Helper.StringToJudgmentStatusStatistics(this.CollectionWeightData[i][20])); this.SetData(this.CollectionLaneData[6], this.CollectionWeightData[i][21], Helper.StringToJudgmentStatusStatistics(this.CollectionWeightData[i][22])); } } else if (this.ParentForm.SystemConfig.EquipmentColumns == 8) { for (int i = 0; i < this.CollectionWeightData.Count; i++) { this.SetData(this.CollectionLaneData[0], this.CollectionWeightData[i][9], Helper.StringToJudgmentStatusStatistics(this.CollectionWeightData[i][10])); this.SetData(this.CollectionLaneData[1], this.CollectionWeightData[i][11], Helper.StringToJudgmentStatusStatistics(this.CollectionWeightData[i][12])); this.SetData(this.CollectionLaneData[2], this.CollectionWeightData[i][13], Helper.StringToJudgmentStatusStatistics(this.CollectionWeightData[i][14])); this.SetData(this.CollectionLaneData[3], this.CollectionWeightData[i][15], Helper.StringToJudgmentStatusStatistics(this.CollectionWeightData[i][16])); this.SetData(this.CollectionLaneData[4], this.CollectionWeightData[i][17], Helper.StringToJudgmentStatusStatistics(this.CollectionWeightData[i][18])); this.SetData(this.CollectionLaneData[5], this.CollectionWeightData[i][19], Helper.StringToJudgmentStatusStatistics(this.CollectionWeightData[i][20])); this.SetData(this.CollectionLaneData[6], this.CollectionWeightData[i][21], Helper.StringToJudgmentStatusStatistics(this.CollectionWeightData[i][22])); this.SetData(this.CollectionLaneData[7], this.CollectionWeightData[i][23], Helper.StringToJudgmentStatusStatistics(this.CollectionWeightData[i][24])); } } else if (this.ParentForm.SystemConfig.EquipmentColumns == 10) { for (int i = 0; i < this.CollectionWeightData.Count; i++) { this.SetData(this.CollectionLaneData[0], this.CollectionWeightData[i][9], Helper.StringToJudgmentStatusStatistics(this.CollectionWeightData[i][10])); this.SetData(this.CollectionLaneData[1], this.CollectionWeightData[i][11], Helper.StringToJudgmentStatusStatistics(this.CollectionWeightData[i][12])); this.SetData(this.CollectionLaneData[2], this.CollectionWeightData[i][13], Helper.StringToJudgmentStatusStatistics(this.CollectionWeightData[i][14])); this.SetData(this.CollectionLaneData[3], this.CollectionWeightData[i][15], Helper.StringToJudgmentStatusStatistics(this.CollectionWeightData[i][16])); this.SetData(this.CollectionLaneData[4], this.CollectionWeightData[i][17], Helper.StringToJudgmentStatusStatistics(this.CollectionWeightData[i][18])); this.SetData(this.CollectionLaneData[5], this.CollectionWeightData[i][19], Helper.StringToJudgmentStatusStatistics(this.CollectionWeightData[i][20])); this.SetData(this.CollectionLaneData[6], this.CollectionWeightData[i][21], Helper.StringToJudgmentStatusStatistics(this.CollectionWeightData[i][22])); this.SetData(this.CollectionLaneData[7], this.CollectionWeightData[i][23], Helper.StringToJudgmentStatusStatistics(this.CollectionWeightData[i][24])); this.SetData(this.CollectionLaneData[8], this.CollectionWeightData[i][25], Helper.StringToJudgmentStatusStatistics(this.CollectionWeightData[i][26])); this.SetData(this.CollectionLaneData[9], this.CollectionWeightData[i][27], Helper.StringToJudgmentStatusStatistics(this.CollectionWeightData[i][28])); } } else { for (int i = 0; i < this.CollectionWeightData.Count; i++) { this.SetData(this.CollectionLaneData[0], this.CollectionWeightData[i][9], Helper.StringToJudgmentStatusStatistics(this.CollectionWeightData[i][10])); this.SetData(this.CollectionLaneData[1], this.CollectionWeightData[i][11], Helper.StringToJudgmentStatusStatistics(this.CollectionWeightData[i][12])); this.SetData(this.CollectionLaneData[2], this.CollectionWeightData[i][13], Helper.StringToJudgmentStatusStatistics(this.CollectionWeightData[i][14])); this.SetData(this.CollectionLaneData[3], this.CollectionWeightData[i][15], Helper.StringToJudgmentStatusStatistics(this.CollectionWeightData[i][16])); this.SetData(this.CollectionLaneData[4], this.CollectionWeightData[i][17], Helper.StringToJudgmentStatusStatistics(this.CollectionWeightData[i][18])); this.SetData(this.CollectionLaneData[5], this.CollectionWeightData[i][19], Helper.StringToJudgmentStatusStatistics(this.CollectionWeightData[i][20])); this.SetData(this.CollectionLaneData[6], this.CollectionWeightData[i][21], Helper.StringToJudgmentStatusStatistics(this.CollectionWeightData[i][22])); this.SetData(this.CollectionLaneData[7], this.CollectionWeightData[i][23], Helper.StringToJudgmentStatusStatistics(this.CollectionWeightData[i][24])); this.SetData(this.CollectionLaneData[8], this.CollectionWeightData[i][25], Helper.StringToJudgmentStatusStatistics(this.CollectionWeightData[i][26])); this.SetData(this.CollectionLaneData[9], this.CollectionWeightData[i][27], Helper.StringToJudgmentStatusStatistics(this.CollectionWeightData[i][28])); this.SetData(this.CollectionLaneData[10], this.CollectionWeightData[i][29], Helper.StringToJudgmentStatusStatistics(this.CollectionWeightData[i][30])); this.SetData(this.CollectionLaneData[11], this.CollectionWeightData[i][31], Helper.StringToJudgmentStatusStatistics(this.CollectionWeightData[i][32])); } } #endregion for (int i = 0; i < this.CollectionLaneData.Count; i++) this.CollectionLaneData[i].StatisticalAnalysis(); this.SetCommonData(this.CollectionWeightData, this.CollectionLaneData); this.UpdateDisplay(this.CurrentDataCommonList, this.CollectionLaneData); } public int DataRead() { int ret = 0, flag = 0; long count = 0; if (this.SelectFilePath == "") return ret = -1; SmartSplash splash = new SmartSplash(); splash.CenterPosition = true; splash.AnimationInterval = 100; splash.LoadingImagePathname = "SmartLoading4"; splash.Start(); this.CollectionWeightData.Clear(); this.ParentForm.smartFileIO.FilePathName = this.SelectFilePath; this.ParentForm.smartFileIO.Open(2000000); this.ParentForm.smartFileIO.ReadStringAllBuffer(); try { count = this.ParentForm.smartFileIO.GetCount(); for (int i = 0; i < count; i++) { if (flag == 100) { Thread.Sleep(5); flag = 0; } this.CollectionWeightData.Add(this.ParentForm.smartFileIO.ReadStringBuffer(i).Split(',')); flag++; } this.ParentForm.smartFileIO.Close(); this.CollectionWeightData.RemoveAt(0); this.DataAnalysis(); ret = 0; splash.Finish(); } catch { ret = -1; splash.Finish(); DialogFormMessage msg = new DialogFormMessage(13, this.ParentForm.SystemConfig.Language); msg.ShowDialog(); this.ParentForm.smartFileIO.Close(); } return ret; } public void ClearData() { this.InitializeLabels(); for (int i = 0; i < this.CollectionLaneData.Count; i++) this.CollectionLaneData[i].ClearDatas(); } private void FileBackup1(string path, DateTime time, DataCommonList commonList, Collection datas) { bool fileCheck = false; string fullFilePath = ""; StreamWriter sw; fullFilePath = string.Format("{0}S{1:yyyyMMdd-HHmmss}.csv", path, time); this.ParentForm.smartFileIO.FilePathName = fullFilePath; sw = new StreamWriter(fullFilePath, true, Encoding.UTF8); FileInfo fileInfo = new FileInfo(fullFilePath); fileCheck = fileInfo.Exists; if (fileCheck == true) { this.ParentForm.smartFileIO.Open(this.ParentForm.BufferSmartUart); for (int i = 0; i < 40; i++) { this.ParentForm.smartFileIO.WriteString(""); } this.ParentForm.smartFileIO.Close(); } sw.WriteLine(string.Format("Product Name,{0}", commonList.ProductName)); sw.WriteLine(string.Format("Lot,{0}", commonList.Lot)); sw.WriteLine(string.Format("Start Time,{0}", commonList.StartTime)); sw.WriteLine(string.Format("End Time,{0}", commonList.EndTime)); sw.WriteLine(string.Format("Under Range[g],{0}", commonList.UnderRange)); sw.WriteLine(string.Format("Pass Range[g],{0}", commonList.PassRange)); sw.WriteLine(string.Format("Over Range[g],{0}", commonList.OverRange)); sw.WriteLine(string.Format("Tare Range[g],{0}", commonList.TareRange)); sw.WriteLine(string.Format("Total Count[ea],{0}", commonList.TotalCount)); sw.WriteLine(string.Format("Total NG Count[ea],{0}", commonList.TotalNGCount)); sw.WriteLine(string.Format("Total Pass Count[ea],{0}", commonList.TotalPassCount)); sw.WriteLine(string.Format("Total Pass Percentage[%],{0}", commonList.TotalPassPercentage)); sw.WriteLine(string.Format("Total Pass Average[g],{0:0.000}", commonList.TotalPassAverageWeight)); sw.WriteLine(string.Format("Total Pass Standard Deviation[g],{0}", commonList.TotalPassStandardDeviation)); sw.WriteLine(string.Format("Total Under Count[ea],{0}", commonList.TotalUnderCount)); sw.WriteLine(string.Format("Total Under Percentage[%],{0}", commonList.TotalUnderPercentage)); sw.WriteLine(string.Format("Total Under Sum Weight[kg],{0:0.000}", commonList.TotalUnderSumWeight / 1000)); sw.WriteLine(string.Format("Total Over Count[ea],{0}", commonList.TotalOverCount)); sw.WriteLine(string.Format("Total Over Percentage[%],{0}", commonList.TotalOverPercentage)); sw.WriteLine(string.Format("Total Over Sum Weight[kg],{0:0.000}", commonList.TotalOverSumWeight / 1000)); sw.WriteLine(string.Format("Total ExNG count[ea],{0}", commonList.TotalExNgCount)); sw.WriteLine(string.Format("Total ExNG Percentage[%],{0}", commonList.TotalExNgPercentage)); sw.Write(""); sw.Write(","); for (int i = 0; i < this.ParentForm.SystemConfig.EquipmentColumns; i++) { sw.Write(string.Format("#{0}", i + 1)); sw.Write(","); } sw.WriteLine(); #region Pass sw.Write("Pass Count[ea]"); for (int i = 0; i < datas.Count; i++) { sw.Write(","); sw.Write(datas[i].PassTotalCount); } sw.WriteLine(); sw.Write("Pass Average[g]"); for (int i = 0; i < datas.Count; i++) { sw.Write(","); sw.Write(string.Format("{0:0.000}", datas[i].PassAverage)); } sw.WriteLine(); sw.Write("Pass Percentage[%]"); for (int i = 0; i < datas.Count; i++) { sw.Write(","); sw.Write(datas[i].PassPercentage); } sw.WriteLine(); sw.Write("Pass Standard Deviation[g]"); for (int i = 0; i < datas.Count; i++) { sw.Write(","); sw.Write(string.Format("{0:0.00}", datas[i].PassStandardDeviation)); } sw.WriteLine(); sw.Write("Pass Min Weight[g]"); for (int i = 0; i < datas.Count; i++) { sw.Write(","); sw.Write(Helper.DoubleToString(datas[i].PassMinWeight, 1)); } sw.WriteLine(); sw.Write("Pass Max Weight[g]"); for (int i = 0; i < datas.Count; i++) { sw.Write(","); sw.Write(Helper.DoubleToString(datas[i].PassMaxWeight, 1)); } sw.WriteLine(); #endregion #region Over sw.Write("Over Count[ea]"); for (int i = 0; i < datas.Count; i++) { sw.Write(","); sw.Write(datas[i].OverTotalCount); } sw.WriteLine(); sw.Write("Over Sum Weight[kg]"); for (int i = 0; i < datas.Count; i++) { sw.Write(","); sw.Write(Helper.DoubleToString(datas[i].OverSumWeight / 1000, 3)); } sw.WriteLine(); sw.Write("Over Percentage[%]"); for (int i = 0; i < datas.Count; i++) { sw.Write(","); sw.Write(datas[i].OverPercentage); } sw.WriteLine(); #endregion #region Under sw.Write("Under Count[ea]"); for (int i = 0; i < datas.Count; i++) { sw.Write(","); sw.Write(datas[i].UnderTotalCount); } sw.WriteLine(); sw.Write("Under Sum Weight[kg]"); for (int i = 0; i < datas.Count; i++) { sw.Write(","); sw.Write(Helper.DoubleToString(datas[i].UnderSumWeight / 1000, 3)); } sw.WriteLine(); sw.Write("Under Percentage[%]"); for (int i = 0; i < datas.Count; i++) { sw.Write(","); sw.Write(datas[i].UnderPercentage); } sw.WriteLine(); #endregion #region Ex sw.Write("ExNG Count[ea]"); for (int i = 0; i < datas.Count; i++) { sw.Write(","); sw.Write(datas[i].ExNgTotalCount); } sw.WriteLine(); sw.Write("ExNG Percentage[%]"); for (int i = 0; i < datas.Count; i++) { sw.Write(","); sw.Write(datas[i].ExNgPercentage); } sw.WriteLine(); #endregion #region Total sw.Write("Total Count[ea]"); for (int i = 0; i < datas.Count; i++) { sw.Write(","); sw.Write(datas[i].TotalCount); } sw.WriteLine(); sw.Write("Total NG Count[ea]"); for (int i = 0; i < datas.Count; i++) { sw.Write(","); sw.Write(datas[i].TotalNGCount); } sw.WriteLine(); #endregion sw.Close(); } private void FileBackup2(string path, DateTime time, DataCommonList commonList, Collection datas) { bool fileCheck = false; string fullFilePath = ""; StreamWriter sw; fullFilePath = string.Format("{0}S{1:yyyyMMdd-HHmmss}.csv", path, time); this.ParentForm.smartFileIO.FilePathName = fullFilePath; sw = new StreamWriter(fullFilePath, true, Encoding.UTF8); FileInfo fileInfo = new FileInfo(fullFilePath); fileCheck = fileInfo.Exists; // 같은 파일이 있으면 초기화 if (fileCheck == true) { this.ParentForm.smartFileIO.Open(this.ParentForm.BufferSmartUart); for (int i = 0; i < 40; i++) { this.ParentForm.smartFileIO.WriteString(""); } this.ParentForm.smartFileIO.Close(); } for (int i = 0; i < this.ParentForm.SystemConfig.EquipmentColumns; i++) { #region 데이터 출력 // Lane Number sw.Write("{0}", i + 1); sw.Write(","); // ProductName sw.Write(commonList.ProductName); sw.Write(","); // Lot sw.Write(commonList.Lot); sw.Write(","); // StartTime sw.Write(commonList.StartTime); sw.Write(","); // EndTime sw.Write(commonList.EndTime); sw.Write(","); // UnderRange sw.Write(commonList.UnderRange); sw.Write(","); // PassRange sw.Write(commonList.PassRange); sw.Write(","); // OverRange sw.Write(commonList.OverRange); sw.Write(","); // TareRange sw.Write(commonList.TareRange); sw.Write(","); // TotalCount sw.Write(commonList.TotalCount); sw.Write(","); // TotalNGCount sw.Write(commonList.TotalNGCount); sw.Write(","); // TotalPassCount sw.Write(commonList.TotalPassCount); sw.Write(","); // TotalPassPercentage sw.Write(commonList.TotalPassPercentage); sw.Write(","); // TotalPassAverage sw.Write(string.Format("{0:0.000}", commonList.TotalPassAverageWeight)); sw.Write(","); // TotalPassSD sw.Write(string.Format("{0:0.00}", commonList.TotalPassStandardDeviation)); sw.Write(","); // TotalUnderCount sw.Write(commonList.TotalUnderCount); sw.Write(","); // TotalUnderPercentage sw.Write(commonList.TotalUnderPercentage); sw.Write(","); // TotalUnderSumWeight sw.Write(string.Format("{0:0.0000}", commonList.TotalUnderSumWeight / 1000)); sw.Write(","); // TotalOverCount sw.Write(commonList.TotalOverCount); sw.Write(","); // TotalOverPercentage sw.Write(commonList.TotalOverPercentage); sw.Write(","); // TotalOverSumWeight sw.Write(string.Format("{0:0.0000}", commonList.TotalOverSumWeight / 1000)); sw.Write(","); // TotalExNgCount sw.Write(commonList.TotalExNgCount); sw.Write(","); // TotalExNgPercentage sw.Write(commonList.TotalExNgPercentage); sw.Write(","); // Lane PassCount sw.Write(datas[i].PassTotalCount); sw.Write(","); // Lane PassAverage sw.Write(string.Format("{0:0.000}", datas[i].PassAverage)); sw.Write(","); // Lane PassPercentage sw.Write(datas[i].PassPercentage); sw.Write(","); // Lane PassSD sw.Write(string.Format("{0:0.00}", datas[i].PassStandardDeviation)); sw.Write(","); // Lane PassMinWeight sw.Write(Helper.DoubleToString(datas[i].PassMinWeight, 1)); sw.Write(","); // Lane PassMaxWeight sw.Write(Helper.DoubleToString(datas[i].PassMaxWeight, 1)); sw.Write(","); // Lane OverCount sw.Write(datas[i].OverTotalCount); sw.Write(","); // Lane OverSumWeight sw.Write(Helper.DoubleToString(datas[i].OverSumWeight / 1000, 3)); sw.Write(","); // Lane OverPercentage sw.Write(datas[i].OverPercentage); sw.Write(","); // Lane UnderCount sw.Write(datas[i].UnderTotalCount); sw.Write(","); // Lane UnderSumWeight sw.Write(Helper.DoubleToString(datas[i].UnderSumWeight / 1000, 3)); sw.Write(","); // Lane UnderPercentage sw.Write(datas[i].UnderPercentage); sw.Write(","); // Lane ExNgCount sw.Write(datas[i].ExNgTotalCount); sw.Write(","); // Lane ExNgPercentage sw.Write(datas[i].ExNgPercentage); sw.Write(","); // Lane TotalCount sw.Write(datas[i].TotalCount); sw.Write(","); // Lane TotalNgCount sw.Write(datas[i].TotalNGCount); sw.WriteLine(); #endregion } sw.Close(); } private bool CheckUSBMemory() { bool ret = false; try { DirectoryInfo dinfo = new DirectoryInfo("하드 디스크\\"); dinfo.GetDirectories(); ret = true; } catch { ret = false; } return ret; } private void FileCopy(FileInfo file, string fileName) { try { if (this.FileIndex == 0) { file.CopyTo(fileName); this.FileIndex = 0; } else { file.CopyTo(fileName.Insert(fileName.Length - 4, "_" + this.FileIndex.ToString())); this.FileIndex = 0; } } catch { this.FileIndex++; this.FileCopy(file, fileName); } } private void CreateScreenCapture(string path, DateTime time) { string filePath = ""; Bitmap bitMap = new Bitmap(1024, 768); bitMap = IntechGraphics.CopyFromScreen(); filePath = string.Format("{0}S{1:yyyyMMdd-HHmmss}.jpg", path, time); bitMap.Save(filePath, ImageFormat.Jpeg); } private int Backup1() { int ret = 0; string filePath = ""; bool directoryCheck = false; DateTime time = DateTime.Now; // 메모리 장착 체크 if (this.CheckUSBMemory() == false) { DialogFormMessage msg = new DialogFormMessage(5, this.ParentForm.SystemConfig.Language); msg.ShowDialog(); this.buttonSave.Enabled = true; ret = -1; return ret; } #region 통계 데이터 생성 // ScreenCapture this.CreateScreenCapture(this.ParentForm.PathDataStatisticsFolder, time); // csv File this.FileBackup1(this.ParentForm.PathDataStatisticsFolder, time, this.CurrentDataCommonList, this.CollectionLaneData); #endregion #region 메모리로 파일 복사 try { filePath = "하드 디스크\\"; DirectoryInfo dir = new DirectoryInfo(this.ParentForm.PathDataStatisticsFolder); directoryCheck = dir.Exists; // 폴더 체크 if (directoryCheck == false) dir.Create(); FileInfo[] files = dir.GetFiles(); foreach (FileInfo file in files) { this.FileCopy(file, filePath + file.Name); file.Delete(); } DialogFormMessage msg = new DialogFormMessage("2", this.ParentForm.SystemConfig.Language); msg.ShowDialog(); } catch { DialogFormMessage msg = new DialogFormMessage(6, this.ParentForm.SystemConfig.Language); msg.ShowDialog(); ret = -1; return ret; } #endregion return ret; } private int Backup2() { int ret = 0; DateTime time = DateTime.Now; // csv File this.FileBackup2(this.ParentForm.PathDataBackupFolder, time, this.CurrentDataCommonList, this.CollectionLaneData); return ret; } public void DisplayRefresh() { this.ParentForm.SystemConfig.CurrentForm = DataStore.FormStore.FormDataStatistics; this.ClearData(); this.buttonSave.Enabled = false; } #endregion #region Override Member protected override void OnLoad(EventArgs e) { base.OnLoad(e); } #endregion #region Event Handler private void buttonBack_Click(object sender, EventArgs e) { this.ParentForm.ChildFormMenu.DisplayRefresh(); ((FormMain)(Owner)).smartForm.Show((int)DataStore.FormStore.FormMenu); } private void buttonFileSelect_Click(object sender, EventArgs e) { DialogFormDataStatistics form = new DialogFormDataStatistics(this); if (form.ShowDialog() == DialogResult.OK) this.buttonSave.Enabled = true; else this.buttonSave.Enabled = false; } private void buttonSave_Click(object sender, EventArgs e) { if (this.SelectFilePath == "") return; this.buttonSave.Enabled = false; if (this.ParentForm.SystemConfig.IsPart11 == false) this.Backup1(); else this.Backup2(); this.buttonSave.Enabled = true; } #endregion } }