Imports System.Collections.ObjectModel Imports System.Drawing Imports System.IO Imports System.Reflection Imports EgtUILib Imports EgtWPFLib5 Imports Icarus.ImportExportMachiningPanelVM Public Class ImportExportMachiningPanelVM Inherits VMBase Private Const m_MaterialDataExtension As String = ".mtd" Public Shared ReadOnly Property MaterialDataExtension As String Get Return m_MaterialDataExtension End Get End Property Private Const m_OriginalMaterialDataExtension As String = ".omtd" Public Shared ReadOnly Property OriginalMaterialDataExtension As String Get Return m_OriginalMaterialDataExtension End Get End Property Private Const m_MachiningDataExtension As String = ".mcd" Public Shared ReadOnly Property MachiningDataExtension As String Get Return m_MachiningDataExtension End Get End Property ' Modalita' di apertura della finestra Public Enum WindowModeEnum As Integer IMPORT = 1 EXPORT = 2 IMPORT_ORIG = 3 EXPORT_ORIG = 4 End Enum ' Tipo da importare/esportare Public Enum WindowTypeEnum As Integer MATERIAL = 1 MACHINING = 2 End Enum Private m_WindowMode As WindowModeEnum Public ReadOnly Property WindowMode As WindowModeEnum Get Return m_WindowMode End Get End Property Private m_WindowType As WindowTypeEnum Public ReadOnly Property WindowType As WindowTypeEnum Get Return m_WindowType End Get End Property ' Lista delle lavorazioni Private m_MachiningList As New ObservableCollection(Of ImpExpMachiningItem) Public Property MachiningList As ObservableCollection(Of ImpExpMachiningItem) Get Return m_MachiningList End Get Set(value As ObservableCollection(Of ImpExpMachiningItem)) m_MachiningList = value End Set End Property ' Percorso del file da cui importare le lavorazioni Private m_ImportFilePath As String Public ReadOnly Property ImportFilePath As String Get Return m_ImportFilePath End Get End Property ' Lista delle lavorazioni presenti nel file da cui importare Private m_ImportFileMachiningNameList As String() Public ReadOnly Property ImportFileMachiningNameList As String() Get Return m_ImportFileMachiningNameList End Get End Property ' Lista delle lavorazioni importate con successo Private m_vsImported As String() Public ReadOnly Property vsImported As String() Get Return m_vsImported End Get End Property Public ReadOnly Property IsEnabledOkBtn As Boolean Get For Each Machining In MachiningList If Machining.Active Then Return True Next Return False End Get End Property Friend Event m_CloseWindow(bDialogResult As Boolean) ' Definizione comandi Private m_cmdOk As ICommand #Region "MESSAGES" Public ReadOnly Property OkMsg As String Get If WindowMode = WindowModeEnum.IMPORT Then Return EgtMsg(31450) Else Return EgtMsg(31451) End If End Get End Property #End Region ' Messages #Region "CONSTRUCTOR" ' export Sub New(Type As WindowTypeEnum, Mode As WindowModeEnum, Optional sImportFilePath As String = "") m_WindowType = Type ImpExpMachiningItem.SetWindowType(m_WindowType) m_WindowMode = Mode ' carico lista lavorazioni MachiningList.Clear() Select Case Mode Case WindowModeEnum.IMPORT Select Case Type Case WindowTypeEnum.MATERIAL m_ImportFilePath = sImportFilePath ' carico lista lavorazioni MachiningList.Clear() ' leggo ed aggiungo le altre Dim nIndex As Integer = 1 Dim sGUID As String = "" Dim sName As String = "" Dim sMaterials As String = "" Dim bIsOriginal = False Dim bIsCustom = False While ReadMachiningParamString(nIndex, MAT_GUID, "", sGUID, sImportFilePath) > 0 Dim Guid As Guid = Guid.Empty Guid.TryParse(sGUID, Guid) ReadMachiningParamString(nIndex, MAT_NAME, "", sName, sImportFilePath) Dim sOrigGUID As String = "" ReadMachiningParamString(nIndex, MAT_ORIG, "", sOrigGUID, sImportFilePath) If sOrigGUID = ORIG_MATERIAL Then If Not bIsOriginal Then bIsOriginal = True Else If Not bIsCustom Then bIsCustom = True End If MachiningList.Add(New ImpExpMachiningItem(nIndex, Guid, sName, AlreadyExist(sName))) nIndex += 1 End While If bIsOriginal AndAlso bIsCustom Then MessageBox.Show("Corrupted file! Impossible to import it!") ElseIf bIsOriginal Then LoadOriginalMaterial() End If Case WindowTypeEnum.MACHINING m_ImportFilePath = sImportFilePath ' carico lista lavorazioni MachiningList.Clear() ' leggo ed aggiungo le altre Dim nIndex As Integer = 1 Dim sGUID As String = "" Dim sName As String = "" Dim sMaterials As String = "" While ReadMachiningParamString(nIndex, MAC_GUID, "", sGUID, sImportFilePath) > 0 Dim Guid As Guid = Guid.Empty Guid.TryParse(sGUID, Guid) ReadMachiningParamString(nIndex, MAC_NAME, "", sName, sImportFilePath) MachiningList.Add(New ImpExpMachiningItem(nIndex, Guid, sName, AlreadyExist(sName))) nIndex += 1 End While End Select Case WindowModeEnum.EXPORT Select Case Type Case WindowTypeEnum.MATERIAL ' leggo ed aggiungo le altre Dim nIndex As Integer = 1 Dim sGUID As String = "" Dim sName As String = "" While ReadMaterialParamString(nIndex, MAC_GUID, "", sGUID) > 0 Dim sOrigGUID As String = "" ReadMaterialParamString(nIndex, MAT_ORIG, "", sOrigGUID) If sOrigGUID <> ORIG_MATERIAL Then Dim Guid As Guid = Guid.Empty Guid.TryParse(sGUID, Guid) ReadMaterialParamString(nIndex, MAC_NAME, "", sName) MachiningList.Add(New ImpExpMachiningItem(nIndex, Guid, sName, False)) End If nIndex += 1 End While Case WindowTypeEnum.MACHINING ' leggo ed aggiungo le altre Dim nIndex As Integer = 1 Dim sGUID As String = "" Dim sName As String = "" While ReadMachiningParamString(nIndex, MAC_GUID, "", sGUID) > 0 Dim Guid As Guid = Guid.Empty Guid.TryParse(sGUID, Guid) ReadMachiningParamString(nIndex, MAC_NAME, "", sName) MachiningList.Add(New ImpExpMachiningItem(nIndex, Guid, sName, False)) nIndex += 1 End While End Select Case WindowModeEnum.EXPORT_ORIG If Type = WindowTypeEnum.MATERIAL Then ' leggo ed aggiungo le altre Dim nIndex As Integer = 1 Dim sGUID As String = "" Dim sName As String = "" While ReadMaterialParamString(nIndex, MAC_GUID, "", sGUID) > 0 Dim sOrigGUID As String = "" ReadMaterialParamString(nIndex, MAT_ORIG, "", sOrigGUID) If sOrigGUID = ORIG_MATERIAL Then Dim Guid As Guid = Guid.Empty Guid.TryParse(sGUID, Guid) ReadMaterialParamString(nIndex, MAC_NAME, "", sName) MachiningList.Add(New ImpExpMachiningItem(nIndex, Guid, sName, False)) End If nIndex += 1 End While End If End Select ImpExpMachiningItem.m_delEnableOkBtn = AddressOf EnableOkBtn End Sub ' import Sub New(sImportFilePath As String) m_WindowMode = WindowModeEnum.IMPORT m_ImportFilePath = sImportFilePath ' carico lista lavorazioni MachiningList.Clear() ' leggo ed aggiungo le altre Dim nIndex As Integer = 1 Dim sGUID As String = "" Dim sName As String = "" Dim sMaterials As String = "" While ReadMachiningParamString(nIndex, MAC_GUID, "", sGUID, sImportFilePath) > 0 Dim Guid As Guid = Guid.Empty Guid.TryParse(sGUID, Guid) ReadMachiningParamString(nIndex, MAC_NAME, "", sName, sImportFilePath) MachiningList.Add(New ImpExpMachiningItem(nIndex, Guid, sName, AlreadyExist(sName))) nIndex += 1 End While ImpExpMachiningItem.m_delEnableOkBtn = AddressOf EnableOkBtn End Sub #End Region ' Constructor #Region "METHODS" Private Sub EnableOkBtn() NotifyPropertyChanged(NameOf(IsEnabledOkBtn)) End Sub Private Function AlreadyExist(MachiningName As String) As Boolean Select Case m_WindowType Case WindowTypeEnum.MATERIAL Return Map.refMaterialDbVM.MaterialList.Any(Function(x) x.sName = MachiningName) Case Else ' WindowTypeEnum.MACHINING Return Map.refMachiningDbVM.MachiningList.Any(Function(x) x.sName = MachiningName) End Select End Function Enum MaterialState As Integer NOTFOUND = 1 FOUND = 2 NOTORIGSAMENAME = 3 End Enum Private Sub LoadOriginalMaterial() m_WindowMode = WindowModeEnum.IMPORT_ORIG ' verifico se esistono materiali con lo stesso nome ma non originali Dim ImportedMaterialList As New List(Of MaterialState) For Each ImpExpMaterial In m_MachiningList Dim IsNotOrigSameName As MaterialState = MaterialState.NOTFOUND For Each DbMaterial In Map.refMaterialDbVM.MaterialList If DbMaterial.sName = ImpExpMaterial.sName Then Dim sOrigGUID As String = "" ReadMaterialParamString(DbMaterial.nIndex, MAT_ORIG, "", sOrigGUID) If sOrigGUID <> ORIG_MATERIAL Then If Not IsNotOrigSameName Then IsNotOrigSameName = MaterialState.NOTORIGSAMENAME End If Else IsNotOrigSameName = MaterialState.FOUND End If Next ImportedMaterialList.Add(IsNotOrigSameName) Next If ImportedMaterialList.Contains(True) Then Dim sDuplicatedMaterialList As String = "" For Index = 0 To ImportedMaterialList.Count - 1 If ImportedMaterialList(Index) = MaterialState.NOTORIGSAMENAME Then sDuplicatedMaterialList &= " - " & m_MachiningList(Index).sName & Environment.NewLine End If Next MessageBox.Show("Impossible to import the package because materials named:" & Environment.NewLine & sDuplicatedMaterialList & Environment.NewLine & "Please modify the names of these machining and then retry to import the materials.") Return End If ' aggiorno/aggiungo materiali Dim OrigFilePath As String = CurrentMachine.sMaterialFilePath Dim NewMaterial As Material = Nothing For Each Material In m_MachiningList Dim nIndex As Integer = Map.refMaterialDbVM.MaterialList.Max(Function(x) x.nIndex) + 1 If Material.Active Then CurrentMachine.SetMaterialFilePath(ImportFilePath) ' leggo lavorazione da file di import NewMaterial = New Material(Material.nIndex) ' cambio guid, indice e verifico nome NewMaterial.sGUID = Guid.NewGuid.ToString() NewMaterial.SetIndex(nIndex) If Material.AlreadyExist Then If Material.ChangeName Then NewMaterial.sName = Material.sName Map.refMaterialDbVM.MaterialList.Add(NewMaterial) Else ' sostituisco lavorazione gia' presente con stesso nome Dim ToSubstituteMaterial As Material = Map.refMaterialDbVM.MaterialList.FirstOrDefault(Function(x) x.sName = Material.sName) NewMaterial.SetIndex(ToSubstituteMaterial.nIndex) NewMaterial.sGUID = ToSubstituteMaterial.sGUID Dim nToReplaceIndex As Integer = Map.refMaterialDbVM.MaterialList.IndexOf(ToSubstituteMaterial) Map.refMaterialDbVM.MaterialList(nToReplaceIndex) = NewMaterial End If Else Map.refMaterialDbVM.MaterialList.Add(NewMaterial) End If ' ripristino path corretta del Db CurrentMachine.SetMaterialFilePath(OrigFilePath) ' salvo la lavorazione NewMaterial.Save() End If Next ' ripristino path corretta del Db CurrentMachine.SetMaterialFilePath(OrigFilePath) ' seleziono ultima importata If Not IsNothing(NewMaterial) Then Map.refMaterialDbVM.SelMaterial = NewMaterial Map.refMaterialDbVM.NotifyPropertyChanged(NameOf(Map.refMaterialDbVM.SelMaterial)) End If ' imposto Db modificato Map.refMaterialDbVM.SetIsModified(True) ' messaggio con modifiche Dim sMaterialList As String = "" For Index = 0 To ImportedMaterialList.Count - 1 sMaterialList &= " - " & m_MachiningList(Index).sName & " (" & If(ImportedMaterialList(Index) = MaterialState.NOTFOUND, "New", "Updated") & ")" & Environment.NewLine Next MessageBox.Show("List of the materials:" & Environment.NewLine & sMaterialList & Environment.NewLine & "Import successfully completed.") Return End Sub #End Region ' METHODS #Region "COMMANDS" #Region "OkCommand" ''' ''' Returns a command that remove the current selected machining. ''' Public ReadOnly Property OkCommand() As ICommand Get If m_cmdOk Is Nothing Then m_cmdOk = New Command(AddressOf ConfirmImpExpMachinings) End If Return m_cmdOk End Get End Property ''' ''' Manage the MachiningDb closing. This method is invoked by the CloseMachiningDbCommand. ''' Public Sub ConfirmImpExpMachinings(param As Object) Select Case m_WindowMode Case WindowModeEnum.IMPORT Select Case m_WindowType Case WindowTypeEnum.MATERIAL Dim OrigFilePath As String = CurrentMachine.sMaterialFilePath Dim NewMaterial As Material = Nothing For Each Material In m_MachiningList Dim nIndex As Integer = Map.refMaterialDbVM.MaterialList.Max(Function(x) x.nIndex) + 1 If Material.Active Then CurrentMachine.SetMaterialFilePath(ImportFilePath) ' leggo lavorazione da file di import NewMaterial = New Material(Material.nIndex) ' cambio guid, indice e verifico nome NewMaterial.sGUID = Guid.NewGuid.ToString() NewMaterial.SetIndex(nIndex) If Material.AlreadyExist Then If Material.ChangeName Then NewMaterial.sName = Material.sName Map.refMaterialDbVM.MaterialList.Add(NewMaterial) Else ' sostituisco lavorazione gia' presente con stesso nome Dim ToSubstituteMaterial As Material = Map.refMaterialDbVM.MaterialList.FirstOrDefault(Function(x) x.sName = Material.sName) NewMaterial.SetIndex(ToSubstituteMaterial.nIndex) NewMaterial.sGUID = ToSubstituteMaterial.sGUID Dim nToReplaceIndex As Integer = Map.refMaterialDbVM.MaterialList.IndexOf(ToSubstituteMaterial) Map.refMaterialDbVM.MaterialList(nToReplaceIndex) = NewMaterial End If Else Map.refMaterialDbVM.MaterialList.Add(NewMaterial) End If ' ripristino path corretta del Db CurrentMachine.SetMaterialFilePath(OrigFilePath) ' salvo la lavorazione NewMaterial.Save() End If Next ' ripristino path corretta del Db CurrentMachine.SetMaterialFilePath(OrigFilePath) ' seleziono ultima importata If Not IsNothing(NewMaterial) Then Map.refMaterialDbVM.SelMaterial = NewMaterial Map.refMaterialDbVM.NotifyPropertyChanged(NameOf(Map.refMaterialDbVM.SelMaterial)) End If ' imposto Db modificato Map.refMaterialDbVM.SetIsModified(True) Case WindowTypeEnum.MACHINING Dim OrigFilePath As String = CurrentMachine.sMachiningFilePath Dim NewMachining As Machining = Nothing For Each Machining In m_MachiningList Dim nIndex As Integer = Map.refMachiningDbVM.MachiningList.Max(Function(x) x.nIndex) + 1 If Machining.Active Then CurrentMachine.SetMachiningFilePath(ImportFilePath) ' leggo lavorazione da file di import NewMachining = New Machining(Machining.nIndex) ' cambio guid, indice e verifico nome NewMachining.sGUID = Guid.NewGuid.ToString() NewMachining.SetIndex(nIndex) If Machining.AlreadyExist Then If Machining.ChangeName Then NewMachining.sName = Machining.sName Map.refMachiningDbVM.MachiningList.Add(NewMachining) Else ' sostituisco lavorazione gia' presente con stesso nome Dim ToSubstituteMachining As Machining = Map.refMachiningDbVM.MachiningList.FirstOrDefault(Function(x) x.sName = Machining.sName) NewMachining.SetIndex(ToSubstituteMachining.nIndex) NewMachining.sGUID = ToSubstituteMachining.sGUID Dim nToReplaceIndex As Integer = Map.refMachiningDbVM.MachiningList.IndexOf(ToSubstituteMachining) Map.refMachiningDbVM.MachiningList(nToReplaceIndex) = NewMachining End If Else Map.refMachiningDbVM.MachiningList.Add(NewMachining) End If ' ripristino path corretta del Db CurrentMachine.SetMachiningFilePath(OrigFilePath) ' salvo la lavorazione NewMachining.Save() End If Next ' ripristino path corretta del Db CurrentMachine.SetMachiningFilePath(OrigFilePath) ' seleziono ultima importata If Not IsNothing(NewMachining) Then Map.refMachiningDbVM.SelMachining = NewMachining Map.refMachiningDbVM.NotifyPropertyChanged(NameOf(Map.refMachiningDbVM.SelMachining)) End If ' imposto Db modificato Map.refMachiningDbVM.SetIsModified(True) End Select Case WindowModeEnum.EXPORT, WindowModeEnum.EXPORT_ORIG ' chiedo il nome con cui salvare il file Dim sExtension As String ="" If m_WindowType = WindowTypeEnum.MATERIAL Then If m_WindowMode = WindowModeEnum.EXPORT_ORIG Then sExtension = OriginalMaterialDataExtension Else sExtension = MaterialDataExtension End If Else sExtension = MachiningDataExtension End If Dim SaveFileDlg As New System.Windows.Forms.SaveFileDialog() With { .Title = EgtMsg(31451) & " " & EgtMsg(31452), .Filter = "File data (*" & sExtension & ")|*" & sExtension, .FileName = String.Empty } If SaveFileDlg.ShowDialog() <> System.Windows.Forms.DialogResult.OK Then Return Dim sFilePath As String = String.Empty sFilePath = SaveFileDlg.FileName ' se esiste già lo elimino If File.Exists(sFilePath) Then Try File.Delete(sFilePath) Catch ex As Exception End Try End If ' creo nuovo file If Not File.Exists(sFilePath) Then Try File.WriteAllLines(sFilePath, {"; Commento per evitare BOM con UTF-8"}) Catch ex As Exception End Try End If Select Case m_WindowType Case WindowTypeEnum.MATERIAL Dim ActiveMachiningList As List(Of Material) = (From Material In Map.refMaterialDbVM.MaterialList Select Material Where m_MachiningList.Any(Function(x) x.sGUID.ToString() = Material.sGUID AndAlso x.Active)).ToList() ' salvo tutti i materiali sul Db For Index = 0 To ActiveMachiningList.Count - 1 ActiveMachiningList(Index).WriteParamsOnDb(Index + 1, sFilePath) Next Case WindowTypeEnum.MACHINING Dim ActiveMachiningList As List(Of Machining) = (From Machining In Map.refMachiningDbVM.MachiningList Select Machining Where m_MachiningList.Any(Function(x) x.sGUID.ToString() = Machining.sGUID AndAlso x.Active)).ToList() ' salvo tutte le lavorazioni sul Db For Index = 0 To ActiveMachiningList.Count - 1 ActiveMachiningList(Index).WriteParamsOnDb(Index + 1, sFilePath) Next End Select End Select ' Chiusura finestra RaiseEvent m_CloseWindow(True) End Sub #End Region ' OkCommand #End Region ' Commands End Class Public Class ImpExpMachiningItem Inherits VMBase Public Const IMPEXPNAME As String = "_imp" ' Actions Friend Shared m_delEnableOkBtn As Action Private Shared m_Empty As New MachiningIndex(-1, Guid.Empty, "None") Private Shared m_WindowType As WindowTypeEnum Friend Shared Sub SetWindowType(value As WindowTypeEnum) m_WindowType = value End Sub Private m_nIndex As Integer Public ReadOnly Property nIndex As Integer Get Return m_nIndex End Get End Property Private m_sGUID As Guid Public ReadOnly Property sGUID As Guid Get Return m_sGUID End Get End Property Private m_sOrigName As String Private m_sName As String Public ReadOnly Property sName As String Get Return m_sName End Get End Property Private m_Active As Boolean Public Property Active As Boolean Get Return m_Active End Get Set(value As Boolean) ' se esiste gia' chiedo se sovrascriverla If value Then If m_AlreadyExist Then Select Case m_WindowType Case WindowTypeEnum.MATERIAL Select Case System.Windows.MessageBox.Show("Material already existing in Db. Overwrite it?", "", MessageBoxButton.YesNoCancel) Case MessageBoxResult.Yes m_ChangeName = False m_Active = True Case MessageBoxResult.No Dim bImpNameAlreadyInList = False Dim nImpNameIndex As Integer = 0 If Map.refMaterialDbVM.MaterialList.Any(Function(x) x.sName = m_sOrigName & IMPEXPNAME) Then nImpNameIndex += 1 While Map.refMaterialDbVM.MaterialList.Any(Function(x) x.sName = m_sOrigName & IMPEXPNAME & "_" & nImpNameIndex) nImpNameIndex += 1 End While End If m_sName = m_sOrigName & IMPEXPNAME & If(nImpNameIndex > 0, "_" & nImpNameIndex, "") System.Windows.MessageBox.Show("Material will be imported with the name: " & m_sName, "", MessageBoxButton.OK) NotifyPropertyChanged(NameOf(sName)) m_ChangeName = True m_Active = True Case Else m_Active = False End Select Case WindowTypeEnum.MACHINING Select Case System.Windows.MessageBox.Show("Machining already existing in Db. Overwrite it?", "", MessageBoxButton.YesNoCancel) Case MessageBoxResult.Yes m_ChangeName = False m_Active = True Case MessageBoxResult.No Dim bImpNameAlreadyInList = False Dim nImpNameIndex As Integer = 0 If Map.refMachiningDbVM.MachiningList.Any(Function(x) x.sName = m_sOrigName & IMPEXPNAME) Then nImpNameIndex += 1 While Map.refMachiningDbVM.MachiningList.Any(Function(x) x.sName = m_sOrigName & IMPEXPNAME & "_" & nImpNameIndex) nImpNameIndex += 1 End While End If m_sName = m_sOrigName & IMPEXPNAME & If(nImpNameIndex > 0, "_" & nImpNameIndex, "") System.Windows.MessageBox.Show("Machining will be imported with the name: " & m_sName, "", MessageBoxButton.OK) NotifyPropertyChanged(NameOf(sName)) m_ChangeName = True m_Active = True Case Else m_Active = False End Select End Select NotifyPropertyChanged(NameOf(Active)) Else m_Active = True End If Else m_ChangeName = False m_Active = False m_sName = m_sOrigName NotifyPropertyChanged(NameOf(sName)) End If NotifyPropertyChanged(NameOf(Overwrite_Visibility)) If Not IsNothing(m_delEnableOkBtn) Then m_delEnableOkBtn() End Set End Property ' Parametro che indica se questo item da importare esiste gia' Private m_AlreadyExist As Boolean Friend ReadOnly Property AlreadyExist As Boolean Get Return m_AlreadyExist End Get End Property Private m_Overwrite_Visibility As Visibility = Visibility.Collapsed Public ReadOnly Property Overwrite_Visibility As Visibility Get Return If(m_Active AndAlso m_AlreadyExist AndAlso Not m_ChangeName, Visibility.Visible, Visibility.Collapsed) End Get End Property ' Parametro che indica se cambiare il nome di un item che esiste gia' o sovrascriverlo Private m_ChangeName As Boolean Friend Property ChangeName As Boolean Get Return m_ChangeName End Get Set(value As Boolean) m_ChangeName = value End Set End Property Sub New(nIndex As Integer, GUID As Guid, sName As String, AlreadyExist As Boolean) m_nIndex = nIndex m_sGUID = GUID m_sOrigName = sName m_sName = sName m_AlreadyExist = AlreadyExist m_Active = False End Sub Friend Shared Function Empty() As MachiningIndex Return m_Empty End Function End Class