From cc28b87b9fd6809821f1f97862bfbf82f62e56ec Mon Sep 17 00:00:00 2001 From: mdn <1stdragon@gmail.com> Date: Fri, 4 Dec 2015 07:47:13 +0100 Subject: [PATCH] Init --- .gitignore | 29 ++++ TimeScheduler/TimeScheduler.sln | 22 +++ TimeScheduler/TimeScheduler/App.config | 6 + TimeScheduler/TimeScheduler/App.xaml | 9 + TimeScheduler/TimeScheduler/App.xaml.cs | 17 ++ .../TimeScheduler/Common/BindingProxy.cs | 38 +++++ .../TimeScheduler/Common/MathUtil.cs | 38 +++++ .../TimeScheduler/Common/NotifyableObject.cs | 38 +++++ .../TimeScheduler/Common/RelayCommand.cs | 45 +++++ TimeScheduler/TimeScheduler/Domain/IDomain.cs | 20 +++ .../TimeScheduler/Domain/Impl/FileDomain.cs | 110 ++++++++++++ .../TimeScheduler/Domain/Impl/TimeItem.cs | 23 +++ .../TimeScheduler/Domain/TimeItemType.cs | 15 ++ TimeScheduler/TimeScheduler/MainWindow.xaml | 157 ++++++++++++++++++ .../TimeScheduler/MainWindow.xaml.cs | 11 ++ .../TimeScheduler/Model/ATimeItem.cs | 13 ++ .../TimeScheduler/Model/ITimeItem.cs | 24 +++ .../TimeScheduler/Properties/AssemblyInfo.cs | 55 ++++++ .../Properties/Resources.Designer.cs | 71 ++++++++ .../TimeScheduler/Properties/Resources.resx | 117 +++++++++++++ .../Properties/Settings.Designer.cs | 30 ++++ .../Properties/Settings.settings | 7 + .../TimeScheduler/TimeScheduler.csproj | 118 +++++++++++++ .../TimeScheduler/ViewModel/MainViewModel.cs | 126 ++++++++++++++ 24 files changed, 1139 insertions(+) create mode 100644 .gitignore create mode 100644 TimeScheduler/TimeScheduler.sln create mode 100644 TimeScheduler/TimeScheduler/App.config create mode 100644 TimeScheduler/TimeScheduler/App.xaml create mode 100644 TimeScheduler/TimeScheduler/App.xaml.cs create mode 100644 TimeScheduler/TimeScheduler/Common/BindingProxy.cs create mode 100644 TimeScheduler/TimeScheduler/Common/MathUtil.cs create mode 100644 TimeScheduler/TimeScheduler/Common/NotifyableObject.cs create mode 100644 TimeScheduler/TimeScheduler/Common/RelayCommand.cs create mode 100644 TimeScheduler/TimeScheduler/Domain/IDomain.cs create mode 100644 TimeScheduler/TimeScheduler/Domain/Impl/FileDomain.cs create mode 100644 TimeScheduler/TimeScheduler/Domain/Impl/TimeItem.cs create mode 100644 TimeScheduler/TimeScheduler/Domain/TimeItemType.cs create mode 100644 TimeScheduler/TimeScheduler/MainWindow.xaml create mode 100644 TimeScheduler/TimeScheduler/MainWindow.xaml.cs create mode 100644 TimeScheduler/TimeScheduler/Model/ATimeItem.cs create mode 100644 TimeScheduler/TimeScheduler/Model/ITimeItem.cs create mode 100644 TimeScheduler/TimeScheduler/Properties/AssemblyInfo.cs create mode 100644 TimeScheduler/TimeScheduler/Properties/Resources.Designer.cs create mode 100644 TimeScheduler/TimeScheduler/Properties/Resources.resx create mode 100644 TimeScheduler/TimeScheduler/Properties/Settings.Designer.cs create mode 100644 TimeScheduler/TimeScheduler/Properties/Settings.settings create mode 100644 TimeScheduler/TimeScheduler/TimeScheduler.csproj create mode 100644 TimeScheduler/TimeScheduler/ViewModel/MainViewModel.cs diff --git a/.gitignore b/.gitignore new file mode 100644 index 0000000..0bc8230 --- /dev/null +++ b/.gitignore @@ -0,0 +1,29 @@ + +#ignore thumbnails created by windows +Thumbs.db +#Ignore files build by Visual Studio +*.obj +*.exe +*.pdb +*.user +*.aps +*.pch +*.vspscc +*_i.c +*_p.c +*.ncb +*.suo +*.tlb +*.tlh +*.bak +*.cache +*.ilk +*.log +[Bb]in +[Dd]ebug*/ +*.lib +*.sbr +obj/ +[Rr]elease*/ +_ReSharper*/ +[Tt]est[Rr]esult* diff --git a/TimeScheduler/TimeScheduler.sln b/TimeScheduler/TimeScheduler.sln new file mode 100644 index 0000000..3b4ec2f --- /dev/null +++ b/TimeScheduler/TimeScheduler.sln @@ -0,0 +1,22 @@ + +Microsoft Visual Studio Solution File, Format Version 12.00 +# Visual Studio 14 +VisualStudioVersion = 14.0.23107.0 +MinimumVisualStudioVersion = 10.0.40219.1 +Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "TimeScheduler", "TimeScheduler\TimeScheduler.csproj", "{0129AAAE-40F7-4B87-959F-0C48806F496A}" +EndProject +Global + GlobalSection(SolutionConfigurationPlatforms) = preSolution + Debug|Any CPU = Debug|Any CPU + Release|Any CPU = Release|Any CPU + EndGlobalSection + GlobalSection(ProjectConfigurationPlatforms) = postSolution + {0129AAAE-40F7-4B87-959F-0C48806F496A}.Debug|Any CPU.ActiveCfg = Debug|Any CPU + {0129AAAE-40F7-4B87-959F-0C48806F496A}.Debug|Any CPU.Build.0 = Debug|Any CPU + {0129AAAE-40F7-4B87-959F-0C48806F496A}.Release|Any CPU.ActiveCfg = Release|Any CPU + {0129AAAE-40F7-4B87-959F-0C48806F496A}.Release|Any CPU.Build.0 = Release|Any CPU + EndGlobalSection + GlobalSection(SolutionProperties) = preSolution + HideSolutionNode = FALSE + EndGlobalSection +EndGlobal diff --git a/TimeScheduler/TimeScheduler/App.config b/TimeScheduler/TimeScheduler/App.config new file mode 100644 index 0000000..88fa402 --- /dev/null +++ b/TimeScheduler/TimeScheduler/App.config @@ -0,0 +1,6 @@ + + + + + + \ No newline at end of file diff --git a/TimeScheduler/TimeScheduler/App.xaml b/TimeScheduler/TimeScheduler/App.xaml new file mode 100644 index 0000000..eeab7ec --- /dev/null +++ b/TimeScheduler/TimeScheduler/App.xaml @@ -0,0 +1,9 @@ + + + + + diff --git a/TimeScheduler/TimeScheduler/App.xaml.cs b/TimeScheduler/TimeScheduler/App.xaml.cs new file mode 100644 index 0000000..cc73bb8 --- /dev/null +++ b/TimeScheduler/TimeScheduler/App.xaml.cs @@ -0,0 +1,17 @@ +using System; +using System.Collections.Generic; +using System.Configuration; +using System.Data; +using System.Linq; +using System.Threading.Tasks; +using System.Windows; + +namespace TimeScheduler +{ + /// + /// Interaktionslogik für "App.xaml" + /// + public partial class App : Application + { + } +} diff --git a/TimeScheduler/TimeScheduler/Common/BindingProxy.cs b/TimeScheduler/TimeScheduler/Common/BindingProxy.cs new file mode 100644 index 0000000..0bf7614 --- /dev/null +++ b/TimeScheduler/TimeScheduler/Common/BindingProxy.cs @@ -0,0 +1,38 @@ +using System.Windows; + +namespace TimeScheduler.Common +{ + /// Hilfsklasse, mit der man in andere Datenkontexte greifen kann + /// + /// Vorbereitung: + /// + /// <FrameworkElement.Resources> + /// &tl;c:BindingProxy x:Key="proxy" Data="{Binding}"> + /// </FrameworkElement.Resources> + /// + /// Verwendung an einer anderen Stelle: + /// + /// <FrameworkElement Property="{Binding Source={StaticResource proxy},Path=VMProperty}"> + /// + /// + class BindingProxy : Freezable + { + #region Konstruktion + /// Standard-Konstruktor + public BindingProxy() { } + #endregion + + #region Überschreibungen + /// Ermittelt das Hauptobjekt + /// Ein neues Hauptobjekt + protected override Freezable CreateInstanceCore() { return new BindingProxy(); } + #endregion + + #region Eigenschaften + /// Getter/Setter für + public object Data { get { return GetValue(DataProperty); } set { SetValue(DataProperty, value); } } + /// Eigenschaft in der der Datenkontext gebunden wird + public static readonly DependencyProperty DataProperty = DependencyProperty.Register("Data", typeof(object), typeof(BindingProxy), new PropertyMetadata(null)); + #endregion + } +} diff --git a/TimeScheduler/TimeScheduler/Common/MathUtil.cs b/TimeScheduler/TimeScheduler/Common/MathUtil.cs new file mode 100644 index 0000000..6aab752 --- /dev/null +++ b/TimeScheduler/TimeScheduler/Common/MathUtil.cs @@ -0,0 +1,38 @@ +using System; +using System.Collections.Generic; +using System.Linq; +using System.Text; +using System.Threading.Tasks; + +namespace TimeScheduler.Common +{ + public static class MathUtil + { + public static int IncrementDecrementNumber(string num, int minValue, int maxVal, bool increment) + { + int newNum = ValidateNumber(num, minValue, maxVal); + if (increment) + newNum = Math.Min(newNum + 1, maxVal); + else + newNum = Math.Max(newNum - 1, 0); + return newNum; + } + + public static int ValidateNumber(string newNum, int minValue, int maxValue) + { + int num; + if (!int.TryParse(newNum, out num)) + return 0; + + return ValidateNumber(num, minValue, maxValue); + } + + public static int ValidateNumber(int newNum, int minValue, int maxValue) + { + newNum = Math.Max(newNum, minValue); + newNum = Math.Min(newNum, maxValue); + + return newNum; + } + } +} diff --git a/TimeScheduler/TimeScheduler/Common/NotifyableObject.cs b/TimeScheduler/TimeScheduler/Common/NotifyableObject.cs new file mode 100644 index 0000000..20a673f --- /dev/null +++ b/TimeScheduler/TimeScheduler/Common/NotifyableObject.cs @@ -0,0 +1,38 @@ +using System.Collections.Generic; +using System.ComponentModel; +using System.Runtime.CompilerServices; + +namespace TimeScheduler.Common +{ + /// Basis-Klasse für Objekte, die sich der Oberfläche mitteilen möchten + abstract class NotifyableObject : INotifyPropertyChanged + { + /// Setzt den neuen Wert auf das Feld, wenn sie unterschiedlich sind und wird das -Ereignis + /// Typ des Feldes + /// Verweis aufs Feld + /// Neuer Wert + /// Name der Eigenschaft, die verändert wird + /// Wahr, wenn es ein neuer Wert ist, sonst Falsch + protected bool SetField(ref T field, T newValue, [CallerMemberName]string propertyName = null) + { + // Wenn beide Werte gleich sind, dann nichts tun + if (object.Equals(field, newValue)) return false; + //if (Comparer.Default.Compare(field, newValue) == 0) return false; + + field = newValue; + OnPropertyChanged(propertyName); + return true; + } + + /// Wirft das Ereignis + /// + protected void OnPropertyChanged([CallerMemberName]string propertyName = null) + { + var handler = PropertyChanged; + if (handler != null) + handler(this, new PropertyChangedEventArgs(propertyName)); + } + /// Ereignis um der Oberfläche mitzuteilen, dass sich eine Eigenschaft verändert hat + public event PropertyChangedEventHandler PropertyChanged; + } +} diff --git a/TimeScheduler/TimeScheduler/Common/RelayCommand.cs b/TimeScheduler/TimeScheduler/Common/RelayCommand.cs new file mode 100644 index 0000000..622652f --- /dev/null +++ b/TimeScheduler/TimeScheduler/Common/RelayCommand.cs @@ -0,0 +1,45 @@ +using System; +using System.Windows.Input; + +namespace TimeScheduler.Common +{ + /// Proxy-Objekt zur -Schnittstelle + class RelayCommand : ICommand + { + #region Konstruktion + private Action execute_; + private Func canExecute_; + + /// Konstruktor + /// Auszuführende Funktion + /// Prüfung zum ausführen der Funktion + public RelayCommand(Action execute, Func canExecute = null) + { + if (execute == null) throw new ArgumentNullException("execute"); + + execute_ = execute; + canExecute_ = canExecute; + } + #endregion + + #region ICommand + /// Wirft Ereignis, dass die Oberfläche die Prüfung zum ausführen erneut ruft + public void OnCanExecuteChanged() + { + var handler = CanExecuteChanged; + if (handler != null) + handler(this, EventArgs.Empty); + } + public event EventHandler CanExecuteChanged; + + /// Prüft ob das Kommando ausgeführt werden darf + /// + /// + public bool CanExecute(object parameter) { return canExecute_ == null ? true : canExecute_(); } + + /// Wird gerufen um das Kommando ausführen + /// + public void Execute(object parameter) { execute_(); } + #endregion + } +} diff --git a/TimeScheduler/TimeScheduler/Domain/IDomain.cs b/TimeScheduler/TimeScheduler/Domain/IDomain.cs new file mode 100644 index 0000000..2a031c5 --- /dev/null +++ b/TimeScheduler/TimeScheduler/Domain/IDomain.cs @@ -0,0 +1,20 @@ +using System; +using System.Collections.Generic; +using System.Linq; +using System.Text; +using System.Threading.Tasks; + +namespace TimeScheduler.Model +{ + /// Schnittstelle zum Provider der die Daten ermitteln + public interface IDomain + { + List GetItems(DateTime date); + + Dictionary GetCostUnits(); + + void ElementAdded(ITimeItem timeItem); + void ElementChanged(ITimeItem timeItem); + void ElementRemoved(ITimeItem timeItem); + } +} diff --git a/TimeScheduler/TimeScheduler/Domain/Impl/FileDomain.cs b/TimeScheduler/TimeScheduler/Domain/Impl/FileDomain.cs new file mode 100644 index 0000000..4139e68 --- /dev/null +++ b/TimeScheduler/TimeScheduler/Domain/Impl/FileDomain.cs @@ -0,0 +1,110 @@ +using System; +using System.Collections.Generic; +using System.IO; +using System.Runtime.Serialization.Formatters.Binary; +using System.Xml.Serialization; +using System.Linq; + +namespace TimeScheduler.Model.Impl +{ + class FileDomain : IDomain + { + #region Konstruktion + private List allItems_ = new List(); + private string filename_ = string.Empty; + + public FileDomain() + { + var fi = new FileInfo(System.Reflection.Assembly.GetExecutingAssembly().Location); + filename_ = Path.Combine(fi.DirectoryName, fi.Name + ".xmldata"); + + if (File.Exists(filename_)) + ReadList(filename_); + else + { + // Wenn nichts vorhanden, dann einen Spielsatz anlegen + allItems_ = new List { + new TimeItem { Description = "Desc 01", From = DateTime.Now.Subtract(TimeSpan.FromHours(2)), Till = DateTime.Now, CostUnit = 14, ItemType = TimeItemType.Normal }, + new TimeItem { Description = "Desc 02", From = DateTime.Now.Subtract(TimeSpan.FromHours(2)), Till = DateTime.Now, CostUnit = 13, ItemType = TimeItemType.Break }, + new TimeItem { Description = "Desc 03", From = DateTime.Now.Subtract(TimeSpan.FromHours(2)), Till = DateTime.Now, CostUnit = 12, ItemType = TimeItemType.Holiday }, + new TimeItem { Description = "Desc 04", From = DateTime.Now.Subtract(TimeSpan.FromHours(2)), Till = DateTime.Now, CostUnit = 11, ItemType = TimeItemType.Ill }, + new TimeItem { Description = "Desc 05", From = DateTime.Now.Subtract(TimeSpan.FromHours(2)), Till = DateTime.Now, CostUnit = 15, ItemType = TimeItemType.Normal }, + }; + } + } + #endregion + + #region Hilfsfunktionen + private void ReadList(string filePath) + { + var xs = new XmlSerializer(typeof(List)); + var bin = new BinaryFormatter(); + using (var rd = new StreamReader(filePath)) + { + var elems = xs.Deserialize(rd) as List; + allItems_ = elems; + //allItems.Clear(); + //foreach (var elem in elems) + // allItems.Add(elem); + } + } + + private void WriteList(string path) + { + XmlSerializer xs = new XmlSerializer(typeof(List)); + var bin = new BinaryFormatter(); + using (StreamWriter wr = new StreamWriter(path)) + { + xs.Serialize(wr, (List)allItems_); + } + } + + private void Save() + { + var newFilename = filename_ + ".new"; + WriteList(newFilename); + File.Delete(filename_); + File.Move(newFilename, filename_); + } + #endregion + + #region IDomain + public List GetItems(DateTime date) + { + var founded = allItems_.Where(x => x.From.Date == date); + return founded.ToList(); + } + + public Dictionary GetCostUnits() + { + return new Dictionary + { + { 11, "Allgemein CC1" }, + { 12, "Allgemein CC2" }, + { 13, "Allgemein CC3" }, + { 14, "Allgemein IC4" }, + { 15, "Allgemein CC5" }, + { 16, "Allgemein CC6" }, + { 17, "Allgemein CC7" }, + }; + } + + public void ElementAdded(ITimeItem timeItem) + { + allItems_.Add(timeItem); + Save(); + } + public void ElementChanged(ITimeItem timeItem) + { + allItems_.Remove(timeItem); + allItems_.Add(timeItem); + Save(); + } + public void ElementRemoved(ITimeItem timeItem) + { + allItems_.Remove(timeItem); + Save(); + } + #endregion + } +} diff --git a/TimeScheduler/TimeScheduler/Domain/Impl/TimeItem.cs b/TimeScheduler/TimeScheduler/Domain/Impl/TimeItem.cs new file mode 100644 index 0000000..634cfb2 --- /dev/null +++ b/TimeScheduler/TimeScheduler/Domain/Impl/TimeItem.cs @@ -0,0 +1,23 @@ +using System; +using TimeScheduler.Common; + +namespace TimeScheduler.Model.Impl +{ + public class TimeItem : NotifyableObject, ITimeItem + { + private string description_; + public string Description { get { return description_; } set { SetField(ref description_, value); } } + + private DateTime from_; + public DateTime From { get { return from_; } set { SetField(ref from_, value); } } + + private DateTime till_; + public DateTime Till { get { return till_; } set { SetField(ref till_, value); } } + + private int costUnit_; + public int CostUnit { get { return costUnit_; } set { SetField(ref costUnit_, value); } } + + private TimeItemType itemType_; + public TimeItemType ItemType { get { return itemType_; } set { SetField(ref itemType_, value); } } + } +} diff --git a/TimeScheduler/TimeScheduler/Domain/TimeItemType.cs b/TimeScheduler/TimeScheduler/Domain/TimeItemType.cs new file mode 100644 index 0000000..e266251 --- /dev/null +++ b/TimeScheduler/TimeScheduler/Domain/TimeItemType.cs @@ -0,0 +1,15 @@ +namespace TimeScheduler.Model +{ + /// Typen, die ein sein kann + public enum TimeItemType : int + { + /// Normale Stundenerfassung + Normal = 0, + /// Pause + Break = 1, + /// Urlaub + Holiday = 2, + /// Krankheit + Ill = 3 + } +} diff --git a/TimeScheduler/TimeScheduler/MainWindow.xaml b/TimeScheduler/TimeScheduler/MainWindow.xaml new file mode 100644 index 0000000..db784b7 --- /dev/null +++ b/TimeScheduler/TimeScheduler/MainWindow.xaml @@ -0,0 +1,157 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/TimeScheduler/TimeScheduler/MainWindow.xaml.cs b/TimeScheduler/TimeScheduler/MainWindow.xaml.cs new file mode 100644 index 0000000..fde382c --- /dev/null +++ b/TimeScheduler/TimeScheduler/MainWindow.xaml.cs @@ -0,0 +1,11 @@ +using System.Windows; + +namespace TimeScheduler +{ + /// Interaktionslogik für MainWindow.xaml + public partial class MainWindow : Window + { + /// Standard-Konstruktor + public MainWindow() { InitializeComponent(); } + } +} diff --git a/TimeScheduler/TimeScheduler/Model/ATimeItem.cs b/TimeScheduler/TimeScheduler/Model/ATimeItem.cs new file mode 100644 index 0000000..953de83 --- /dev/null +++ b/TimeScheduler/TimeScheduler/Model/ATimeItem.cs @@ -0,0 +1,13 @@ +using System; +using System.Collections.Generic; +using System.Linq; +using System.Text; +using System.Threading.Tasks; +using TimeScheduler.Common; + +namespace TimeScheduler.Model +{ + abstract class ATimeItem : NotifyableObject, ITimeItem + { + } +} diff --git a/TimeScheduler/TimeScheduler/Model/ITimeItem.cs b/TimeScheduler/TimeScheduler/Model/ITimeItem.cs new file mode 100644 index 0000000..72535c5 --- /dev/null +++ b/TimeScheduler/TimeScheduler/Model/ITimeItem.cs @@ -0,0 +1,24 @@ +using System; +using System.ComponentModel; + +namespace TimeScheduler.Model +{ + /// Beinhaltet die Definition eines Daten-Elementes, das eine Zeiteinheit aufnimmt + public interface ITimeItem : INotifyPropertyChanged + { + /// Textuelle Beschreibung + string Description { get; set; } + + /// Startzeit + DateTime From { get; set; } + + /// Endezeit + DateTime Till { get; set; } + + /// Kostenstelle + int CostUnit { get; set; } + + /// Typ + TimeItemType ItemType { get; set; } + } +} diff --git a/TimeScheduler/TimeScheduler/Properties/AssemblyInfo.cs b/TimeScheduler/TimeScheduler/Properties/AssemblyInfo.cs new file mode 100644 index 0000000..feccbfc --- /dev/null +++ b/TimeScheduler/TimeScheduler/Properties/AssemblyInfo.cs @@ -0,0 +1,55 @@ +using System.Reflection; +using System.Resources; +using System.Runtime.CompilerServices; +using System.Runtime.InteropServices; +using System.Windows; + +// Allgemeine Informationen über eine Assembly werden über die folgenden +// Attribute gesteuert. Ändern Sie diese Attributwerte, um die Informationen zu ändern, +// die einer Assembly zugeordnet sind. +[assembly: AssemblyTitle("TimeScheduler")] +[assembly: AssemblyDescription("")] +[assembly: AssemblyConfiguration("")] +[assembly: AssemblyCompany("")] +[assembly: AssemblyProduct("TimeScheduler")] +[assembly: AssemblyCopyright("Copyright © 2015")] +[assembly: AssemblyTrademark("")] +[assembly: AssemblyCulture("")] + +// Durch Festlegen von ComVisible auf "false" werden die Typen in dieser Assembly unsichtbar +// für COM-Komponenten. Wenn Sie auf einen Typ in dieser Assembly von +// COM aus zugreifen müssen, sollten Sie das ComVisible-Attribut für diesen Typ auf "True" festlegen. +[assembly: ComVisible(false)] + +//Um mit dem Erstellen lokalisierbarer Anwendungen zu beginnen, legen Sie +//ImCodeVerwendeteKultur in der .csproj-Datei +//in einer fest. Wenn Sie in den Quelldateien beispielsweise Deutsch +//(Deutschland) verwenden, legen Sie auf \"de-DE\" fest. Heben Sie dann die Auskommentierung +//des nachstehenden NeutralResourceLanguage-Attributs auf. Aktualisieren Sie "en-US" in der nachstehenden Zeile, +//sodass es mit der UICulture-Einstellung in der Projektdatei übereinstimmt. + +//[assembly: NeutralResourcesLanguage("en-US", UltimateResourceFallbackLocation.Satellite)] + + +[assembly: ThemeInfo( + ResourceDictionaryLocation.None, //Speicherort der designspezifischen Ressourcenwörterbücher + //(wird verwendet, wenn eine Ressource auf der Seite + // oder in den Anwendungsressourcen-Wörterbüchern nicht gefunden werden kann.) + ResourceDictionaryLocation.SourceAssembly //Speicherort des generischen Ressourcenwörterbuchs + //(wird verwendet, wenn eine Ressource auf der Seite, in der Anwendung oder einem + // designspezifischen Ressourcenwörterbuch nicht gefunden werden kann.) +)] + + +// Versionsinformationen für eine Assembly bestehen aus den folgenden vier Werten: +// +// Hauptversion +// Nebenversion +// Buildnummer +// Revision +// +// Sie können alle Werte angeben oder die standardmäßigen Build- und Revisionsnummern +// übernehmen, indem Sie "*" eingeben: +// [assembly: AssemblyVersion("1.0.*")] +[assembly: AssemblyVersion("1.0.0.0")] +[assembly: AssemblyFileVersion("1.0.0.0")] diff --git a/TimeScheduler/TimeScheduler/Properties/Resources.Designer.cs b/TimeScheduler/TimeScheduler/Properties/Resources.Designer.cs new file mode 100644 index 0000000..c38d92a --- /dev/null +++ b/TimeScheduler/TimeScheduler/Properties/Resources.Designer.cs @@ -0,0 +1,71 @@ +//------------------------------------------------------------------------------ +// +// Dieser Code wurde von einem Tool generiert. +// Laufzeitversion: 4.0.30319.42000 +// +// Änderungen an dieser Datei können fehlerhaftes Verhalten verursachen und gehen verloren, wenn +// der Code neu generiert wird. +// +//------------------------------------------------------------------------------ + +namespace TimeScheduler.Properties +{ + + + /// + /// Eine stark typisierte Ressourcenklasse zum Suchen von lokalisierten Zeichenfolgen usw. + /// + // Diese Klasse wurde von der StronglyTypedResourceBuilder-Klasse + // über ein Tool wie ResGen oder Visual Studio automatisch generiert. + // Um einen Member hinzuzufügen oder zu entfernen, bearbeiten Sie die .ResX-Datei und führen dann ResGen + // mit der Option /str erneut aus, oder erstellen Sie Ihr VS-Projekt neu. + [global::System.CodeDom.Compiler.GeneratedCodeAttribute("System.Resources.Tools.StronglyTypedResourceBuilder", "4.0.0.0")] + [global::System.Diagnostics.DebuggerNonUserCodeAttribute()] + [global::System.Runtime.CompilerServices.CompilerGeneratedAttribute()] + internal class Resources + { + + private static global::System.Resources.ResourceManager resourceMan; + + private static global::System.Globalization.CultureInfo resourceCulture; + + [global::System.Diagnostics.CodeAnalysis.SuppressMessageAttribute("Microsoft.Performance", "CA1811:AvoidUncalledPrivateCode")] + internal Resources() + { + } + + /// + /// Gibt die zwischengespeicherte ResourceManager-Instanz zurück, die von dieser Klasse verwendet wird. + /// + [global::System.ComponentModel.EditorBrowsableAttribute(global::System.ComponentModel.EditorBrowsableState.Advanced)] + internal static global::System.Resources.ResourceManager ResourceManager + { + get + { + if ((resourceMan == null)) + { + global::System.Resources.ResourceManager temp = new global::System.Resources.ResourceManager("TimeScheduler.Properties.Resources", typeof(Resources).Assembly); + resourceMan = temp; + } + return resourceMan; + } + } + + /// + /// Überschreibt die CurrentUICulture-Eigenschaft des aktuellen Threads für alle + /// Ressourcenlookups, die diese stark typisierte Ressourcenklasse verwenden. + /// + [global::System.ComponentModel.EditorBrowsableAttribute(global::System.ComponentModel.EditorBrowsableState.Advanced)] + internal static global::System.Globalization.CultureInfo Culture + { + get + { + return resourceCulture; + } + set + { + resourceCulture = value; + } + } + } +} diff --git a/TimeScheduler/TimeScheduler/Properties/Resources.resx b/TimeScheduler/TimeScheduler/Properties/Resources.resx new file mode 100644 index 0000000..af7dbeb --- /dev/null +++ b/TimeScheduler/TimeScheduler/Properties/Resources.resx @@ -0,0 +1,117 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + text/microsoft-resx + + + 2.0 + + + System.Resources.ResXResourceReader, System.Windows.Forms, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089 + + + System.Resources.ResXResourceWriter, System.Windows.Forms, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089 + + \ No newline at end of file diff --git a/TimeScheduler/TimeScheduler/Properties/Settings.Designer.cs b/TimeScheduler/TimeScheduler/Properties/Settings.Designer.cs new file mode 100644 index 0000000..0c2c18a --- /dev/null +++ b/TimeScheduler/TimeScheduler/Properties/Settings.Designer.cs @@ -0,0 +1,30 @@ +//------------------------------------------------------------------------------ +// +// This code was generated by a tool. +// Runtime Version:4.0.30319.42000 +// +// Changes to this file may cause incorrect behavior and will be lost if +// the code is regenerated. +// +//------------------------------------------------------------------------------ + +namespace TimeScheduler.Properties +{ + + + [global::System.Runtime.CompilerServices.CompilerGeneratedAttribute()] + [global::System.CodeDom.Compiler.GeneratedCodeAttribute("Microsoft.VisualStudio.Editors.SettingsDesigner.SettingsSingleFileGenerator", "11.0.0.0")] + internal sealed partial class Settings : global::System.Configuration.ApplicationSettingsBase + { + + private static Settings defaultInstance = ((Settings)(global::System.Configuration.ApplicationSettingsBase.Synchronized(new Settings()))); + + public static Settings Default + { + get + { + return defaultInstance; + } + } + } +} diff --git a/TimeScheduler/TimeScheduler/Properties/Settings.settings b/TimeScheduler/TimeScheduler/Properties/Settings.settings new file mode 100644 index 0000000..033d7a5 --- /dev/null +++ b/TimeScheduler/TimeScheduler/Properties/Settings.settings @@ -0,0 +1,7 @@ + + + + + + + \ No newline at end of file diff --git a/TimeScheduler/TimeScheduler/TimeScheduler.csproj b/TimeScheduler/TimeScheduler/TimeScheduler.csproj new file mode 100644 index 0000000..8b16cd0 --- /dev/null +++ b/TimeScheduler/TimeScheduler/TimeScheduler.csproj @@ -0,0 +1,118 @@ + + + + + Debug + AnyCPU + {0129AAAE-40F7-4B87-959F-0C48806F496A} + WinExe + Properties + TimeScheduler + TimeScheduler + v4.5.2 + 512 + {60dc8134-eba5-43b8-bcc9-bb4bc16c2548};{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC} + 4 + true + + + AnyCPU + true + full + false + bin\Debug\ + DEBUG;TRACE + prompt + 4 + + + AnyCPU + pdbonly + true + bin\Release\ + TRACE + prompt + 4 + + + + + + + + + + + + 4.0 + + + + + + + + MSBuild:Compile + Designer + + + + + + + + + + + + MSBuild:Compile + Designer + + + App.xaml + Code + + + + + MainWindow.xaml + Code + + + + + Code + + + True + True + Resources.resx + + + True + Settings.settings + True + + + ResXFileCodeGenerator + Resources.Designer.cs + + + SettingsSingleFileGenerator + Settings.Designer.cs + + + + + + + + + + \ No newline at end of file diff --git a/TimeScheduler/TimeScheduler/ViewModel/MainViewModel.cs b/TimeScheduler/TimeScheduler/ViewModel/MainViewModel.cs new file mode 100644 index 0000000..f2d8afa --- /dev/null +++ b/TimeScheduler/TimeScheduler/ViewModel/MainViewModel.cs @@ -0,0 +1,126 @@ +using System; +using System.Collections.Generic; +using System.Collections.ObjectModel; +using System.Linq; +using System.Text; +using System.Threading.Tasks; +using System.Windows.Input; +using TimeScheduler.Common; +using TimeScheduler.Model; + +namespace TimeScheduler.ViewModel +{ + class MainViewModel : NotifyableObject + { + #region Konstruktion + private bool inLoading_ = false; + /// Standard-Konstruktor + public MainViewModel() : this(new Model.Impl.FileDomain()) { Refresh(); } + + /// Konstruktor + /// + public MainViewModel(IDomain provider) + { + Provider = provider; + + TimeItems = new ObservableCollection(); + TimeItems.CollectionChanged += TimeItems_CollectionChanged; + + CreateCommands(); + } + + protected IDomain Provider { get; private set; } + #endregion + + #region Eigenschaften + private DateTime currentDate_ = DateTime.Now.Date; + public DateTime CurrentDate + { + get { return currentDate_; } + set + { + if (SetField(ref currentDate_, value)) + RefreshForDate(currentDate_); + } + } + + private Dictionary costUnits_; + public Dictionary CostUnits { get { return costUnits_; } private set { SetField(ref costUnits_, value); } } + + private Dictionary itemTypes_; + public Dictionary ItemTypes { get { return itemTypes_; } private set { SetField(ref itemTypes_, value); } } + + private ObservableCollection timeItems_; + /// Beinhaltet die Elemente des aktuell ausgewählten Tages + public ObservableCollection TimeItems { get { return timeItems_; } private set { SetField(ref timeItems_, value); } } + + private ITimeItem selectedTimeItem_; + /// Das aktuell selektierte Element, von dem weitere Details angezeigt werden sollen + public ITimeItem SelectedTimeItem { get { return selectedTimeItem_; } set { SetField(ref selectedTimeItem_, value); } } + #endregion + + #region Kommandos + private void CreateCommands() + { + RefreshCommand = new RelayCommand(Refresh); + } + + public ICommand RefreshCommand { get; private set; } + private void Refresh() + { + // Standardwerte belegen + CostUnits = Provider.GetCostUnits(); + var it = new Dictionary(); + foreach (TimeItemType tit in Enum.GetValues(typeof(TimeItemType))) + it[tit] = Enum.GetName(typeof(TimeItemType), tit); + ItemTypes = it; + + // Andere Daten ermitteln + RefreshForDate(CurrentDate); + } + private void RefreshForDate(DateTime date) + { + foreach (var item in TimeItems) + item.PropertyChanged -= Item_PropertyChanged; + + // Laufende Datein belegen + var items = Provider.GetItems(date); + + try + { + inLoading_ = true; + TimeItems.Clear(); + foreach (var item in items) + { + item.PropertyChanged += Item_PropertyChanged; + TimeItems.Add(item); + } + } + finally { inLoading_ = false; } + + SelectedTimeItem = TimeItems.FirstOrDefault(); + } + #endregion + + #region Hilfsfunktionen + private void TimeItems_CollectionChanged(object sender, System.Collections.Specialized.NotifyCollectionChangedEventArgs e) + { + if (e.Action == System.Collections.Specialized.NotifyCollectionChangedAction.Add) + { + foreach (ITimeItem item in e.NewItems) + Provider.ElementAdded(item); + } + else if (e.Action == System.Collections.Specialized.NotifyCollectionChangedAction.Remove) + { + foreach (ITimeItem item in e.OldItems) + Provider.ElementRemoved(item); + } + } + + private void Item_PropertyChanged(object sender, System.ComponentModel.PropertyChangedEventArgs e) + { + Provider.ElementChanged((ITimeItem)sender); + } + #endregion + } +}