using System; using System.Collections.Generic; using System.ComponentModel; using System.IO; using System.Linq; using System.Windows.Media; using System.Xml; using BeWo.Scheduler.Resources; using BeWo.Scheduler.View; using BeWo.ServiceProxy; using BeWo.ViewModel.ListViewModel; using BS.Shared; using BS.Shared.DataContracts; using BS.Shared.DataContracts.Compact; using DevExpress.Xpf.Scheduler; using DevExpress.XtraScheduler; namespace BeWo.Scheduler.ViewModel { public class ResourceAppointmentListVM : AbstractDCListMapperVM, ISchedulerViewModel { private IList mAppointmentCategoryList; private IList mAppointmentResourceList; public IList Categories { get; private set; } public IList Resources { get; private set; } public Dictionary>> ChangedOccurencyCustomFields { get { return changedOccurencyCustomFields; } private set { changedOccurencyCustomFields = value; } } public object SelectedFilterObject { get; set; } private readonly Dictionary> mCategories2Resources; private readonly List mAllEmployees; private BindingList mAppointmentList; public BindingList Appointments { get { if (mAppointmentList == null) { mAppointmentList = new BindingList(VMList.ToList()); mAppointmentList.AddingNew += mAppointmentList_AddingNew; } return mAppointmentList; } } private Dictionary oid2Category; private Dictionary catOid2Index; private Dictionary>> changedOccurencyCustomFields; private static void mAppointmentList_AddingNew(object sender, AddingNewEventArgs e) { var dc = new ResourceAppointmentDC {Status = 0}; ServiceFacade.DoEmployeeServiceSync(a => dc.Employee = a.LoadCompactEmployee(BeWoApp.LoggedOnEmployee.EmployeeOid.Value)); e.NewObject = new ResourceAppointmentVM(dc); } public ResourceAppointmentListVM(Dictionary> lCategoriesToResources, List allemps, IEnumerable appList) : base(appList) { mCategories2Resources = lCategoriesToResources; mAllEmployees = allemps; InitViewModel(); InitChangedOccurrencyCustomFields(appList.Where(t => t.Type == 3).ToList()); } private void InitViewModel() { oid2Category = new Dictionary(); catOid2Index = new Dictionary(); mAppointmentCategoryList = new List(); mAppointmentResourceList = new List(); var index = 0; foreach (var category in mCategories2Resources.Keys) { foreach (var item in mCategories2Resources[category]) { var solidColorBrush = (SolidColorBrush)new BrushConverter().ConvertFrom(item.Color); var color = solidColorBrush == null ? Color.FromArgb(255, 4, 180, 208) : solidColorBrush.Color; var cat = new BeWoAppointmentCategory { CategoryObject = item, Color = color, DisplayName = item.Name, MenuCaption = item.Name }; if (item.ResourceOid.HasValue && !oid2Category.ContainsKey(item.ResourceOid.Value)) oid2Category.Add(item.ResourceOid.Value, cat); mAppointmentCategoryList.Add(cat); if (item.ResourceOid.HasValue && !catOid2Index.ContainsKey(item.ResourceOid.Value)) catOid2Index.Add(item.ResourceOid.Value, index); index++; } } Categories = mAppointmentCategoryList; foreach (var item in VMList) { if (item.Resource != null && item.Resource.ResourceOid != null) { item.CustomFields.Add("BeWoResourceOid", item.Resource.ResourceOid.Value); item.CustomFields.Add("Employee", item.Employee); if (item.Resource != null && oid2Category.ContainsKey(item.Resource.ResourceOid.Value)) item.AppointmentCategory = oid2Category[item.Resource.ResourceOid.Value]; item.LabelId = catOid2Index[item.Resource.ResourceOid.Value]; } } ((List)mAppointmentResourceList).Sort((a, b) => a.Caption.CompareTo(b.Caption)); } public SchedulerSettings GetDefaultSchedulerSettings() { var settings = new SchedulerSettings(AppointmentKind.Resource, AppointmentViewType.WorkWeek); return settings; } public void SaveAppointments(SchedulerControl control, IEnumerable list) { var sindGleich = false; var dcList = new List(); foreach (var item in list) { var vm = item.GetSourceObject(control.GetCoreStorage()) as ResourceAppointmentVM; if (vm == null) continue; UpdateResourceAppointment(item, vm); if(item.Type.Equals(AppointmentType.ChangedOccurrence)) sindGleich = TermineSindGleich(geoeffneterTermin, item); if (!sindGleich) dcList.Add(vm.CommitToDataContract()); } if (dcList.Count <= 0) return; var erg = new List(); ServiceFacade.DoResourceServiceSync(r => erg = r.UpdateResourceAppointments(dcList)); UpdateViewModel(erg); } private void UpdateResourceAppointment(Appointment app, ResourceAppointmentVM vm) { vm.Employee = app.CustomFields["Employee"] as CompactEmployeeDC; if (mAppointmentCategoryList == null) return; foreach (var category in mAppointmentCategoryList) { var co = category.CategoryObject as ResourceDC; if (co == null) continue; if (!co.ResourceOid.HasValue || !co.ResourceOid.Equals(app.CustomFields["BeWoResourceOid"])) continue; vm.AppointmentCategory = category; break; } app.LabelId = catOid2Index.First(kvp => kvp.Key.Equals(((ResourceDC) vm.AppointmentCategory.CategoryObject).ResourceOid.Value)).Value; if(app.RecurrenceInfo != null) { var index = app.RecurrenceIndex.ToString(); var id = app.RecurrenceInfo.Id; if (changedOccurencyCustomFields.ContainsKey(app.RecurrenceInfo.Id) && changedOccurencyCustomFields[id].ContainsKey(index)) { if (app.Type.Equals(AppointmentType.ChangedOccurrence)) { app.CustomFields["Employee"] = changedOccurencyCustomFields[id][index]["Employee"]; app.CustomFields["BeWoResourceOid"] = changedOccurencyCustomFields[id][index]["BeWoResourceOid"]; } } } if (vm.AppointmentCategory != null && vm.AppointmentCategory.CategoryObject is ResourceDC) vm.Resource = vm.AppointmentCategory.CategoryObject as ResourceDC; } public void ApplyChangesToChangedOccurencyCustomFields(CompactEmployeeDC employee, long? beWoResourceOid, string index, Guid id) { if (!changedOccurencyCustomFields.ContainsKey(id) || !changedOccurencyCustomFields[id].ContainsKey(index)) return; changedOccurencyCustomFields[id][index]["Employee"] = employee; changedOccurencyCustomFields[id][index]["BeWoResourceOid"] = beWoResourceOid; } private void UpdateViewModel(IEnumerable updatedDCList) { foreach (var dc in updatedDCList) { ResourceAppointmentVM found = null; foreach (var ivm in Appointments) { var vm = ivm as ResourceAppointmentVM; if (vm != null && vm.DataContract.Equals(dc)) found = vm; } if (found != null) found.DataContract = dc; } } public void DeleteAppointments(SchedulerControl control, IEnumerable list) { var dcList = list.Select(item => item.GetSourceObject(control.GetCoreStorage())).OfType().Select(vm => vm.CommitToDataContract()).Where(dc => dc.ResourceAppointmentOid.HasValue).ToList(); var idList = (from item in dcList where item.ResourceAppointmentOid.HasValue select item.ResourceAppointmentOid.Value).ToList(); ServiceFacade.DoResourceServiceSync(s=> dcList = s.GetResourceAppointmentsById(idList)); if (dcList.Count <= 0) return; var wörterbuch = dcList.ToDictionary(dc => dc.ResourceAppointmentOid != null ? dc.ResourceAppointmentOid.Value : 0, dc => dc.ResourceAppointmentVersion != null ? dc.ResourceAppointmentVersion.Value : 0); ServiceFacade.DoResourceServiceAsync(s => s.DeleteResourceAppointments(wörterbuch)); } public void InsertNewAppointments(SchedulerControl control, IEnumerable list) { var dcList = new List(); foreach (var item in list) { var vm = item.GetSourceObject(control.GetCoreStorage()) as ResourceAppointmentVM; if (vm == null) continue; UpdateResourceAppointment(item, vm); dcList.Add(vm.CommitToDataContract()); } if (dcList.Count > 0) { var liste = new List(); ServiceFacade.DoResourceServiceSync(r => liste = r.InsertNewResourceAppointments(dcList)); UpdateViewModel(liste); } } private Appointment geoeffneterTermin; AbstractAppointmentEditForm ISchedulerViewModel.GetEditAppointmentForm(SchedulerControl control, Appointment appointment) { geoeffneterTermin = control.Storage.CreateAppointment(AppointmentType.Normal); geoeffneterTermin.AllDay = appointment.AllDay; geoeffneterTermin.Start = appointment.Start; geoeffneterTermin.End = appointment.End; geoeffneterTermin.Description = appointment.Description; geoeffneterTermin.CustomFields["Employee"] = appointment.CustomFields["Employee"]; geoeffneterTermin.CustomFields["BeWoResourceOid"] = appointment.CustomFields["BeWoResourceOid"]; if (!appointment.Type.Equals(AppointmentType.ChangedOccurrence)) return new ResourceAppointmentEditForm(this, control, appointment, mAllEmployees, mCategories2Resources, SelectedFilterObject); var index = appointment.RecurrenceIndex; var id = appointment.RecurrenceInfo.Id; if (changedOccurencyCustomFields.ContainsKey(id) && changedOccurencyCustomFields[id].ContainsKey(index.ToString())) { var specialCustomFields = changedOccurencyCustomFields[id][index.ToString()]; appointment.CustomFields["Employee"] = specialCustomFields["Employee"]; appointment.CustomFields["BeWoResourceOid"] = specialCustomFields["BeWoResourceOid"]; geoeffneterTermin.CustomFields["Employee"] = specialCustomFields["Employee"]; geoeffneterTermin.CustomFields["BeWoResourceOid"] = specialCustomFields["BeWoResourceOid"]; } return new ResourceAppointmentEditForm(this, control, appointment, mAllEmployees, mCategories2Resources, SelectedFilterObject); } private static bool TermineSindGleich(Appointment eins, Appointment zwei) { // Die Appointments sind irgendwie nie gleich... if (eins == null || zwei == null) return false; return eins.Description == zwei.Description && eins.AllDay == zwei.AllDay && eins.Start == zwei.Start && eins.End == zwei.End && eins.CustomFields["Employee"] == zwei.CustomFields["Employee"] && eins.CustomFields["BeWoResourceOid"] == zwei.CustomFields["BeWoResourceOid"]; } public void AddCustomFieldsMapping(SchedulerStorage schedulerStorage) { var bewoResourceOidMapping = new SchedulerCustomFieldMapping("BeWoResourceOid", "BeWoResourceOid"); var employeeMapping = new SchedulerCustomFieldMapping("Employee", "Employee"); schedulerStorage.AppointmentStorage.CustomFieldMappings.Add(bewoResourceOidMapping); schedulerStorage.AppointmentStorage.CustomFieldMappings.Add(employeeMapping); } public void InitNewAppointment(Appointment appointment) { appointment.CustomFields["BeWoResourceOid"] = null; ServiceFacade.DoEmployeeServiceSync(s => appointment.CustomFields["Employee"] = s.LoadCompactEmployee(BeWoApp.LoggedOnEmployee.EmployeeOid.Value)); appointment.StatusId = 0; } public bool FilterAppointment(string filterCategory, object selectedObject, Appointment appointment, TimeInterval interval = null) { var selectedObjectType = selectedObject == null ? null : selectedObject.GetType(); var result = false; SelectedFilterObject = selectedObject; if (selectedObjectType == typeof(CompactEmployeeDC)) { result = !(appointment.CustomFields["Employee"] != null && appointment.CustomFields["Employee"].Equals(selectedObject as CompactEmployeeDC)); } if (selectedObjectType == typeof(ResourceDC)) { var obj = selectedObject as ResourceDC; result = !(obj != null && appointment.CustomFields["BeWoResourceOid"] != null && appointment.CustomFields["BeWoResourceOid"].Equals(obj.ResourceOid)); } if (selectedObjectType == typeof(ValueListEntryDC)) { var obj = selectedObject as ValueListEntryDC; result = !(appointment.CustomFields["BeWoResourceOid"] != null && obj != null && mCategories2Resources[obj].Any(a => a.ResourceOid.Equals(appointment.CustomFields["BeWoResourceOid"]))); } // false => alle werden angezeigt return result; } public void InitChangedOccurrencyCustomFields(IEnumerable appList) where T : IDataContract { var liste = (List) appList; changedOccurencyCustomFields = new Dictionary>>(); foreach (var termin in liste) { var ri = new RecurrenceInfo(); ri.FromXml(termin.RecurrenceInfo); var index = string.Empty; using (var reader = XmlReader.Create(new StringReader(termin.RecurrenceInfo))) { reader.ReadToFollowing("RecurrenceInfo"); reader.MoveToAttribute("Index"); index = reader.Value; } if (index.Equals("")) index = "0"; var customFieldCollection = new Dictionary(); customFieldCollection["Employee"] = termin.Employee; customFieldCollection["BeWoResourceOid"] = termin.Resource.ResourceOid; if (!changedOccurencyCustomFields.ContainsKey(ri.Id)) changedOccurencyCustomFields.Add(ri.Id, new Dictionary> { { index, customFieldCollection } }); else if (!changedOccurencyCustomFields[ri.Id].ContainsKey(index)) changedOccurencyCustomFields[ri.Id].Add(index, customFieldCollection); else changedOccurencyCustomFields[ri.Id][index] = customFieldCollection; } } } }