diff --git a/VECTO3GUI2020/Helper/Converter/MultipleBoolConverter.cs b/VECTO3GUI2020/Helper/Converter/MultipleBoolConverter.cs new file mode 100644 index 0000000000000000000000000000000000000000..2217f002db725c114b5b54c7c3cc4e235f79bbe1 --- /dev/null +++ b/VECTO3GUI2020/Helper/Converter/MultipleBoolConverter.cs @@ -0,0 +1,33 @@ +using System; +using System.Globalization; +using System.Linq; +using System.Windows.Data; + +namespace VECTO3GUI2020.Helper.Converter +{ + public class MultipleBoolConverter : IMultiValueConverter + { + #region Implementation of IMultiValueConverter + + public object Convert(object[] values, Type targetType, object parameter, CultureInfo culture) + { + var boolVals = values.Cast<bool>(); + bool returnValue = (bool)values[0]; + foreach (var val in boolVals) { + returnValue = returnValue && val; + if (!returnValue) { + break; + } + } + + return returnValue; + } + + public object[] ConvertBack(object value, Type[] targetTypes, object parameter, CultureInfo culture) + { + throw new NotImplementedException(); + } + + #endregion + } +} \ No newline at end of file diff --git a/VECTO3GUI2020/VECTO3GUI2020.csproj b/VECTO3GUI2020/VECTO3GUI2020.csproj index c79a96c6d09a6228b0709ba2b7c21b31da7eca54..339b942e079cabaa58a392f32060de39434d0df9 100644 --- a/VECTO3GUI2020/VECTO3GUI2020.csproj +++ b/VECTO3GUI2020/VECTO3GUI2020.csproj @@ -163,6 +163,7 @@ <Compile Include="Helper\Converter\InvertBoolConverter.cs" /> <Compile Include="Helper\Converter\JobTypeStringConverter.cs" /> <Compile Include="Helper\Converter\LabledTextBoxLabelConverter.cs" /> + <Compile Include="Helper\Converter\MultipleBoolConverter.cs" /> <Compile Include="Helper\Converter\MultistageParameterModeToVisibilityConverter.cs" /> <Compile Include="Helper\Converter\BoolToIntConverter.cs" /> <Compile Include="Helper\Converter\NullToUnsetValueConverter.cs" /> diff --git a/VECTO3GUI2020/ViewModel/Implementation/Common/BackingStorage.cs b/VECTO3GUI2020/ViewModel/Implementation/Common/BackingStorage.cs index 98632857888c848bea268542e89eb2465280a5fa..45de76bb68f1528775f17a5666611bbe9382ee4b 100644 --- a/VECTO3GUI2020/ViewModel/Implementation/Common/BackingStorage.cs +++ b/VECTO3GUI2020/ViewModel/Implementation/Common/BackingStorage.cs @@ -40,8 +40,8 @@ namespace VECTO3GUI2020.ViewModel.Implementation.Common private void ResetUnsavedChanges() { - OnPropertyChanged(nameof(UnsavedChanges)); _unsavedChanges.Clear(); + OnPropertyChanged(nameof(UnsavedChanges)); } public void SaveChanges() diff --git a/VECTO3GUI2020/ViewModel/MultiStage/Implementation/CreateVifViewModel.cs b/VECTO3GUI2020/ViewModel/MultiStage/Implementation/CreateVifViewModel.cs index 30ea9249a0d30a687eddee6a30c767729f9c7d81..1c87d0c0ab6eb9c10a737e7f72b35532461b9d69 100644 --- a/VECTO3GUI2020/ViewModel/MultiStage/Implementation/CreateVifViewModel.cs +++ b/VECTO3GUI2020/ViewModel/MultiStage/Implementation/CreateVifViewModel.cs @@ -87,6 +87,8 @@ namespace VECTO3GUI2020.ViewModel.MultiStage.Implementation #endregion + public bool UnsavedChanges => _backingStorage.UnsavedChanges; + public CreateVifViewModel(IDialogHelper dialogHelper, IXMLInputDataReader inputDataReader, @@ -99,17 +101,33 @@ namespace VECTO3GUI2020.ViewModel.MultiStage.Implementation _inputDataReader = inputDataReader; _additionalJobInfo = additionalJobInfo; additionalJobInfo.SetParent(this); - UpdateTitleAndDocumentName(); + + SetupBackingStorage(); + + + UpdateTitleAndDocumentName(); (this as INotifyPropertyChanged).PropertyChanged += CreateVifViewModel_PropertyChanged; } - private void CreateVifViewModel_PropertyChanged(object sender, PropertyChangedEventArgs e) + private void SetupBackingStorage() + { + _backingStorage = new BackingStorage<CreateVifViewModel>(this, + nameof(this.PrimaryInputPath), + nameof(this.StageInputPath)); + _backingStorage.PropertyChanged += (object s, PropertyChangedEventArgs e) => { + OnPropertyChanged(nameof(UnsavedChanges)); + }; + } + + private void CreateVifViewModel_PropertyChanged(object sender, PropertyChangedEventArgs e) { + switch (e.PropertyName) { case nameof(DataSource): case nameof(Completed): + case nameof(UnsavedChanges): UpdateTitleAndDocumentName(); break; default: @@ -123,6 +141,7 @@ namespace VECTO3GUI2020.ViewModel.MultiStage.Implementation IAdditionalJobInfoViewModel additionalJobInfo) : this(dialogHelper, inputDataReader, additionalJobInfo) { SetInputData(inputData); + _backingStorage.SaveChanges(); } public CreateVifViewModel(bool completed, IDialogHelper dialogHelper, IXMLInputDataReader inputDataReader, @@ -158,6 +177,7 @@ namespace VECTO3GUI2020.ViewModel.MultiStage.Implementation titleStringBuilder.Append(" - ").Append(Path.GetFileName(DataSource.SourceFile)); } + titleStringBuilder.Append(UnsavedChanges ? "*" : ""); Title = titleStringBuilder.ToString(); DocumentName = Path.GetFileNameWithoutExtension(_dataSource?.SourceFile) ?? $"New {VifType} {_newVifCount}"; } @@ -281,12 +301,13 @@ namespace VECTO3GUI2020.ViewModel.MultiStage.Implementation Debug.WriteLine(jsonString); File.WriteAllText(path, jsonString); SetInputData(JSONInputDataFactory.ReadJsonJob(path)); + _backingStorage.SaveChanges(); return path; } - private ICommand _saveJobAsCommand; + private IRelayCommand _saveJobAsCommand; - public ICommand SaveJobAsCommand + public IRelayCommand SaveJobAsCommand { get => _saveJobAsCommand ?? (_saveJobAsCommand = new RelayCommand(() => { if (CanBeSaved()) { @@ -421,6 +442,7 @@ namespace VECTO3GUI2020.ViewModel.MultiStage.Implementation private string _documentName; private DataSource _dataSource; private IAdditionalJobInfoViewModel _additionalJobInfo; + private BackingStorage<CreateVifViewModel> _backingStorage; public string DocumentName diff --git a/VECTO3GUI2020/Views/Multistage/CreateVifView.xaml b/VECTO3GUI2020/Views/Multistage/CreateVifView.xaml index 1052b4a2aab20ef4780c0b81cbbb98e96f6690df..017e59827400afc8400c6f4232d93c000fe89738 100644 --- a/VECTO3GUI2020/Views/Multistage/CreateVifView.xaml +++ b/VECTO3GUI2020/Views/Multistage/CreateVifView.xaml @@ -13,6 +13,11 @@ d:DesignHeight="450" d:DesignWidth="800" d:DataContext="{d:DesignInstance implementation1:CreateVifViewModel}"> <Grid> <DockPanel LastChildFill="False" HorizontalAlignment="Stretch" VerticalAlignment="Stretch"> + <!--<Label HorizontalAlignment="Center" DockPanel.Dock="Top" + Visibility="{Binding UnsavedChanges, + Converter={StaticResource BooleanToVisibilityConverter}}"> + There are unsaved changes + </Label>--> <Grid DockPanel.Dock="Top" VerticalAlignment="Top"> <Grid.RowDefinitions> <RowDefinition></RowDefinition> @@ -59,8 +64,15 @@ <DockPanel DockPanel.Dock="Bottom" LastChildFill="False"> <UniformGrid DockPanel.Dock="Right" Rows="1" Width="500" HorizontalAlignment="Right"> <Button Style="{StaticResource MultiStageButtonStyle1}">Create</Button> - <Button Style="{StaticResource MultiStageButtonStyle1}" Command="{Binding SaveJobAsCommand}">Save Job as ...</Button> - <Button Style="{StaticResource MultiStageButtonStyle1}" Command="{Binding SaveJobCommand}">Save Job</Button> + <Button Style="{StaticResource MultiStageButtonStyle1}" + Command="{Binding SaveJobAsCommand}" + > + Save Job as ... + </Button> + <Button Style="{StaticResource MultiStageButtonStyle1}" + Command="{Binding SaveJobCommand}"> + Save Job + </Button> <Button Style="{StaticResource MultiStageButtonStyle1}" Command="{Binding CloseWindowCommand}" CommandParameter="{Binding RelativeSource={RelativeSource Mode=FindAncestor, AncestorType={x:Type Window}}}">Close</Button>