MoK-Kalender weitergemacht

This commit is contained in:
2026-06-29 13:45:15 +02:00
parent 95bf29a901
commit c25af9c053
45 changed files with 2059 additions and 777 deletions

View File

@@ -1595,7 +1595,9 @@ namespace BeWo.Scheduler.View
private void AllowAppointmentCreateEvent(object sender, AppointmentOperationEventArgs e) private void AllowAppointmentCreateEvent(object sender, AppointmentOperationEventArgs e)
{ {
e.Allow = BeWoApp.LoggedOnUser.HasRight(UserRightType.KalenderAnsehen) || BeWoApp.LoggedOnUser.HasRight(UserRightType.KalenderKliententermineAnlegen) || BeWoApp.LoggedOnUser.HasRight(UserRightType.KalenderMitarbeitertermineAnlegen); e.Allow = BeWoApp.LoggedOnUser.HasRight(UserRightType.KalenderAnsehen) ||
BeWoApp.LoggedOnUser.HasRight(UserRightType.KalenderKliententermineAnlegen) ||
BeWoApp.LoggedOnUser.HasRight(UserRightType.KalenderMitarbeitertermineAnlegen);
} }
private void UpdateOptionPanel() private void UpdateOptionPanel()
@@ -1733,9 +1735,9 @@ namespace BeWo.Scheduler.View
} }
var empList = customFieldStorage.EmployeeList; var empList = customFieldStorage.EmployeeList;
var or = customFieldStorage.Originator; var originator = customFieldStorage.Originator;
return or.EmployeeOid.Equals(BeWoApp.LoggedOnEmployee.EmployeeOid) && empList.Any(a => a.IsPChanged && a.ParticipationAnswer != ParticipationAnswer.Offen && a.ParticipationAnswer != ParticipationAnswer.Verstrichen && !a.Employee.EmployeeOid.Equals(BeWoApp.LoggedOnEmployee.EmployeeOid)); return originator.EmployeeOid.Equals(BeWoApp.LoggedOnEmployee.EmployeeOid) && empList.Any(employee2AppointmentRelation => employee2AppointmentRelation.IsPChanged && employee2AppointmentRelation.ParticipationAnswer != ParticipationAnswer.Offen && employee2AppointmentRelation.ParticipationAnswer != ParticipationAnswer.Verstrichen && !employee2AppointmentRelation.Employee.EmployeeOid.Equals(BeWoApp.LoggedOnEmployee.EmployeeOid));
}).ToList(); }).ToList();
} }
@@ -2176,7 +2178,7 @@ namespace BeWo.Scheduler.View
{ {
if(service.IsDataRefreshAllowed) if(service.IsDataRefreshAllowed)
{ {
GetCacheObjects((c, e, r) => GetCacheObjects((customers, employees, resources) =>
{ {
ServiceFacade.DoResourceServiceAsync(s2 => s2.LoadFilteredAppointmentsMitAufgaben( ServiceFacade.DoResourceServiceAsync(s2 => s2.LoadFilteredAppointmentsMitAufgaben(
BeWoApp.HasLoggedOnUserRight(new[] BeWoApp.HasLoggedOnUserRight(new[]
@@ -2218,11 +2220,11 @@ namespace BeWo.Scheduler.View
prefilteredAppointments = prefilteredAppointments.Where(app => !app.IsTask).ToList(); prefilteredAppointments = prefilteredAppointments.Where(app => !app.IsTask).ToList();
} }
var vm = new SchedulerAppointmentListVM(prefilteredAppointments, c, e, r); var vm = new SchedulerAppointmentListVM(prefilteredAppointments, customers, employees, resources);
if(pShouldShowAbsenceTimes) if(pShouldShowAbsenceTimes)
{ {
vm.Appointments.AddRange(ViewModel.ConvertAbsenceTimesToAppointments(customerAbsenceTimes, end, e, c)); vm.Appointments.AddRange(ViewModel.ConvertAbsenceTimesToAppointments(customerAbsenceTimes, end, employees, customers));
vm.Appointments.AddRange(ViewModel.ConvertAbsenceTimesToAppointments(employeeAbsenceTimes, end, e, c)); vm.Appointments.AddRange(ViewModel.ConvertAbsenceTimesToAppointments(employeeAbsenceTimes, end, employees, customers));
//vm.Appointments.AddRange(ViewModel.ConvertAbsenceTimesToAppointments(employeeAbsenceTimes.Where(w => { return SelectedEmployees.Count == 0 || SelectedEmployees.Any(a => a.EmployeeOid == w.EmployeeOid); }), end, e, c)); //vm.Appointments.AddRange(ViewModel.ConvertAbsenceTimesToAppointments(employeeAbsenceTimes.Where(w => { return SelectedEmployees.Count == 0 || SelectedEmployees.Any(a => a.EmployeeOid == w.EmployeeOid); }), end, e, c));
} }

View File

@@ -325,6 +325,7 @@
<Compile Include="Models\AppointmentModel.cs" /> <Compile Include="Models\AppointmentModel.cs" />
<Compile Include="Models\AppointmentSessionModel.cs" /> <Compile Include="Models\AppointmentSessionModel.cs" />
<Compile Include="Models\DevExpressSchedulerSessionModel.cs" /> <Compile Include="Models\DevExpressSchedulerSessionModel.cs" />
<Compile Include="Models\DevToolsSessionModel.cs" />
<Compile Include="Models\EmployeeModel.cs" /> <Compile Include="Models\EmployeeModel.cs" />
<Compile Include="Models\EmployeeSessionModel.cs" /> <Compile Include="Models\EmployeeSessionModel.cs" />
<Compile Include="Models\IAbsenceTimeModel.cs" /> <Compile Include="Models\IAbsenceTimeModel.cs" />
@@ -406,6 +407,9 @@
<Compile Include="Util\Umfeldsperson.cs" /> <Compile Include="Util\Umfeldsperson.cs" />
<Compile Include="Util\ValidationResult.cs" /> <Compile Include="Util\ValidationResult.cs" />
<Compile Include="Util\Watermarker.cs" /> <Compile Include="Util\Watermarker.cs" />
<Compile Include="Views\DevExpressScheduler\CustomerInfoObject.cs" />
<Compile Include="Views\DevExpressScheduler\ParticipationInfoObject.cs" />
<Compile Include="Views\DevExpressScheduler\ResourceInfoObject.cs" />
<Compile Include="Views\DevExpressScheduler\SchedulerHelper.cs" /> <Compile Include="Views\DevExpressScheduler\SchedulerHelper.cs" />
</ItemGroup> </ItemGroup>
<ItemGroup> <ItemGroup>
@@ -713,9 +717,6 @@
<Content Include="Views\Shared\AbsenceTimeFormPartial.cshtml" /> <Content Include="Views\Shared\AbsenceTimeFormPartial.cshtml" />
<Content Include="Views\Shared\AbsenceTimePartial.cshtml" /> <Content Include="Views\Shared\AbsenceTimePartial.cshtml" />
<Content Include="Views\DevExpressScheduler\CustomAppointmentFormPartial.cshtml" /> <Content Include="Views\DevExpressScheduler\CustomAppointmentFormPartial.cshtml" />
<Content Include="Views\DevExpressScheduler\CustomerMultiSelectPartial.cshtml" />
<Content Include="Views\DevExpressScheduler\ResourceMultiSelectPartial.cshtml" />
<Content Include="Views\DevExpressScheduler\EmployeeMultiSelectPartial.cshtml" />
<Content Include="Views\DevExpressScheduler\VerticalAppointmentTemplatePartial.cshtml" /> <Content Include="Views\DevExpressScheduler\VerticalAppointmentTemplatePartial.cshtml" />
<Content Include="Views\DevExpressScheduler\HorizontalAppointmentTemplatePartial.cshtml" /> <Content Include="Views\DevExpressScheduler\HorizontalAppointmentTemplatePartial.cshtml" />
<Content Include="Views\DevExpressScheduler\AptFltEmployeesPartial.cshtml" /> <Content Include="Views\DevExpressScheduler\AptFltEmployeesPartial.cshtml" />
@@ -725,11 +726,16 @@
<Content Include="Views\DevExpressScheduler\AptFltCustomerPopupListPartial.cshtml" /> <Content Include="Views\DevExpressScheduler\AptFltCustomerPopupListPartial.cshtml" />
<Content Include="Views\DevExpressScheduler\AptFltResourcePopupListPartial.cshtml" /> <Content Include="Views\DevExpressScheduler\AptFltResourcePopupListPartial.cshtml" />
<Content Include="Views\DevExpressScheduler\SchedulerNotificationPartial.cshtml" /> <Content Include="Views\DevExpressScheduler\SchedulerNotificationPartial.cshtml" />
<Content Include="Views\DevExpressScheduler\NotificationPopupContent.cshtml" /> <Content Include="Views\DevExpressScheduler\SelectedOpenEmployee2AppointmentFormPartial.cshtml" />
<Content Include="Views\DevExpressScheduler\NotificationsPopupContent.cshtml" /> <Content Include="Views\DevExpressScheduler\NotificationsPopupContent.cshtml" />
<Content Include="Views\DevExpressScheduler\CustomEmployeeSelectPartial.cshtml" /> <Content Include="Views\DevExpressScheduler\CustomEmployeeSelectPartial.cshtml" />
<Content Include="Views\DevExpressScheduler\CustomCustomerSelectPartial.cshtml" /> <Content Include="Views\DevExpressScheduler\CustomCustomerSelectPartial.cshtml" />
<Content Include="Views\DevExpressScheduler\CustomResourceSelectPartial.cshtml" /> <Content Include="Views\DevExpressScheduler\CustomResourceSelectPartial.cshtml" />
<Content Include="Views\DevExpressScheduler\OpenEmployee2AppointmentListPartial.cshtml" />
<Content Include="Views\DevExpressScheduler\NotificationsLinkPartial.cshtml" />
<Content Include="Views\DevExpressScheduler\CustomAppointmentToolTipPartial.cshtml" />
<Content Include="Views\DevExpressScheduler\CustomAppointmentDragToolTip.cshtml" />
<Content Include="Views\DevExpressScheduler\CustomSelectionToolTip.cshtml" />
</ItemGroup> </ItemGroup>
<ItemGroup> <ItemGroup>
<Content Include="packages.config" /> <Content Include="packages.config" />

View File

@@ -28,8 +28,7 @@
<VisualStudio> <VisualStudio>
<FlavorProperties GUID="{349c5851-65df-11da-9384-00065b846f21}"> <FlavorProperties GUID="{349c5851-65df-11da-9384-00065b846f21}">
<WebProjectProperties> <WebProjectProperties>
<StartPageUrl> <StartPageUrl>Views/Main/Main.cshtml</StartPageUrl>
</StartPageUrl>
<StartAction>CurrentPage</StartAction> <StartAction>CurrentPage</StartAction>
<AspNetDebugging>True</AspNetDebugging> <AspNetDebugging>True</AspNetDebugging>
<SilverlightDebugging>False</SilverlightDebugging> <SilverlightDebugging>False</SilverlightDebugging>

View File

@@ -16,15 +16,13 @@ using System;
using System.Collections.Generic; using System.Collections.Generic;
using System.Linq; using System.Linq;
using System.Web.Mvc; using System.Web.Mvc;
using CompactCustomerDC = BS.Shared.DataContracts.Compact.CompactCustomerDC;
namespace BeWoPlanerMobil.Controllers namespace BeWoPlanerMobil.Controllers
{ {
/* /*
* ToDo: * ToDo:
* 1. Filterung einbauen (Mitarbeiter, Klienten, Ressourcen, Privat, Aufgaben, Abwesenheiten) * Übersetzungen
* 2. Benachrichtigungen einbauen
* 3. Rechte implementieren
* 4. Übersetzungen
*/ */
public class DevExpressSchedulerController : AbstractBaseController public class DevExpressSchedulerController : AbstractBaseController
@@ -118,6 +116,7 @@ namespace BeWoPlanerMobil.Controllers
Model.SelectedEmployeeOidsForFiltering = new List<long> { employeeOid }; Model.SelectedEmployeeOidsForFiltering = new List<long> { employeeOid };
} }
// Nach den Kalenderrechten filtern!
Model.PossibleEmployees = EmployeeService.GetAllAuthorizedCompactEmployees(); Model.PossibleEmployees = EmployeeService.GetAllAuthorizedCompactEmployees();
Model.PossibleCustomers = CustomerService.GetAllAuthorizedCompactCustomers(); Model.PossibleCustomers = CustomerService.GetAllAuthorizedCompactCustomers();
Model.PossibleResources = KalenderService.GetAllResources(); Model.PossibleResources = KalenderService.GetAllResources();
@@ -165,12 +164,14 @@ namespace BeWoPlanerMobil.Controllers
var employeeOid = user.Employee.EmployeeOid; var employeeOid = user.Employee.EmployeeOid;
var userSettings = user.Settings.FirstOrDefault(f => f.Type.Equals(SettingsType.ApplicationSettings))?.Value; var userSettings = user.Settings.FirstOrDefault(f => f.Type.Equals(SettingsType.ApplicationSettings))?.Value;
var relatedCustomerOids = user.Employee.RelatedCustomerOIDList;
Model.CurrentViewType = (SchedulerViewType) UserSettingsUtils.GetSettingValueAsInteger(userSettings, SettingsKeys.SchedulerViewType); Model.CurrentViewType = (SchedulerViewType) UserSettingsUtils.GetSettingValueAsInteger(userSettings, SettingsKeys.SchedulerViewType);
var intervalStart = DateTimeExtensions.GetDayOfWeek(DayOfWeek.Monday); var intervalStart = DateTimeExtensions.GetDayOfWeek(DayOfWeek.Monday);
var intervalEnd = intervalStart.AddDays(7); var intervalEnd = intervalStart.AddDays(7);
var appointments = KalenderService.LoadFilteredAppointmentsMitAufgaben var allAppointments = KalenderService.LoadFilteredAppointmentsMitAufgaben
( (
Model.HasRightKalenderMitarbeitertermineAnsehen, Model.HasRightKalenderMitarbeitertermineAnsehen,
employeeOid, employeeOid,
@@ -187,11 +188,83 @@ namespace BeWoPlanerMobil.Controllers
Model.ShowTasks Model.ShowTasks
); );
var allCustomerOids = Model.PossibleCustomers.Select(s => s.CustomerOid).ToList(); var appointments = allAppointments;
var allEmployeeOids = Model.PossibleEmployees.Select(s => s.EmployeeOid).ToList();
var customerAbsenceTimes = KalenderService.GetAllActiveCustomersAbsenceTimesInInterval(intervalStart, intervalEnd, employeeOid, allCustomerOids); foreach(var appointment in appointments)
var employeeAbsenceTimes = KalenderService.GetAllActiveEmployeeAbsenceTimesInInterval(intervalStart, intervalEnd, employeeOid, allEmployeeOids); {
if(false == appointment.IsPrivate || appointment.Originator.EmployeeOid.Equals(employeeOid) || appointment.EmployeeList.Any(e => e.Employee.EmployeeOid.Equals(employeeOid)))
{
continue;
}
appointment.Description = "Privater Termin";
appointment.Subject = $"Privat ({appointment.Originator})";
appointment.CanBeDeleted = false;
appointment.CanBeEdited = false;
appointment.CanBeViewed = false;
}
// Den Rechten entsprechend filtern
if(Model.HasRightKalenderKliententermineAnsehen is false)
{
var relatedCustomers = Model.LoggedInEmployee.RelatedCustomers.Select(s => s.Customer);
var filteredAppointments = new List<SchedulerAppointmentDC>();
// Nur die der eigenen Klienten nicht filtern?
appointments = appointments.Where(appointment =>
appointment.IsTask is false &&
appointment.IsAbsenceTime is false &&
appointment.CustomerList.Any(customer => relatedCustomers.Contains(customer)) ||
appointment.CustomerList.Count == 0
).ToList();
foreach(var appointment in appointments)
{
if(appointment.CustomerList.Any() && false == appointment.CustomerList.Any(customer => relatedCustomers.Contains(customer)))
{
continue;
}
filteredAppointments.Add(appointment);
}
appointments = filteredAppointments;
}
if(Model.HasRightKalenderMitarbeitertermineAnsehen is false)
{
appointments = appointments.Where(appointment =>
appointment.IsTask is false &&
appointment.IsAbsenceTime is false &&
(appointment.Originator.Equals(Model.LoggedInCompactEmployee) ||appointment.EmployeeList.Any(employee2Appointment => employee2Appointment.Employee.Equals(Model.LoggedInCompactEmployee)))
).ToList();
}
if(Model.HasRightKalenderRessourcentermineAnsehen is false)
{
appointments = appointments.Where(appointment =>
appointment.IsTask is false &&
appointment.IsAbsenceTime is false &&
appointment.ResourceList.Count == 0
).ToList();
}
if(Model.ShowTasks is false)
{
appointments = appointments.Where(appointment => appointment.IsTask is false).ToList();
}
else
{
appointments.AddRangeIfElementsNotIn(allAppointments.Where(appointment => appointment.IsTask));
}
if(Model.ShowEmployeeColors)
{
appointments.DoForEach(appointment => appointment.ShowEmployeeColors = true);
}
var customerAbsenceTimes = KalenderService.GetAllActiveCustomersAbsenceTimesInInterval(intervalStart, intervalEnd, employeeOid, Model.SelectedCustomerOidsForFiltering);
var employeeAbsenceTimes = KalenderService.GetAllActiveEmployeeAbsenceTimesInInterval(intervalStart, intervalEnd, employeeOid, Model.SelectedEmployeeOidsForFiltering);
if(Model.ShowAbsenceTimes) if(Model.ShowAbsenceTimes)
{ {
@@ -202,6 +275,27 @@ namespace BeWoPlanerMobil.Controllers
appointments.AddRange(ConvertAbsenceTimesToAppointments(allAbsenceTimes, Model.PossibleCustomers, Model.PossibleEmployees)); appointments.AddRange(ConvertAbsenceTimesToAppointments(allAbsenceTimes, Model.PossibleCustomers, Model.PossibleEmployees));
} }
if(Model.HasRightKalenderRessourcenTermineAndererAendern is false)
{
appointments
.Where(appointment => appointment.Originator.Equals(Model.LoggedInCompactEmployee) is false && appointment.ResourceList.Any())
.DoForEach(appointment => appointment.CanBeEdited = false);
}
if(Model.HasRightKalenderKlientenTermineAendern is false)
{
appointments
.Where(appointment => appointment.Originator.Equals(Model.LoggedInCompactEmployee) is false && appointment.CustomerList.Any(customer => relatedCustomerOids.Contains(customer.CustomerOid) is false))
.DoForEach(appointment => appointment.CanBeEdited = false);
}
if(Model.HasRightKalenderMitarbeiterTermineAendern is false)
{
appointments
.Where(appointment => appointment.Originator.Equals(Model.LoggedInCompactEmployee) is false)
.DoForEach(appointment => appointment.CanBeEdited = false);
}
Model.Appointments = appointments; Model.Appointments = appointments;
LoadNotificationCount(); LoadNotificationCount();
@@ -217,23 +311,41 @@ namespace BeWoPlanerMobil.Controllers
private void LoadNotificationCount() private void LoadNotificationCount()
{ {
Model.OpenAppointments = KalenderService.GetAllOpenAppointmentsForEmployee(LoggedInUser.Employee.EmployeeOid).OrderByDescending(openAppointment => openAppointment.StartDate).ToList(); var openAppointments = KalenderService.GetAllOpenAppointmentsForEmployee(LoggedInUser.Employee.EmployeeOid).OrderBy(openAppointment => openAppointment.StartDate).ToList();
Model.OpenAppointmentOids = Model.OpenAppointments.Where(openAppointment => openAppointment.SchedulerAppointmentOid.HasValue).Select(openAppointment => openAppointment.SchedulerAppointmentOid.Value).ToList();
if(Model.AppointmentOid2Answer.HasValue)
{
Model.Appointment2Answer = Model.OpenAppointments.FirstOrDefault(openAppointment => openAppointment.SchedulerAppointmentOid?.Equals(Model.AppointmentOid2Answer.Value) ?? false);
}
else
{
var first = Model.OpenAppointments.FirstOrDefault();
if(first != null) var employee2Appointments = new List<Employee2SchedulerAppointmentDC>();
{
Model.Appointment2Answer = first; foreach(var appointment in openAppointments)
Model.AppointmentOid2Answer = first.SchedulerAppointmentOid; {
} // Termine, die von anderen Beantwortet wurden:
employee2Appointments.AddRangeIfElementsNotIn(appointment.EmployeeList.Where(e2a =>
appointment.Originator.Equals(Model.LoggedInCompactEmployee) &&
false == e2a.Employee.Equals(Model.LoggedInCompactEmployee) &&
e2a.IsPChanged &&
e2a.IsPC_CheckedTs is null &&
e2a.ParticipationAnswer != ParticipationAnswer.Offen &&
e2a.ParticipationAnswer != ParticipationAnswer.Verstrichen
));
// Termine zum Beantworten:
employee2Appointments.AddRangeIfElementsNotIn(appointment.EmployeeList.Where(e2A =>
false == appointment.Originator.Equals(Model.LoggedInCompactEmployee) &&
false == e2A.IsPChanged &&
e2A.Employee.Equals(Model.LoggedInCompactEmployee)
));
} }
Model.OpenEmployee2AppointmentRels = new List<Employee2SchedulerAppointmentDC>();
Model.OpenEmployee2AppointmentRelOids = new List<long>();
Model.OpenAppointments = openAppointments;
Model.OpenAppointmentOids = openAppointments
.Where(schedulerAppointment => schedulerAppointment.SchedulerAppointmentOid.HasValue)
.Select(schedulerAppointment => schedulerAppointment.SchedulerAppointmentOid.Value)
.ToList();
Model.OpenEmployee2AppointmentRels.AddRange(employee2Appointments);
Model.OpenEmployee2AppointmentRelOids = employee2Appointments.Where(w => w.Employee2SchedulerAppointmentOid.HasValue).Select(s => s.Employee2SchedulerAppointmentOid.Value).ToList();
} }
private List<SchedulerAppointmentDC> ConvertAbsenceTimesToAppointments(List<AbsenceTimeDC> absenceTimes, List<CompactCustomerDC> allCustomers, List<CompactEmployeeDC> allEmployees) private List<SchedulerAppointmentDC> ConvertAbsenceTimesToAppointments(List<AbsenceTimeDC> absenceTimes, List<CompactCustomerDC> allCustomers, List<CompactEmployeeDC> allEmployees)
@@ -356,10 +468,16 @@ namespace BeWoPlanerMobil.Controllers
{ {
appointment.CustomerList = AppointmentModel.SelectedCustomers; appointment.CustomerList = AppointmentModel.SelectedCustomers;
appointment.ResourceList = AppointmentModel.SelectedResources; appointment.ResourceList = AppointmentModel.SelectedResources;
appointment.EmployeeList = AppointmentModel.SelectedEmployee2SchedulerAppointments;
appointment.EmployeeList = new List<Employee2SchedulerAppointmentDC>();
foreach(var selectedEmployee in AppointmentModel.SelectedEmployees ?? new List<CompactEmployeeDC>())
{
appointment.EmployeeList.Add(new Employee2SchedulerAppointmentDC { Employee = selectedEmployee });
}
appointment.Originator = Model.LoggedInUser.Employee; appointment.Originator = Model.LoggedInUser.Employee;
KalenderService.InsertSchedulerAppointment(appointment); KalenderService.InsertSchedulerAppointment(appointment);
ViewData["EditableAppointmentModel"] = appointment; ViewData["EditableAppointmentModel"] = appointment;
} }
@@ -399,42 +517,6 @@ namespace BeWoPlanerMobil.Controllers
ReloadAppointments(); ReloadAppointments();
} }
//[HttpPost]
//public ActionResult CustomerMultiSelectPartial(string value)
//{
// var selectedCustomerOids = GridLookupExtension.GetSelectedValues<long?>("CustomerGridLookup") ?? Array.Empty<long?>();
// AppointmentModel.SelectedCustomerOids = selectedCustomerOids.Where(oid => oid.HasValue).Select(oid => oid.Value).ToList();
// return PartialView("CustomerMultiSelectPartial", AppointmentModel);
//}
//[HttpPost]
//public ActionResult ResourceGridLookupPartial(string value)
//{
// var selectedResourceOids = GridLookupExtension.GetSelectedValues<long?>("ResourceGridLookup") ?? Array.Empty<long?>();
// AppointmentModel.SelectedResourceOids = selectedResourceOids.Where(oid => oid.HasValue).Select(oid => oid.Value).ToList();
// return PartialView("ResourceMultiSelectPartial", AppointmentModel);
//}
//[HttpPost]
//public ActionResult EmployeeGridLookupPartial(string value)
//{
// /*
// * Im AppointmentModel müssen die PossibleEmployees bleiben, denn daraus wählt man die Mitarbeiter, die noch nicht mit dem Termin
// * verknüpft sind und es müssen - zumindest beim Bearbeiten - die bereits mit dem Termin verbundenen Mitarbeiter-zu-Termin-Relationen
// * zwischengespeichert werden.
// *
// */
// var selectedEmployeeOids = GridLookupExtension.GetSelectedValues<long?>("EmployeeGridLookup") ?? Array.Empty<long?>();
// AppointmentModel.SelectedEmployeeOids = selectedEmployeeOids.Where(oid => oid.HasValue).Select(oid => oid.Value).ToList();
// return PartialView("EmployeeMultiSelectPartial", AppointmentModel);
//}
[Authorize] [Authorize]
public string SelectActiveViewType(string viewTypeName) public string SelectActiveViewType(string viewTypeName)
{ {
@@ -467,11 +549,510 @@ namespace BeWoPlanerMobil.Controllers
case "Reload": case "Reload":
ReloadAppointments(); ReloadAppointments();
break; break;
case "debug_DummyAppointments":
CreateDummyAppointments();
break;
} }
return PartialView("SchedulerPagePartial", Model); return PartialView("SchedulerPagePartial", Model);
} }
private void CreateDummyAppointments()
{
var today = DateTime.Today;
var day1 = today;
var day2 = day1.AddDays(1);
switch(day2.DayOfWeek)
{
case DayOfWeek.Saturday:
day2 = day1.AddDays(-2); // Samstag -> Donnerstag
break;
case DayOfWeek.Sunday:
day2 = day1.AddDays(-3); // Sonntag -> Donnerstag
break;
}
var day3 = day2.AddDays(1);
switch(day3.DayOfWeek)
{
case DayOfWeek.Saturday:
day3 = day2.AddDays(-2); // Samstag -> Donnerstag
break;
case DayOfWeek.Sunday:
day3 = day2.AddDays(-3); // Sonntag -> Donnerstag
break;
}
var employees = EmployeeService.GetAllCompactEmployees();
var customers = CustomerService.GetAllCompactCustomers();
var resources = KalenderService.GetAllResources();
var ich = Model.LoggedInCompactEmployee;
var nichtIch = employees.First(employee => employee.EmployeeOid != ich.EmployeeOid);
var weiterer = employees.First(employee => employee.EmployeeOid != ich.EmployeeOid && employee.EmployeeOid != nichtIch.EmployeeOid);
var eigenerKlient = customers.FirstOrDefault(customer => ich.RelatedCustomerOIDList.Contains(customer.CustomerOid));
var fremderKlient = customers.FirstOrDefault(customer => ich.RelatedCustomerOIDList.Contains(customer.CustomerOid) is false);
var ressource = resources.FirstOrDefault();
var ressource2 = resources.Count > 1 ? resources[1] : ressource;
var nichtIchsKlient = customers.FirstOrDefault(customer => nichtIch.RelatedCustomerOIDList.Contains(customer.CustomerOid));
var nichtIchsFremderKlient = customers.FirstOrDefault(customer => nichtIch.RelatedCustomerOIDList.Contains(customer.CustomerOid) is false);
// 1a) Einfacher eigener Termin
var apt_1a = new SchedulerAppointmentDC
{
StartDate = day1.MergeDateWithHoursMinutesSeconds(8,0,0),
EndDate = day1.MergeDateWithHoursMinutesSeconds(9,0,0),
Subject = "Einfacher eigener Termin",
Location = "Datenbank",
Originator = ich,
Description = "Einfacher eigener Termin"
};
// 1b) mit Mitarbeiter
var apt_1b = new SchedulerAppointmentDC
{
StartDate = day1.MergeDateWithHoursMinutesSeconds(9, 0, 0),
EndDate = day1.MergeDateWithHoursMinutesSeconds(10, 0, 0),
Subject = "mit Mitarbeiter",
Location = "Datenbank",
Originator = ich,
Description = "mit Mitarbeiter",
EmployeeList = new List<Employee2SchedulerAppointmentDC>
{
new Employee2SchedulerAppointmentDC { Employee = nichtIch },
new Employee2SchedulerAppointmentDC { Employee = ich }
}
};
// 1c) mit eigenem Klient
var apt_1c = new SchedulerAppointmentDC
{
StartDate = day1.MergeDateWithHoursMinutesSeconds(10, 0, 0),
EndDate = day1.MergeDateWithHoursMinutesSeconds(11, 0, 0),
Subject = "mit eigenem Klient",
Location = "Datenbank",
Originator = ich,
Description = "mit eigenem Klient",
CustomerList = new List<CompactCustomerDC>{ eigenerKlient }
};
// 1d) mit fremdem Klient
var apt_1d = new SchedulerAppointmentDC
{
StartDate = day1.MergeDateWithHoursMinutesSeconds(11, 0, 0),
EndDate = day1.MergeDateWithHoursMinutesSeconds(12, 0, 0),
Subject = "mit fremdem Klient",
Location = "Datenbank",
Originator = ich,
Description = "mit fremdem Klient",
CustomerList = new List<CompactCustomerDC>{ fremderKlient }
};
// 1e) mit Ressource
var apt_1e = new SchedulerAppointmentDC
{
StartDate = day1.MergeDateWithHoursMinutesSeconds(12, 0, 0),
EndDate = day1.MergeDateWithHoursMinutesSeconds(13, 0, 0),
Subject = "mit Ressource",
Location = "Datenbank",
Originator = ich,
Description = "mit Ressource",
ResourceList = new List<ResourceDC>{ ressource }
};
// 1f) mit Mitarbeiter, eigenem Klient
var apt_1f = new SchedulerAppointmentDC
{
StartDate = day1.MergeDateWithHoursMinutesSeconds(13, 0, 0),
EndDate = day1.MergeDateWithHoursMinutesSeconds(14, 0, 0),
Subject = "mit Mitarbeiter, eigenem Klient",
Location = "Datenbank",
Originator = ich,
Description = "mit Mitarbeiter, eigenem Klient",
EmployeeList = new List<Employee2SchedulerAppointmentDC>
{
new Employee2SchedulerAppointmentDC { Employee = nichtIch },
new Employee2SchedulerAppointmentDC { Employee = ich }
},
CustomerList = new List<CompactCustomerDC> { eigenerKlient }
};
// 1g) mit Mitarbeiter, fremdem Klient
var apt_1g = new SchedulerAppointmentDC
{
StartDate = day1.MergeDateWithHoursMinutesSeconds(14, 0, 0),
EndDate = day1.MergeDateWithHoursMinutesSeconds(15, 0, 0),
Subject = "mit Mitarbeiter, fremdem Klient",
Location = "Datenbank",
Originator = ich,
Description = "mit Mitarbeiter, fremdem Klient",
EmployeeList = new List<Employee2SchedulerAppointmentDC>
{
new Employee2SchedulerAppointmentDC { Employee = nichtIch },
new Employee2SchedulerAppointmentDC { Employee = ich }
},
CustomerList = new List<CompactCustomerDC> { fremderKlient }
};
// 1h) mit eigenem Klient, Ressource
var apt_1h = new SchedulerAppointmentDC
{
StartDate = day1.MergeDateWithHoursMinutesSeconds(15, 0, 0),
EndDate = day1.MergeDateWithHoursMinutesSeconds(16, 0, 0),
Subject = "mit eigenem Klient, Ressource",
Location = "Datenbank",
Originator = ich,
Description = "mit eigenem Klient, Ressource",
CustomerList = new List<CompactCustomerDC> { eigenerKlient },
ResourceList = new List<ResourceDC> { ressource }
};
// 1i) mit fremdem Klient, Ressource
var apt_1i = new SchedulerAppointmentDC
{
StartDate = day1.MergeDateWithHoursMinutesSeconds(16, 0, 0),
EndDate = day1.MergeDateWithHoursMinutesSeconds(17, 0, 0),
Subject = "mit fremdem Klient, Ressource",
Location = "Datenbank",
Originator = ich,
Description = "mit fremdem Klient, Ressource",
CustomerList = new List<CompactCustomerDC> { fremderKlient },
ResourceList = new List<ResourceDC> { ressource }
};
// 1j) mit Mitarbeiter, eigenem Klient, Ressource
var apt_1j = new SchedulerAppointmentDC
{
StartDate = day1.MergeDateWithHoursMinutesSeconds(17, 0, 0),
EndDate = day1.MergeDateWithHoursMinutesSeconds(18, 0, 0),
Subject = "mit Mitarbeiter, eigenem Klient, Ressource",
Location = "Datenbank",
Originator = ich,
Description = "mit Mitarbeiter, eigenem Klient, Ressource",
EmployeeList = new List<Employee2SchedulerAppointmentDC>
{
new Employee2SchedulerAppointmentDC { Employee = nichtIch },
new Employee2SchedulerAppointmentDC { Employee = ich }
},
CustomerList = new List<CompactCustomerDC> { eigenerKlient },
ResourceList = new List<ResourceDC> { ressource }
};
// 1k) mit Mitarbeiter, fremdem Klient, Ressource
var apt_1k = new SchedulerAppointmentDC
{
StartDate = day1.MergeDateWithHoursMinutesSeconds(18, 0, 0),
EndDate = day1.MergeDateWithHoursMinutesSeconds(19, 0, 0),
Subject = "mit Mitarbeiter, fremdem Klient, Ressource",
Location = "Datenbank",
Originator = ich,
Description = "mit Mitarbeiter, fremdem Klient, Ressource",
EmployeeList = new List<Employee2SchedulerAppointmentDC>
{
new Employee2SchedulerAppointmentDC { Employee = nichtIch },
new Employee2SchedulerAppointmentDC { Employee = ich }
},
CustomerList = new List<CompactCustomerDC> { fremderKlient },
ResourceList = new List<ResourceDC> { ressource }
};
// -----------------------------------------------------------------------------
// 2a) einfach
var apt_2a = new SchedulerAppointmentDC
{
StartDate = day1.MergeDateWithHoursMinutesSeconds(19),
EndDate = day1.MergeDateWithHoursMinutesSeconds(20),
Subject = "einfach",
Location = "Datenbank",
Originator = nichtIch,
Description = "einfach"
};
// 2b) mit Mitarbeiter
var apt_2b = new SchedulerAppointmentDC
{
StartDate = day2.MergeDateWithHoursMinutesSeconds(8),
EndDate = day2.MergeDateWithHoursMinutesSeconds(9),
Subject = "mit Mitarbeiter",
Location = "Datenbank",
Description = "mit Mitarbeiter",
Originator = nichtIch,
EmployeeList = new List<Employee2SchedulerAppointmentDC>
{
new Employee2SchedulerAppointmentDC { Employee = nichtIch },
new Employee2SchedulerAppointmentDC { Employee = weiterer }
}
};
// 2c) mit angemeldetem Mitarbeiter
var apt_2c = new SchedulerAppointmentDC
{
StartDate = day2.MergeDateWithHoursMinutesSeconds(9),
EndDate = day2.MergeDateWithHoursMinutesSeconds(10),
Subject = "mit angemeldetem Mitarbeiter",
Location = "Datenbank",
Description = "mit angemeldetem Mitarbeiter",
Originator = nichtIch,
EmployeeList = new List<Employee2SchedulerAppointmentDC>
{
new Employee2SchedulerAppointmentDC { Employee = nichtIch },
new Employee2SchedulerAppointmentDC { Employee = ich }
}
};
// 2d) mit eigenem Klient
var apt_2d = new SchedulerAppointmentDC
{
StartDate = day2.MergeDateWithHoursMinutesSeconds(10),
EndDate = day2.MergeDateWithHoursMinutesSeconds(11),
Subject = "mit eigenem Klient",
Location = "Datenbank",
Description = "mit eigenem Klient",
Originator = nichtIch,
CustomerList = new List<CompactCustomerDC> { nichtIchsKlient }
};
// 2e) mit fremdem Klient
var apt_2e = new SchedulerAppointmentDC
{
StartDate = day2.MergeDateWithHoursMinutesSeconds(11),
EndDate = day2.MergeDateWithHoursMinutesSeconds(12),
Subject = "mit fremdem Klient",
Location = "Datenbank",
Description = "mit fremdem Klient",
Originator = nichtIch,
CustomerList = new List<CompactCustomerDC> { nichtIchsFremderKlient }
};
// 2f) mit Ressource
var apt_2f = new SchedulerAppointmentDC
{
StartDate = day2.MergeDateWithHoursMinutesSeconds(12),
EndDate = day2.MergeDateWithHoursMinutesSeconds(13),
Subject = "mit Ressource",
Location = "Datenbank",
Description = "mit Ressource",
Originator = nichtIch,
ResourceList = new List<ResourceDC>{ ressource2 }
};
// 2g) mit Mitarbeiter, eigenem Klient
var apt_2g = new SchedulerAppointmentDC
{
StartDate = day2.MergeDateWithHoursMinutesSeconds(13),
EndDate = day2.MergeDateWithHoursMinutesSeconds(14),
Subject = "mit Mitarbeiter, eigenem Klient",
Location = "Datenbank",
Description = "mit Mitarbeiter, eigenem Klient",
Originator = nichtIch,
EmployeeList = new List<Employee2SchedulerAppointmentDC>
{
new Employee2SchedulerAppointmentDC { Employee = nichtIch },
new Employee2SchedulerAppointmentDC { Employee = weiterer }
},
CustomerList = new List<CompactCustomerDC> { nichtIchsKlient }
};
// 2h) mit Mitarbeiter, fremdem Klient
var apt_2h = new SchedulerAppointmentDC
{
StartDate = day2.MergeDateWithHoursMinutesSeconds(14),
EndDate = day2.MergeDateWithHoursMinutesSeconds(15),
Subject = "mit Mitarbeiter, fremdem Klient",
Location = "Datenbank",
Description = "mit Mitarbeiter, fremdem Klient",
Originator = nichtIch,
EmployeeList = new List<Employee2SchedulerAppointmentDC>
{
new Employee2SchedulerAppointmentDC { Employee = nichtIch },
new Employee2SchedulerAppointmentDC { Employee = weiterer }
},
CustomerList = new List<CompactCustomerDC> { nichtIchsFremderKlient }
};
// 2i) mit eigenem Klient, Ressource
var apt_2i = new SchedulerAppointmentDC
{
StartDate = day2.MergeDateWithHoursMinutesSeconds(15),
EndDate = day2.MergeDateWithHoursMinutesSeconds(16),
Subject = "mit eigenem Klient, Ressource",
Location = "Datenbank",
Description = "mit eigenem Klient, Ressource",
Originator = nichtIch,
CustomerList = new List<CompactCustomerDC>{ nichtIchsKlient },
ResourceList = new List<ResourceDC>{ ressource2 }
};
// 2j) mit fremdem Klient, Ressource
var apt_2j = new SchedulerAppointmentDC
{
StartDate = day2.MergeDateWithHoursMinutesSeconds(16),
EndDate = day2.MergeDateWithHoursMinutesSeconds(17),
Subject = "mit fremdem Klient, Ressource",
Location = "Datenbank",
Description = "mit fremdem Klient, Ressource",
Originator = nichtIch,
CustomerList = new List<CompactCustomerDC> { nichtIchsFremderKlient },
ResourceList = new List<ResourceDC> { ressource2 }
};
// 2k) mit Mitarbeiter, eigenem Klient, Ressource
var apt_2k = new SchedulerAppointmentDC
{
StartDate = day2.MergeDateWithHoursMinutesSeconds(17),
EndDate = day2.MergeDateWithHoursMinutesSeconds(18),
Subject = "mit Mitarbeiter, eigenem Klient, Ressource",
Location = "Datenbank",
Description = "mit Mitarbeiter, eigenem Klient, Ressource",
Originator = nichtIch
};
// 2l) mit Mitarbeiter, fremdem Klient, Ressource
var apt_2l = new SchedulerAppointmentDC
{
StartDate = day2.MergeDateWithHoursMinutesSeconds(18),
EndDate = day2.MergeDateWithHoursMinutesSeconds(19),
Subject = "mit Mitarbeiter, fremdem Klient, Ressource",
Location = "Datenbank",
Description = "mit Mitarbeiter, fremdem Klient, Ressource",
Originator = nichtIch,
EmployeeList = new List<Employee2SchedulerAppointmentDC>
{
new Employee2SchedulerAppointmentDC { Employee = nichtIch },
new Employee2SchedulerAppointmentDC { Employee = weiterer }
},
CustomerList = new List<CompactCustomerDC> { nichtIchsFremderKlient },
ResourceList = new List<ResourceDC> { ressource2 }
};
// 2m) mit angemeldetem Mitarbeiter, dessen Klient
var apt_2m = new SchedulerAppointmentDC
{
StartDate = day2.MergeDateWithHoursMinutesSeconds(19),
EndDate = day2.MergeDateWithHoursMinutesSeconds(20),
Subject = "mit angemeldetem Mitarbeiter, dessen Klient",
Location = "Datenbank",
Description = "mit angemeldetem Mitarbeiter, dessen Klient",
Originator = nichtIch,
EmployeeList = new List<Employee2SchedulerAppointmentDC>
{
new Employee2SchedulerAppointmentDC { Employee = nichtIch },
new Employee2SchedulerAppointmentDC { Employee = ich }
},
CustomerList = new List<CompactCustomerDC> { eigenerKlient }
};
// 2n) mit angemeldetem Mitarbeiter, diesem fremdem Klient
var apt_2n = new SchedulerAppointmentDC
{
StartDate = day3.MergeDateWithHoursMinutesSeconds(8),
EndDate = day3.MergeDateWithHoursMinutesSeconds(9),
Subject = "mit angemeldetem Mitarbeiter, diesem fremdem Klient",
Location = "Datenbank",
Description = "mit angemeldetem Mitarbeiter, diesem fremdem Klient",
Originator = nichtIch,
EmployeeList = new List<Employee2SchedulerAppointmentDC>
{
new Employee2SchedulerAppointmentDC { Employee = nichtIch },
new Employee2SchedulerAppointmentDC { Employee = ich }
},
CustomerList = new List<CompactCustomerDC> { fremderKlient }
};
// 2o) mit angemeldetem Mitarbeiter, dessen Klient, Ressource
var apt_2o = new SchedulerAppointmentDC
{
StartDate = day3.MergeDateWithHoursMinutesSeconds(9),
EndDate = day3.MergeDateWithHoursMinutesSeconds(10),
Subject = "mit angemeldetem Mitarbeiter, dessen Klient, Ressource",
Location = "Datenbank",
Description = "mit angemeldetem Mitarbeiter, dessen Klient, Ressource",
Originator = nichtIch,
EmployeeList = new List<Employee2SchedulerAppointmentDC>
{
new Employee2SchedulerAppointmentDC { Employee = nichtIch },
new Employee2SchedulerAppointmentDC { Employee = ich }
},
CustomerList = new List<CompactCustomerDC> { eigenerKlient },
ResourceList = new List<ResourceDC>{ ressource }
};
// 2p) mit angemeldetem Mitarbeiter, diesem fremdem Klient, Ressource
var apt_2p = new SchedulerAppointmentDC
{
StartDate = day3.MergeDateWithHoursMinutesSeconds(10),
EndDate = day3.MergeDateWithHoursMinutesSeconds(11),
Subject = "mit angemeldetem Mitarbeiter, diesem fremdem Klient, Ressource",
Location = "Datenbank",
Description = "mit angemeldetem Mitarbeiter, diesem fremdem Klient, Ressource",
Originator = nichtIch,
EmployeeList = new List<Employee2SchedulerAppointmentDC>
{
new Employee2SchedulerAppointmentDC { Employee = nichtIch },
new Employee2SchedulerAppointmentDC { Employee = ich }
},
CustomerList = new List<CompactCustomerDC> { fremderKlient },
ResourceList = new List<ResourceDC> { ressource }
};
var appointmentsToInsert = new List<SchedulerAppointmentDC>
{
apt_1a,
apt_1b,
apt_1c,
apt_1d,
apt_1e,
apt_1f,
apt_1g,
apt_1h,
apt_1i,
apt_1j,
apt_1k,
apt_2a,
apt_2b,
apt_2c,
apt_2d,
apt_2e,
apt_2f,
apt_2g,
apt_2h,
apt_2i,
apt_2j,
apt_2k,
apt_2l,
apt_2m,
apt_2n,
apt_2o,
apt_2p
};
foreach(var appointment in appointmentsToInsert)
{
appointment.ActivationType = ActivationTypeId.Active;
}
KalenderService.InsertSchedulerAppointments(appointmentsToInsert);
ReloadAppointments();
}
[Authorize] [Authorize]
private ActionResult ToServiceRecord(string apptID, string actionId, string[] args) private ActionResult ToServiceRecord(string apptID, string actionId, string[] args)
{ {
@@ -783,62 +1364,129 @@ namespace BeWoPlanerMobil.Controllers
return PartialView("SchedulerPagePartial", Model); return PartialView("SchedulerPagePartial", Model);
} }
[Authorize]
public string UnselectAppointment2Answer()
{
Model.AppointmentOidToAnswerOrUpdate = null;
Model.AppointmentToAnswerOrUpdate = null;
return LeerzeichenFuerGetMethoden;
}
[Authorize] [Authorize]
public ActionResult LoadAppointmentToAnswer(long oid) public ActionResult LoadAppointmentToAnswer(long oid)
{ {
Model.Appointment2Answer = Model.OpenAppointments.FirstOrDefault(openAppointment => openAppointment.SchedulerAppointmentOid?.Equals(oid) ?? false); var relation = Model.OpenEmployee2AppointmentRels.FirstOrDefault(f => f.Employee2SchedulerAppointmentOid.HasValue && f.Employee2SchedulerAppointmentOid.Equals(oid));
return PartialView("NotificationPopupContent", Model); if(relation != null)
{
Model.Employee2AppointmentToAnswerOrUpdateRel = relation;
Model.Employee2AppointmentToAnswerOrUpdateRelOid = relation.Employee2SchedulerAppointmentOid;
var appointment = Model.OpenAppointments.FirstOrDefault(f => f.EmployeeList.Any(a => a.Employee2SchedulerAppointmentOid.Equals(relation.Employee2SchedulerAppointmentOid.Value)));
if(appointment != null)
{
Model.AppointmentToAnswerOrUpdate = appointment;
Model.AppointmentOidToAnswerOrUpdate = appointment.SchedulerAppointmentOid;
}
}
return PartialView("SelectedOpenEmployee2AppointmentFormPartial", Model);
} }
[Authorize] [Authorize]
public ActionResult AnswerOpenAppointment(int answer) public ActionResult AnswerOpenAppointment(int answer)
{ {
var appointment = Model.Appointment2Answer; var appointmentOid = Model.AppointmentOidToAnswerOrUpdate;
var relationOid = Model.Employee2AppointmentToAnswerOrUpdateRelOid;
var employeeRelation = appointment.EmployeeList.FirstOrDefault(employee2Appointment => employee2Appointment.Employee.EmployeeOid == Model.LoggedInUser.Employee.EmployeeOid); var appointment = Model.OpenAppointments.FirstOrDefault(f => f.SchedulerAppointmentOid.Equals(appointmentOid));
var relation = Model.OpenEmployee2AppointmentRels.FirstOrDefault(f => f.Employee2SchedulerAppointmentOid.Equals(relationOid));
if(employeeRelation != null) if(relation is null)
{ {
employeeRelation.ParticipationAnswer = (ParticipationAnswer) answer; throw new ArgumentNullException(nameof(relation), "Das Employee2NewSchedulerAppointmentDC-Objekt ist in der Funktion 'AnswerOpenAppointment' wider Erwarten null!");
employeeRelation.IsPChanged = true;
employeeRelation.IsPC_CheckedTs = DateTime.Now;
} }
KalenderService.UpdateSchedulerAppointments(new List<SchedulerAppointmentDC> { appointment }); if(appointment is null)
{
throw new ArgumentNullException(nameof(appointment), "Das SchedulerAppointmentDC-Objekt ist in der Funktion 'AnswerOpenAppointment' wider Erwarten null!");
}
Model.Appointment2Answer = null; if(answer == 5)
Model.AppointmentOid2Answer = null; {
relation.IsPC_CheckedTs = DateTime.Now;
}
else
{
var participationAnswer = (ParticipationAnswer) answer;
relation.ParticipationAnswer = participationAnswer;
relation.IsPChanged = true;
}
KalenderService.UpdateEmployee2SchedulerAppointments(new List<Employee2SchedulerAppointmentDC> { relation });
Model.AppointmentOidToAnswerOrUpdate = null;
Model.Employee2AppointmentToAnswerOrUpdateRelOid = null;
ReloadAppointments(); ReloadAppointments();
return PartialView("NotificationsPopupContent", Model); return PartialView("NotificationsPopupContent", Model);
} }
[Authorize]
public ActionResult ReloadOpenAppointments()
{
ReloadAppointments();
return PartialView("OpenEmployee2AppointmentListPartial", Model);
}
[Authorize] [Authorize]
public ActionResult ConfirmAllOpenAppointments() public ActionResult ConfirmAllOpenAppointments()
{ {
Model.OpenAppointments = KalenderService.GetAllOpenAppointmentsForEmployee(Model.LoggedInUser.Employee.EmployeeOid); var rels = Model.OpenEmployee2AppointmentRels;
foreach(var openAppointment in Model.OpenAppointments) var appointmentOids = rels
.Where(employee2Appointment => employee2Appointment.SchedulerAppointmentOid.HasValue)
.Select(employee2Appointment => employee2Appointment.SchedulerAppointmentOid.Value)
.ToList();
var appointments = Model.OpenAppointments.Where(appointment => appointment.SchedulerAppointmentOid.HasValue && appointmentOids.Contains(appointment.SchedulerAppointmentOid.Value)).ToList();
foreach(var appointment in appointments)
{ {
var employee2Appointment = openAppointment.EmployeeList.First(first => first.Employee.Equals(Model.LoggedInUser.Employee)); foreach(var employee2Appointment in appointment.EmployeeList)
{
employee2Appointment.ParticipationAnswer = openAppointment.EndDate is null || openAppointment.EndDate > DateTime.Now ? ParticipationAnswer.Zusage : ParticipationAnswer.Verstrichen; if(employee2Appointment.Employee.Equals(Model.LoggedInCompactEmployee))
employee2Appointment.IsPChanged = true; {
employee2Appointment.IsPC_CheckedTs = DateTime.Now; employee2Appointment.IsPChanged = true;
employee2Appointment.ParticipationAnswer = ParticipationAnswer.Zusage;
}
}
} }
KalenderService.UpdateSchedulerAppointments(Model.OpenAppointments); KalenderService.UpdateSchedulerAppointments(appointments);
Model.Appointment2Answer = null;
Model.AppointmentOid2Answer = null;
ReloadAppointments(); ReloadAppointments();
return PartialView("NotificationsPopupContent", Model); return PartialView("NotificationsPopupContent", Model);
} }
[Authorize]
public string GetOpenEmp2AppRelCount()
{
return JsonConvert.SerializeObject(Model.OpenEmployee2AppointmentRelOids.Count);
}
[Authorize]
public ActionResult UpdateOpenEmp2AppCount()
{
return PartialView("NotificationsLinkPartial", Model);
}
[Authorize] [Authorize]
public ActionResult RightClickConfirm(int answer, long id) public ActionResult RightClickConfirm(int answer, long id)
{ {
@@ -890,16 +1538,24 @@ namespace BeWoPlanerMobil.Controllers
var selectedEmployeeOids = selectedOids.Length == 0 ? new List<long>() : selectedOids.Split(',').Select(long.Parse).ToList(); var selectedEmployeeOids = selectedOids.Length == 0 ? new List<long>() : selectedOids.Split(',').Select(long.Parse).ToList();
AppointmentModel.SelectedEmployee2SchedulerAppointments = new List<Employee2SchedulerAppointmentDC>(); var relationsToKeep = AppointmentModel.SelectedEmployee2SchedulerAppointments?.Where(e2A => selectedEmployeeOids.Contains(e2A.Employee.EmployeeOid)).ToList() ?? new List<Employee2SchedulerAppointmentDC>();
var employees = AppointmentModel.PossibleEmployees.Where(possibleEmployee => selectedEmployeeOids.Contains(possibleEmployee.EmployeeOid)).ToList(); var newlySelectedEmployeeOids = selectedEmployeeOids.Except(relationsToKeep.Select(e2A => e2A.Employee.EmployeeOid));
AppointmentModel.SelectedEmployee2SchedulerAppointments = new List<Employee2SchedulerAppointmentDC>(relationsToKeep);
var oids = AppointmentModel.PossibleEmployees.Where(e => selectedEmployeeOids.Contains(e.EmployeeOid)).Select(e => e.EmployeeOid).ToList();
var employees = AppointmentModel.PossibleEmployees.Where(possibleEmployee => newlySelectedEmployeeOids.Contains(possibleEmployee.EmployeeOid)).ToList();
foreach(var employee in employees) foreach(var employee in employees)
{ {
AppointmentModel.SelectedEmployee2SchedulerAppointments.Add(new Employee2SchedulerAppointmentDC { Employee = employee }); AppointmentModel.SelectedEmployee2SchedulerAppointments.Add(new Employee2SchedulerAppointmentDC { Employee = employee });
} }
return LeerzeichenFuerGetMethoden; AppointmentModel.SelectedEmployeeOids = oids;
return JsonConvert.SerializeObject(AppointmentModel.SelectedEmployee2SchedulerAppointments?.Count ?? 0);
} }
[Authorize] [Authorize]
@@ -912,7 +1568,7 @@ namespace BeWoPlanerMobil.Controllers
AppointmentModel.SelectedCustomerOids = selectedOids.Length == 0 ? new List<long>() : selectedOids.Split(',').Select(long.Parse).ToList(); AppointmentModel.SelectedCustomerOids = selectedOids.Length == 0 ? new List<long>() : selectedOids.Split(',').Select(long.Parse).ToList();
return LeerzeichenFuerGetMethoden; return JsonConvert.SerializeObject(AppointmentModel.SelectedCustomerOids?.Count ?? 0);
} }
[Authorize] [Authorize]
@@ -925,7 +1581,7 @@ namespace BeWoPlanerMobil.Controllers
AppointmentModel.SelectedResourceOids = selectedOids.Length == 0 ? new List<long>() : selectedOids.Split(',').Select(long.Parse).ToList(); AppointmentModel.SelectedResourceOids = selectedOids.Length == 0 ? new List<long>() : selectedOids.Split(',').Select(long.Parse).ToList();
return LeerzeichenFuerGetMethoden; return JsonConvert.SerializeObject(AppointmentModel.SelectedResourceOids?.Count ?? 0);
} }
} }

View File

@@ -1,34 +1,75 @@
using System.Web.Mvc; using BeWoPlanerMobil.Models;
using BeWoPlanerMobil.Models;
using BeWoPlanerMobil.Service; using BeWoPlanerMobil.Service;
using Bogus; using Bogus;
using BS.Shared.Core;
using BS.Shared.DataContracts; using BS.Shared.DataContracts;
using System.Web.Mvc;
namespace BeWoPlanerMobil.Controllers namespace BeWoPlanerMobil.Controllers
{ {
public class DevToolsController : AbstractBaseController public class DevToolsController : AbstractBaseController
{ {
/*
private DevExpressSchedulerModel _Model;
public DevExpressSchedulerModel Model
{
get
{
if(false == MobileSessionFacade.IsUserLoggedIn())
{
Logout();
return null;
}
if(_Model != null)
{
return _Model;
}
_Model = new DevExpressSchedulerModel();
InitModel(_Model);
InitViewModel();
return _Model;
}
}
*/
private DevToolsModel _Model; private DevToolsModel _Model;
public DevToolsModel Model public DevToolsModel Model
{ {
get get
{ {
if(!MobileSessionFacade.IsUserLoggedIn()) if(MobileSessionFacade.IsUserLoggedIn() is false)
{ {
Logout(); Logout();
return null; return null;
} }
if(_Model is null) if(_Model != null)
{ {
_Model = new DevToolsModel(); return _Model;
InitModel(_Model);
} }
_Model = new DevToolsModel();
InitModel(_Model);
InitViewModel();
return _Model; return _Model;
} }
} }
public void InitViewModel()
{
Model.Employees = EmployeeService.GetAllCompactEmployees();
Model.Customers = CustomerService.GetAllCompactCustomers();
Model.Resources = KalenderService.GetAllResources();
var mandatorSettings = new MandatorSettings(Model.Mandator.Settings);
}
[Authorize] [Authorize]
public ActionResult DevTools() public ActionResult DevTools()
{ {

View File

@@ -264,7 +264,6 @@ namespace BeWoPlanerMobil.Controllers
Model.SelectedSupportConceptListObject = Model.SupportConceptListObjects.FirstOrDefault(f => f.CostBearer2SupportConceptOid == -1) ?? Model.SupportConceptListObjects.First(); Model.SelectedSupportConceptListObject = Model.SupportConceptListObjects.FirstOrDefault(f => f.CostBearer2SupportConceptOid == -1) ?? Model.SupportConceptListObjects.First();
Model.SelectedCostBearerSupportConceptOid = -1; Model.SelectedCostBearerSupportConceptOid = -1;
} }
else else
{ {
@@ -1667,7 +1666,6 @@ namespace BeWoPlanerMobil.Controllers
{ {
var sc = GetCompactSupportConcept(mokSupportConceptListObject.SupportConceptOid, selectedCostbearerScRelOid); var sc = GetCompactSupportConcept(mokSupportConceptListObject.SupportConceptOid, selectedCostbearerScRelOid);
Model.NewServiceRecord.SupportConcept = sc; Model.NewServiceRecord.SupportConcept = sc;
Model.NewServiceRecord.Customer = sc.Customer; Model.NewServiceRecord.Customer = sc.Customer;

View File

@@ -35,7 +35,7 @@ namespace BeWoPlanerMobil
XmlConfigurator.Configure(); XmlConfigurator.Configure();
} }
protected void Application_BeginRequest(object sender, EventArgs e) protected void Application_BeginRequest(object sender, EventArgs e)
{ {
ServicePointManager.SecurityProtocol = SecurityProtocolType.Tls12; ServicePointManager.SecurityProtocol = SecurityProtocolType.Tls12;

View File

@@ -371,6 +371,24 @@ namespace BeWoPlanerMobil.Models
public bool HasRightToViewPersonDocuments => CheckForAtLeastOneRight(new[] { UserRightType.ViewAll, UserRightType.DokumentePersonen }); public bool HasRightToViewPersonDocuments => CheckForAtLeastOneRight(new[] { UserRightType.ViewAll, UserRightType.DokumentePersonen });
public bool HasRightToViewPersonUmfeld => CheckForAtLeastOneRight(new[] { UserRightType.ViewAll, UserRightType.Person_FamilyView }); public bool HasRightToViewPersonUmfeld => CheckForAtLeastOneRight(new[] { UserRightType.ViewAll, UserRightType.Person_FamilyView });
#region Kalenderrechte
public bool HasRightKalenderAnsehen => CheckRight(UserRightType.KalenderAnsehen);
public bool HasRightKalenderMitarbeitertermineAnsehen => CheckRight(UserRightType.KalenderMitarbeitertermineAnsehen); public bool HasRightKalenderMitarbeitertermineAnsehen => CheckRight(UserRightType.KalenderMitarbeitertermineAnsehen);
public bool HasRightKalenderMitarbeiterTermineAnlegen => CheckRight(UserRightType.KalenderMitarbeitertermineAnlegen);
public bool HasRightKalenderMitarbeiterTermineAendern => CheckRight(UserRightType.KalenderMitarbeitertermineAendern);
public bool HasRightKalenderKliententermineAnsehen => CheckRight(UserRightType.KalenderKliententermineAlleAnsehen);
public bool HasRightKalenderKlientenTermineAnlegen => CheckRight(UserRightType.KalenderKliententermineAnlegen);
public bool HasRightKalenderKlientenTermineAendern => CheckRight(UserRightType.KalenderKliententermineAendern);
public bool HasRightKalenderRessourcentermineAnsehen => CheckRight(UserRightType.KalenderRessourcentermineAnsehen);
public bool HasRightKalenderRessourcenTermineAnlegen => CheckRight(UserRightType.KalenderRessourcentermineAnlegen);
public bool HasRightKalenderRessourcenTermineAendern => CheckRight(UserRightType.KalenderRessourcentermineAendern);
public bool HasRightKalenderRessourcenTermineAndererAendern => CheckRight(UserRightType.KalenderRessourcentermineAndererAendern);
public bool HasRightKalenderInZeiterfassungUebernehmen => CheckRight(UserRightType.KalenderInZeiterfassungUebernehmen);
public bool HasRightKalenderInAbwesenheitUebernehmen => CheckRight(UserRightType.KalenderInAbwesenheitenUebernehmen);
#endregion
} }
} }

View File

@@ -32,6 +32,9 @@ namespace BeWoPlanerMobil.Models
public string CompletedUser { get; set; } public string CompletedUser { get; set; }
public string TaskDescription { get; set; } public string TaskDescription { get; set; }
public bool HasServiceRecordEntry { get; set; } public bool HasServiceRecordEntry { get; set; }
public long? OriginatorOid { get; set; }
public bool ShowEmployeeColors { get; set; }
public List<ServiceRecordDC> ServiceRecordList { get; set; } public List<ServiceRecordDC> ServiceRecordList { get; set; }
#region Mitarbeiter #region Mitarbeiter
@@ -51,10 +54,10 @@ namespace BeWoPlanerMobil.Models
set => AppointmentSessionModel.SelectedEmployeeOids = value; set => AppointmentSessionModel.SelectedEmployeeOids = value;
} }
public List<long> SelectedEmployees2Appointments public List<long> SelectedEmployee2AppointmentOids
{ {
get => AppointmentSessionModel.SelectedEmployees2Appointments; get => AppointmentSessionModel.SelectedEmployees2AppointmentOids;
set => AppointmentSessionModel.SelectedEmployees2Appointments = value; set => AppointmentSessionModel.SelectedEmployees2AppointmentOids = value;
} }
#endregion #endregion
@@ -121,12 +124,47 @@ namespace BeWoPlanerMobil.Models
SessionModel = new AppointmentSessionModel(); SessionModel = new AppointmentSessionModel();
} }
public AppointmentModel(List<CompactCustomerDC> possibleCustomers, List<ResourceDC> possibleResources, List<CompactEmployeeDC> possibleEmployees) public AppointmentModel(List<CompactCustomerDC> possibleCustomers, List<ResourceDC> possibleResources, List<CompactEmployeeDC> possibleEmployees, UserDC user, List<CompactCustomerDC> selectedCustomers, List<ResourceDC> selectedResources, List<Employee2SchedulerAppointmentDC> employee2Appointments)
{ {
LoggedInUser = user;
SessionModel = new AppointmentSessionModel();
SelectedCustomers = selectedCustomers;
SelectedCustomerOids = selectedCustomers.Select(customer => customer.CustomerOid).ToList();
SelectedEmployee2SchedulerAppointments = employee2Appointments;
SelectedEmployee2AppointmentOids = employee2Appointments
.Where(employee2Appointment => employee2Appointment.Employee2SchedulerAppointmentOid.HasValue)
.Select(employee2Appointment => employee2Appointment.Employee2SchedulerAppointmentOid.Value).ToList();
SelectedEmployees = employee2Appointments.Select(employee2Appointment => employee2Appointment.Employee).ToList();
SelectedEmployeeOids = employee2Appointments.Select(employee2Appointment => employee2Appointment.Employee.EmployeeOid).ToList();
SelectedResources = selectedResources;
SelectedResourceOids = selectedResources
.Where(resource => resource.ResourceOid.HasValue)
.Select(resource => resource.ResourceOid.Value).ToList();
PossibleCustomers = possibleCustomers; PossibleCustomers = possibleCustomers;
PossibleResources = possibleResources; PossibleResources = possibleResources;
PossibleEmployees = possibleEmployees; PossibleEmployees = possibleEmployees;
if(PossibleCustomers.Count == 0 && selectedCustomers.Count > 0)
{
PossibleCustomers = selectedCustomers;
}
if(PossibleResources.Count == 0 && selectedResources.Count > 0)
{
PossibleResources = selectedResources;
}
if(PossibleEmployees.Count == 0 && SelectedEmployees.Count > 0)
{
PossibleEmployees = SelectedEmployees;
}
ResourceCategories2Resources = new Dictionary<ValueListEntryDC, List<ResourceDC>>(); ResourceCategories2Resources = new Dictionary<ValueListEntryDC, List<ResourceDC>>();
foreach(var resource in PossibleResources) foreach(var resource in PossibleResources)
@@ -134,7 +172,7 @@ namespace BeWoPlanerMobil.Models
ResourceCategories2Resources.AddOrUpdateValueInDictionary(resource.ResourceCategory, resource); ResourceCategories2Resources.AddOrUpdateValueInDictionary(resource.ResourceCategory, resource);
} }
SessionModel = new AppointmentSessionModel();
} }
public AppointmentModel(SchedulerAppointmentDC appointment) public AppointmentModel(SchedulerAppointmentDC appointment)
@@ -172,6 +210,8 @@ namespace BeWoPlanerMobil.Models
CompletedNotice = appointment.CompletedNotice; CompletedNotice = appointment.CompletedNotice;
CompletedUser = appointment.CompletedUser; CompletedUser = appointment.CompletedUser;
TaskDescription = appointment.TaskDescription; TaskDescription = appointment.TaskDescription;
OriginatorOid = appointment.Originator.EmployeeOid;
} }
public virtual void Assign(AppointmentModel source) public virtual void Assign(AppointmentModel source)
@@ -208,6 +248,8 @@ namespace BeWoPlanerMobil.Models
CompletedNotice = source.CompletedNotice; CompletedNotice = source.CompletedNotice;
CompletedUser = source.CompletedUser; CompletedUser = source.CompletedUser;
TaskDescription = source.TaskDescription; TaskDescription = source.TaskDescription;
OriginatorOid = source.OriginatorOid;
} }
} }
} }

View File

@@ -8,7 +8,8 @@ namespace BeWoPlanerMobil.Models
public List<long> SelectedCustomerOids { get; set; } public List<long> SelectedCustomerOids { get; set; }
public List<long> SelectedResourceOids { get; set; } public List<long> SelectedResourceOids { get; set; }
public List<long> SelectedEmployees2Appointments { get; set; } = new List<long>(); public List<long> SelectedEmployees2AppointmentOids { get; set; } = new List<long>();
public override void ResetValues() public override void ResetValues()
{ {
@@ -17,7 +18,7 @@ namespace BeWoPlanerMobil.Models
SelectedCustomerOids = new List<long>(); SelectedCustomerOids = new List<long>();
SelectedEmployeeOids = new List<long>(); SelectedEmployeeOids = new List<long>();
SelectedResourceOids = new List<long>(); SelectedResourceOids = new List<long>();
SelectedEmployees2Appointments = new List<long>(); SelectedEmployees2AppointmentOids = new List<long>();
} }
} }
} }

View File

@@ -1,5 +1,7 @@
using System.Collections; using System;
using System.Collections;
using System.Collections.Generic; using System.Collections.Generic;
using System.Linq;
using BeWoPlanerMobil.Util.SchedulerUtils; using BeWoPlanerMobil.Util.SchedulerUtils;
using BS.Shared.DataContracts; using BS.Shared.DataContracts;
using BS.Shared.DataContracts.Compact; using BS.Shared.DataContracts.Compact;
@@ -13,6 +15,8 @@ namespace BeWoPlanerMobil.Models
{ {
SessionModel = new DevExpressSchedulerSessionModel(); SessionModel = new DevExpressSchedulerSessionModel();
SessionModel.ResetValues(); SessionModel.ResetValues();
ShowEmployeeColors = true;
} }
public SchedulerViewType CurrentViewType public SchedulerViewType CurrentViewType
@@ -69,13 +73,6 @@ namespace BeWoPlanerMobil.Models
return null; return null;
} }
public long? AppointmentOid2Answer
{
get => DevExpressSchedulerSessionModel.AppointmentOid2Answer;
set => DevExpressSchedulerSessionModel.AppointmentOid2Answer = value;
}
public SchedulerAppointmentDC Appointment2Answer { get; set; }
public List<long> SelectedEmployeeOidsForFiltering public List<long> SelectedEmployeeOidsForFiltering
{ {
get => DevExpressSchedulerSessionModel.SelectedEmployeeOidsForFiltering; get => DevExpressSchedulerSessionModel.SelectedEmployeeOidsForFiltering;
@@ -155,7 +152,13 @@ namespace BeWoPlanerMobil.Models
#region Benachrichtigungen #region Benachrichtigungen
public List<SchedulerAppointmentDC> OpenAppointments { get; set; } public List<Employee2SchedulerAppointmentDC> OpenEmployee2AppointmentRels { get; set; }
public List<long> OpenEmployee2AppointmentRelOids
{
get => DevExpressSchedulerSessionModel.OpenEmployee2AppointmentRelOids;
set => DevExpressSchedulerSessionModel.OpenEmployee2AppointmentRelOids = value;
}
public List<long> OpenAppointmentOids public List<long> OpenAppointmentOids
{ {
@@ -163,8 +166,41 @@ namespace BeWoPlanerMobil.Models
set => DevExpressSchedulerSessionModel.OpenAppointmentOids = value; set => DevExpressSchedulerSessionModel.OpenAppointmentOids = value;
} }
public int NotificationCount => OpenAppointmentOids?.Count ?? 0; public List<SchedulerAppointmentDC> OpenAppointments { get; set; }
public SchedulerAppointmentDC AppointmentToAnswerOrUpdate { get; set; }
public long? AppointmentOidToAnswerOrUpdate
{
get => DevExpressSchedulerSessionModel.AppointmentOidToAnswerOrUpdate;
set => DevExpressSchedulerSessionModel.AppointmentOidToAnswerOrUpdate = value;
}
public Employee2SchedulerAppointmentDC Employee2AppointmentToAnswerOrUpdateRel { get; set; }
public long? Employee2AppointmentToAnswerOrUpdateRelOid
{
get => DevExpressSchedulerSessionModel.Employee2AppointmentToAnswerOrUpdateRelOid;
set => DevExpressSchedulerSessionModel.Employee2AppointmentToAnswerOrUpdateRelOid = value;
}
public int NotificationCount => OpenEmployee2AppointmentRelOids.Count;
public SchedulerAppointmentDC GetAppointment2AnswerByOid(long appointmentOid)
{
return OpenAppointments?.FirstOrDefault(f => f.SchedulerAppointmentOid?.Equals(appointmentOid) ?? false);
}
public bool CanConfirmAllOpenAppointments()
{
return OpenAppointments?.Any(a => a.EndDate is null || a.EndDate.Value < DateTime.Now) is false;
}
#endregion #endregion
public string GetNotificationInfo()
{
return $"{NotificationCount} Benachrichtigung{(NotificationCount == 1 ? string.Empty : "en")}";
}
} }
} }

View File

@@ -14,8 +14,12 @@ namespace BeWoPlanerMobil.Models
public List<long> SelectedCustomerOidsForFiltering { get; set; } public List<long> SelectedCustomerOidsForFiltering { get; set; }
public List<long> SelectedResourceOidsForFiltering { get; set; } public List<long> SelectedResourceOidsForFiltering { get; set; }
public List<long> OpenEmployee2AppointmentRelOids { get; set; }
public List<long> OpenAppointmentOids { get; set; } public List<long> OpenAppointmentOids { get; set; }
public long? AppointmentOid2Answer { get; set; } public long? AppointmentOidToAnswerOrUpdate { get; set; }
public bool ShowTasks { get; set; } public bool ShowTasks { get; set; }
public bool ShowOnlyPrivateAppointments { get; set; } public bool ShowOnlyPrivateAppointments { get; set; }
@@ -26,7 +30,8 @@ namespace BeWoPlanerMobil.Models
public bool ShowEmployeeColors { get; set; } public bool ShowEmployeeColors { get; set; }
public bool ShowOnlyMyOwnAppointments { get; set; } public bool ShowOnlyMyOwnAppointments { get; set; }
public int NotificationCount => OpenAppointmentOids?.Count ?? 0; public int NotificationCount => OpenEmployee2AppointmentRelOids?.Count ?? 0;
public long? Employee2AppointmentToAnswerOrUpdateRelOid { get; set; }
public override void ResetValues() public override void ResetValues()
{ {
@@ -40,6 +45,7 @@ namespace BeWoPlanerMobil.Models
SelectedCustomerOidsForFiltering = new List<long>(); SelectedCustomerOidsForFiltering = new List<long>();
SelectedResourceOidsForFiltering = new List<long>(); SelectedResourceOidsForFiltering = new List<long>();
OpenEmployee2AppointmentRelOids = new List<long>();
OpenAppointmentOids = new List<long>(); OpenAppointmentOids = new List<long>();
ShowTasks = false; ShowTasks = false;
@@ -50,6 +56,8 @@ namespace BeWoPlanerMobil.Models
ShowAbsenceTimes = false; ShowAbsenceTimes = false;
ShowEmployeeColors = false; ShowEmployeeColors = false;
ShowOnlyMyOwnAppointments = false; ShowOnlyMyOwnAppointments = false;
AppointmentOidToAnswerOrUpdate = null;
Employee2AppointmentToAnswerOrUpdateRelOid = null;
} }
} }
} }

View File

@@ -18,7 +18,20 @@ namespace BeWoPlanerMobil.Models
public List<UserRightType> UserRightTypes { get; set; } = new List<UserRightType>(); public List<UserRightType> UserRightTypes { get; set; } = new List<UserRightType>();
public List<UserDC> Users { get; set; } = new List<UserDC>(); public List<UserDC> Users { get; set; } = new List<UserDC>();
public MandatorSettings MandatorSettings { get; set; } public List<ResourceDC> Resources { get; set; }
public MandatorSettings MandatorSettings
{
get => DevToolsSessionModel.MandatorSettings;
set => DevToolsSessionModel.MandatorSettings = value;
}
public DevToolsSessionModel DevToolsSessionModel => SessionModel as DevToolsSessionModel;
public DevToolsModel()
{
SessionModel = new DevToolsSessionModel();
}
} }
public class MandatorSettings public class MandatorSettings
@@ -97,14 +110,9 @@ namespace BeWoPlanerMobil.Models
public bool ShowArbeitszeiten { get; set; } public bool ShowArbeitszeiten { get; set; }
public bool ShowBetrag { get; set; } public bool ShowBetrag { get; set; }
public bool ShowChat { get; set; } public bool ShowChat { get; set; }
private bool _ShowCustomerDistanceFields;
public bool ShowCustomerDistanceFields public bool ShowCustomerDistanceFields { get; set; }
{
get => _ShowCustomerDistanceFields;
set => _ShowCustomerDistanceFields = value;
}
public bool ShowDatevFields { get; set; } public bool ShowDatevFields { get; set; }
public bool ShowDienstplanung { get; set; } public bool ShowDienstplanung { get; set; }
public bool ShowDistanceFields { get; set; } public bool ShowDistanceFields { get; set; }

View File

@@ -0,0 +1,117 @@
using System.Collections.Generic;
namespace BeWoPlanerMobil.Models
{
public class DevToolsSessionModel : BaseSessionModel
{
public List<long> UserGroupOids { get; set; }
public List<long> UserOids { get; set; }
public MandatorSettings MandatorSettings { get; set; }
public bool HideServiceRecordInsertedByAndInsertedOn { get; set; }
public bool IsEndDateVisible { get; set; }
public bool IsServiceRecordNoticeMandatory { get; set; }
public bool IsZeiterfassDateNormal { get; set; }
public bool SetStartTimeToEndTimeAfterSave { get; set; }
public bool ShowAdditionalService { get; set; }
public bool ShowAnnualReport { get; set; }
public bool ShowArbeitszeiten { get; set; }
public bool ShowBetrag { get; set; }
public bool ShowChat { get; set; }
public bool ShowCustomerDistanceFields { get; set; }
public bool ShowDatevFields { get; set; }
public bool ShowDienstplanung { get; set; }
public bool ShowDistanceFields { get; set; }
public bool ShowEmployeeSignature { get; set; }
public bool ShowHilfeplanBezeichnung { get; set; }
public bool ShowHilfeplanStatistikReport { get; set; }
public bool ShowInfoButtonInCalender { get; set; }
public bool ShowKlientenBetreuungszeiten { get; set; }
public bool ShowMarker { get; set; }
public bool ShowMedication { get; set; }
public bool ShowMultipleResourceColors { get; set; }
public bool ShowOnlyMySupportConcepts { get; set; }
public bool ShowOwnChatSettings { get; set; }
public bool ShowPivotGrid { get; set; }
public bool ShowRoundedDurationInEmployeeAnalysis { get; set; }
public bool ShowRtfTextfield { get; set; }
public bool ShowScheduler { get; set; }
public bool ShowServicesOverviewHalfOrWholeMonth { get; set; }
public bool ShowSignature { get; set; }
public bool ShowTeamNews { get; set; }
public bool ShowUrlaubsplanung { get; set; }
public bool ShowWohnheime { get; set; }
public bool AllowStorno { get; set; }
public bool DontShowSpitzabrechnung { get; set; }
public bool IsOnlyYearMonthVisible { get; set; }
public bool IsPasswordSecurityActiv { get; set; }
public bool PrinterSettingsUseLandscape { get; set; }
public bool PrinterSettingsUseMargins { get; set; }
public bool PrinterSettingsUsePaperKind { get; set; }
public bool ShowResources { get; set; }
public int MaxDaysEditServiceRecordsAllowed { get; set; }
public int ZeiterfassungsSchwellwert { get; set; }
public int AnzTageZeiterfassErfolgt { get; set; }
public int DienstplanungStandardZeilenAnzahl { get; set; }
public int HilfeplanAuslaufAuswahl { get; set; }
public int TimeUntilUILock { get; set; }
public int EinheitZeiterfassung { get; set; }
public override void ResetValues()
{
base.ResetValues();
HideServiceRecordInsertedByAndInsertedOn = false;
IsEndDateVisible = false;
IsServiceRecordNoticeMandatory = false;
IsZeiterfassDateNormal = false;
SetStartTimeToEndTimeAfterSave = false;
ShowAdditionalService = false;
ShowAnnualReport = false;
ShowArbeitszeiten = false;
ShowBetrag = false;
ShowChat = false;
ShowCustomerDistanceFields = false;
ShowDatevFields = false;
ShowDienstplanung = false;
ShowDistanceFields = false;
ShowEmployeeSignature = false;
ShowHilfeplanBezeichnung = false;
ShowHilfeplanStatistikReport = false;
ShowInfoButtonInCalender = false;
ShowKlientenBetreuungszeiten = false;
ShowMarker = false;
ShowMedication = false;
ShowMultipleResourceColors = false;
ShowOnlyMySupportConcepts = false;
ShowOwnChatSettings = false;
ShowPivotGrid = false;
ShowRoundedDurationInEmployeeAnalysis = false;
ShowRtfTextfield = false;
ShowScheduler = false;
ShowServicesOverviewHalfOrWholeMonth = false;
ShowSignature = false;
ShowTeamNews = false;
ShowUrlaubsplanung = false;
ShowWohnheime = false;
AllowStorno = false;
DontShowSpitzabrechnung = false;
IsOnlyYearMonthVisible = false;
IsPasswordSecurityActiv = false;
PrinterSettingsUseLandscape = false;
PrinterSettingsUseMargins = false;
PrinterSettingsUsePaperKind = false;
ShowResources = false;
MaxDaysEditServiceRecordsAllowed = 0;
ZeiterfassungsSchwellwert = 0;
AnzTageZeiterfassErfolgt = 0;
DienstplanungStandardZeilenAnzahl = 0;
HilfeplanAuslaufAuswahl = 0;
TimeUntilUILock = 0;
EinheitZeiterfassung = 0;
}
}
}

View File

@@ -9,8 +9,6 @@ using System.Threading;
using System.Web; using System.Web;
using BeWo.Data.Access; using BeWo.Data.Access;
using BeWo.Data.Entities;
using BeWo.Service.DCEntityMapper;
using BeWo.Service.ServiceImplementations; using BeWo.Service.ServiceImplementations;
using BeWoPlanerMobil.Util; using BeWoPlanerMobil.Util;
using BS.Shared; using BS.Shared;
@@ -222,6 +220,7 @@ namespace BeWoPlanerMobil.Service
MobileSessionFacade.LoggedInUserOid = user.Oid; MobileSessionFacade.LoggedInUserOid = user.Oid;
MobileSessionFacade.EmployeeFullname = user.Employee.Person.FirstNameLastName; MobileSessionFacade.EmployeeFullname = user.Employee.Person.FirstNameLastName;
MobileSessionFacade.LoggedInEmployeeOid = user.Employee.Oid;
//MobileSessionFacade.LoggedInEmployee = MapperFactory.EmployeeDC_Employee.MapToNewDC(user.Employee); //MobileSessionFacade.LoggedInEmployee = MapperFactory.EmployeeDC_Employee.MapToNewDC(user.Employee);
} }

View File

@@ -45,6 +45,12 @@ namespace BeWoPlanerMobil.Service
set => HttpContext.Current.Session["LoggedInUserOid"] = value; set => HttpContext.Current.Session["LoggedInUserOid"] = value;
} }
public static long? LoggedInEmployeeOid
{
get => HttpContext.Current.Session["LoggedInEmployeeOid"] as long?;
set => HttpContext.Current.Session["LoggedInEmployeeOid"] = value;
}
//public static UserDC LoggedInUser //public static UserDC LoggedInUser
//{ //{
// get => HttpContext.Current.Session["apuser"] as UserDC; // get => HttpContext.Current.Session["apuser"] as UserDC;

View File

@@ -16,6 +16,8 @@ using System.Linq;
using System.Text; using System.Text;
using System.Text.RegularExpressions; using System.Text.RegularExpressions;
using System.Web; using System.Web;
using BeWo.Service.Plugins;
using BeWoPlanerMobil.Service;
using static System.Int32; using static System.Int32;
using static System.String; using static System.String;
@@ -622,6 +624,13 @@ namespace BeWoPlanerMobil.Util
public static string GetLeftAppointmentBorder(DevExpress.XtraScheduler.Appointment appointment) public static string GetLeftAppointmentBorder(DevExpress.XtraScheduler.Appointment appointment)
{ {
var showEmployeeColors = appointment.CustomFields["ShowEmployeeColors"] is true;
if(false == showEmployeeColors)
{
return "5px solid #C0FFD0";
}
if(appointment.CustomFields[nameof(SchedulerAppointmentDC.Originator)] is CompactEmployeeDC originator && originator.FilterableBrush?.Color != null) if(appointment.CustomFields[nameof(SchedulerAppointmentDC.Originator)] is CompactEmployeeDC originator && originator.FilterableBrush?.Color != null)
{ {
var color = originator.FilterableBrush.Color; var color = originator.FilterableBrush.Color;

View File

@@ -0,0 +1,18 @@
@using BeWoPlanerMobil.Util
<script type="text/javascript">
function onAppointmentDragTipDisplaying(s, e) {
const newIntervalText = e.toolTip.ConvertIntervalToString(e.data.GetInterval());
$('#aptDragToolTipInterval').html(newIntervalText);
}
</script>
<div style="white-space:nowrap;">
<strong>
<span id="aptDragToolTipInterval">
AppointmentDrag
</span>
</strong>
<br />
<span>Press ESC to cancel operation</span>
</div>

View File

@@ -4,9 +4,86 @@
@using DevExpress.Web.Mvc.UI @using DevExpress.Web.Mvc.UI
@{ @{
Html.EnableClientValidation(); Html.EnableClientValidation();
Html.EnableUnobtrusiveJavaScript(); Html.EnableUnobtrusiveJavaScript();
var isNew = Model.Oid is null;
var cancelButtonText = "Abbrechen";
var isOriginator = Model.OriginatorOid?.Equals(Model.LoggedInCompactEmployee.EmployeeOid) ?? false;
var isInEmployeeList = Model.SelectedEmployee2SchedulerAppointments.Any(employee2Appointment => employee2Appointment.Employee.Equals(Model.LoggedInCompactEmployee));
var hasCustomers = Model.SelectedCustomers.Any();
var hasEmployees = Model.SelectedEmployee2SchedulerAppointments.Any();
var hasResources = Model.SelectedResources.Any();
var canEditCustomerApt = Model.HasRightKalenderKlientenTermineAendern;
var canEditEmployeeApt = Model.HasRightKalenderMitarbeiterTermineAendern;
var canEditResourceApt = Model.HasRightKalenderRessourcenTermineAendern;
var canEditOthersResourceApt = Model.HasRightKalenderRessourcenTermineAndererAendern;
var areButtonsVisible = true;
if(isOriginator is false || isNew is false)
{
if(canEditCustomerApt is false && hasCustomers)
{
areButtonsVisible = false;
}
if(canEditEmployeeApt is false && hasEmployees && isInEmployeeList is false)
{
areButtonsVisible = false;
}
}
// Es ist eigentlich unmöglich als jemand anderes einen Termin anzulegen, denn der angemeldete Mitarbeiter ist ja immer der InsUser.
if(isOriginator is false && isNew is false)
{
if(canEditOthersResourceApt is false && hasResources)
{
areButtonsVisible = false;
}
}
else if(isNew is false)
{
// Falls man beim Anlegen mehr Rechte hatte als beim Bearbeiten:
if(canEditResourceApt is false && hasResources)
{
areButtonsVisible = false;
}
}
var disabled = string.Empty;
if(areButtonsVisible is false)
{
cancelButtonText = "Schließen";
disabled = "disabled";
}
var isDeleteButtonVisible = areButtonsVisible && isNew is false;
var dateInputType = isNew is false && Model.AllDay ? "date" : "datetime-local";
var start = Model.StartTime.HasValue ? Model.AllDay ? $"{Model.StartTime:yyyy-MM-dd}" : $"{Model.StartTime:yyyy-MM-ddTHH:mm}" : string.Empty;
var end = Model.EndTime.HasValue ? Model.AllDay ? $"{Model.EndTime:yyyy-MM-dd}" : $"{Model.EndTime:yyyy-MM-ddTHH:mm}" : string.Empty;
var showEmployeeButton = (Model.HasRightKalenderMitarbeitertermineAnsehen && Model.Oid.HasValue) ||
(Model.Oid.HasValue && Model.HasRightKalenderMitarbeiterTermineAendern) ||
(Model.Oid is null && Model.HasRightKalenderMitarbeiterTermineAnlegen);
var showCustomerButton = (Model.HasRightKalenderKliententermineAnsehen && Model.Oid.HasValue) ||
(Model.Oid.HasValue && Model.HasRightKalenderKlientenTermineAendern) ||
(Model.Oid is null && Model.HasRightKalenderKlientenTermineAnlegen);
var showResourceButton = (Model.HasRightKalenderRessourcentermineAnsehen && Model.Oid.HasValue) ||
(Model.Oid.HasValue && (Model.HasRightKalenderRessourcenTermineAendern && isOriginator || isOriginator is false && Model.HasRightKalenderRessourcenTermineAndererAendern)) ||
(Model.Oid is null && Model.HasRightKalenderRessourcenTermineAnlegen);
} }
<style type="text/css"> <style type="text/css">
@@ -18,187 +95,135 @@
@using(Html.BeginForm()) @using(Html.BeginForm())
{ {
<table id="abc-table"> <table id="abc-table" class="w-100">
@* Betreff *@ @* Betreff *@
<tr> <tr>
<td> <td colspan="2">
@Html.DevExpress().Label( <div class="input-group mb-2">
settings => <div class="input-group-prepend">
{ <span class="input-group-text">Betreff</span>
settings.AssociatedControlName = nameof(SchedulerAppointmentDC.Subject); </div>
settings.Text = "Betreff:"; <input class="form-control" type="text" @disabled id="Subject" name="Subject" value="@Model.Subject" />
settings.Width = Unit.Percentage(100); </div>
}).GetHtml()
</td>
<td colspan="3" style="width: 100%; padding: .25em;">
@Html.DevExpress().TextBox(
settings =>
{
settings.Name = nameof(SchedulerAppointmentDC.Subject);
settings.ShowModelErrors = true;
settings.Properties.ValidationSettings.Display = Display.Dynamic;
settings.Width = Unit.Percentage(100);
}).Bind(Model.Subject).GetHtml()
</td> </td>
</tr> </tr>
@* Ort *@ @* Ort *@
<tr> <tr>
<td> <td colspan="2">
@Html.DevExpress().Label( <div class="input-group mb-2">
settings => <div class="input-group-prepend">
{ <span class="input-group-text">Ort</span>
settings.AssociatedControlName = nameof(SchedulerAppointmentDC.Location); </div>
settings.Text = "Ort:"; <input class="form-control" type="text" @disabled id="Location" name="Location" value="@Model.Location" />
settings.Width = Unit.Percentage(100); </div>
}).GetHtml()
</td>
<td colspan="3" style="width: 100%; padding: .25em;">
@Html.DevExpress().TextBox(
settings =>
{
settings.Name = nameof(SchedulerAppointmentDC.Location);
settings.ShowModelErrors = true;
settings.Properties.ValidationSettings.Display = Display.Dynamic;
settings.Width = Unit.Percentage(100);
}).Bind(Model.Location).GetHtml()
</td> </td>
</tr> </tr>
@* Start *@ @* Start *@
<tr> <tr>
<td style="white-space: nowrap;"> <td>
@Html.DevExpress().Label( <div class="input-group mb-2">
settings => <div class="input-group-prepend">
{ <span class="input-group-text">Start</span>
settings.AssociatedControlName = nameof(SchedulerAppointmentDC.StartDate); </div>
settings.Text = "Start:"; <input class="form-control" type="@dateInputType" @disabled id="StartDate" name="StartDate" value="@start" />
settings.Width = Unit.Percentage(100); </div>
}).GetHtml()
</td> </td>
<td colspan="3" style="padding: .25em;"> <td>
@Html.DevExpress().DateEdit( <div class="input-group pl-2 mb-2">
settings => <div class="input-group-prepend">
{ <div class="input-group-text">
settings.Name = nameof(SchedulerAppointmentDC.StartDate);
settings.Properties.EditFormat = EditFormat.DateTime;
settings.ShowModelErrors = true;
settings.Properties.ValidationSettings.Display = Display.Dynamic;
settings.Width = Unit.Percentage(100);
}).Bind(Model.StartTime).GetHtml()
</td>
</tr>
@* Ende *@
<tr>
<td style="white-space: nowrap;">
@Html.DevExpress().Label(
settings =>
{
settings.AssociatedControlName = nameof(SchedulerAppointmentDC.EndDate);
settings.Text = "Ende:";
settings.Width = Unit.Percentage(100);
}).GetHtml()
</td>
<td colspan="3" style="padding: .25em;">
@Html.DevExpress().DateEdit(
settings =>
{
settings.Name = nameof(SchedulerAppointmentDC.EndDate);
settings.Properties.EditFormat = EditFormat.DateTime;
settings.ShowModelErrors = true;
settings.Properties.ValidationSettings.Display = Display.Dynamic;
settings.Width = Unit.Percentage(100);
}).Bind(Model.EndTime).GetHtml()
</td>
</tr>
@* Private & Ganztägig *@
<tr>
<td colspan="4">
<table style="width: 100%;">
<tr>
<td style="width: 1%; wihte-space: nowrap;">
@Html.DevExpress().CheckBox(
settings =>
{
settings.Name = nameof(SchedulerAppointmentDC.IsPrivate);
settings.Width = Unit.Percentage(100);
}).Bind(Model.IsPrivate).GetHtml()
</td>
<td style="margin-right: 1em;">
@Html.DevExpress().Label(
settings =>
{
settings.AssociatedControlName = nameof(SchedulerAppointmentDC.IsPrivate);
settings.Text = "Privat";
settings.Width = Unit.Percentage(100);
settings.ControlStyle.CssClass = "centeredLabel";
}).GetHtml()
</td>
<td style="width: 1%; wihte-space: nowrap;">
@Html.DevExpress().CheckBox( @Html.DevExpress().CheckBox(
settings => settings =>
{ {
settings.Name = nameof(SchedulerAppointmentDC.AllDay); settings.Name = nameof(SchedulerAppointmentDC.AllDay);
settings.Width = Unit.Percentage(100); settings.Width = Unit.Percentage(100);
settings.ReadOnly = disabled.Length > 0;
}).Bind(Model.AllDay).GetHtml() }).Bind(Model.AllDay).GetHtml()
</td> </div>
<td style="margin-right: 1em;"> </div>
@Html.DevExpress().Label( <div class="input-group-append">
settings => <span class="input-group-text">Ganztägig</span>
{ </div>
settings.AssociatedControlName = nameof(SchedulerAppointmentDC.AllDay); </div>
settings.Text = "Ganztägig";
settings.Width = Unit.Percentage(100);
settings.ControlStyle.CssClass = "centeredLabel";
}).GetHtml()
</td>
</tr>
</table>
</td>
</tr>
<tr>
<td colspan="4">
<table class="w-100">
<tr>
<td style="width: 33%; padding: .25em;">
@Html.Partial("CustomEmployeeSelectPartial", Model)
</td>
<td style="width: 33%; padding: .25em;">
@Html.Partial("CustomCustomerSelectPartial", Model)
</td>
<td style="width: 33%; padding: .25em;">
@Html.Partial("CustomResourceSelectPartial", Model)
</td>
</tr>
</table>
</td> </td>
</tr> </tr>
@* Notiz *@ @* Ende *@
<tr> <tr>
<td colspan="4"> <td colspan="2">
@Html.DevExpress().Label( <div class="input-group mb-2">
settings => <div class="input-group-prepend">
{ <span class="input-group-text">Ende</span>
settings.AssociatedControlName = nameof(SchedulerAppointmentDC.Description); </div>
settings.Text = "Notiz:"; <input class="form-control" type="@dateInputType" @disabled id="EndDate" name="EndDate" value="@end" />
settings.Width = Unit.Percentage(100); </div>
}).GetHtml()
</td> </td>
</tr> </tr>
@* Privat *@
<tr> <tr>
<td colspan="4">
@Html.DevExpress().Memo( <td >
settings => <div class="input-group mb-2">
{ <div class="input-group-prepend">
settings.Name = nameof(SchedulerAppointmentDC.Description); <div class="input-group-text">
settings.Properties.Rows = 4; @Html.DevExpress().CheckBox(
settings.ShowModelErrors = true; settings =>
settings.Properties.ValidationSettings.Display = Display.Dynamic; {
settings.Width = Unit.Percentage(100); settings.Name = nameof(SchedulerAppointmentDC.IsPrivate);
}).Bind(Model.Description).GetHtml() settings.Width = Unit.Percentage(100);
settings.Properties.RootStyle.CssClass = "";
settings.ReadOnly = disabled.Length > 0;
}).Bind(Model.IsPrivate).GetHtml()
</div>
</div>
<div class="input-group-append">
<span class="input-group-text">Privat</span>
</div>
</div>
</td>
</tr>
@if(Model.HasRightKalenderMitarbeitertermineAnsehen || Model.HasRightKalenderKliententermineAnsehen || Model.HasRightKalenderRessourcentermineAnsehen)
{
<tr>
@* colspan="4" *@
<td colspan="2">
<table class="w-100">
<tr>
<td style="width: 33%; padding: .25em;">
@if(showEmployeeButton)
{
@Html.Partial("CustomEmployeeSelectPartial", Model)
}
</td>
<td style="width: 33%; padding: .25em;">
@if(showCustomerButton)
{
@Html.Partial("CustomCustomerSelectPartial", Model)
}
</td>
<td style="width: 33%; padding: .25em;">
@if(showResourceButton)
{
@Html.Partial("CustomResourceSelectPartial", Model)
}
</td>
</tr>
</table>
</td>
</tr>
}
@* Notiz *@
<tr>
<td colspan="2">
<div class="form-group">
<label for="Description">Notiz</label>
<textarea class="form-control" @disabled id="Description" name="Description">@Model.Description</textarea>
</div>
</td> </td>
</tr> </tr>
</table> </table>
@@ -206,48 +231,31 @@
@Html.DevExpress().AppointmentRecurrenceForm(ViewBag.AppointmentRecurrenceFormSettings).GetHtml() @Html.DevExpress().AppointmentRecurrenceForm(ViewBag.AppointmentRecurrenceFormSettings).GetHtml()
<table style="width: 100%"> <table style="width: 100%">
<tr> <tr>
<td style="padding: .25em;"> @if(areButtonsVisible)
@Html.DevExpress().Button( {
settings => <button type="button" class="btn btn-primary mr-2" id="Apply" name="Apply" onclick="OnAppointmentFormSave()">OK</button>
{ }
settings.Name = "Apply";
settings.Text = "OK"; <button type="button" class="btn btn-primary mr-2" id="Cancel" name="Cancel" onclick="OnAppointmentFormCancel()">@cancelButtonText</button>
settings.ClientSideEvents.Click = "OnAppointmentFormSave";
}).GetHtml() @if(isDeleteButtonVisible)
</td> {
<td style="padding: .25em;"> <button type="button" class="btn btn-danger" id="Delete" name="Delete" onclick="OnAppointmentFormDelete()">Löschen</button>
@Html.DevExpress().Button( }
settings => </tr>
{
settings.Name = "Cancel";
settings.Text = "Abbrechen";
settings.ClientSideEvents.Click = "function(s, e){ scheduler.AppointmentFormCancel(); }";
}).GetHtml()
</td>
<td style="padding: .25em;">
@Html.DevExpress().Button(
settings =>
{
settings.Name = "Delete";
settings.Text = "Löschen";
settings.Enabled = ViewBag.DeleteButtonEnabled;
settings.ClientSideEvents.Click = "function(s, e){ scheduler.AppointmentFormDelete(); }";
}).GetHtml()
</td>
</tr>
</table> </table>
<table class="w-100"> <table class="w-100">
<tr> <tr>
<td style="width: 100%;"> <td style="width: 100%;">
@Html.DevExpress().SchedulerStatusInfo( @Html.DevExpress().SchedulerStatusInfo(
settings => settings =>
{ {
settings.Name = "schedulerStatusInfo"; settings.Name = "schedulerStatusInfo";
settings.Priority = 1; settings.Priority = 1;
settings.SchedulerName = "scheduler"; settings.SchedulerName = "scheduler";
}).GetHtml() }).GetHtml()
</td> </td>
</tr> </tr>
</table> </table>

View File

@@ -0,0 +1,120 @@
<script type="text/javascript">
function onAppointmentTipDisplaying(s, e) {
const currentApt = getCurrentApt();
if(currentApt.updated === false) {
scheduler.RefreshClientAppointmentProperties(currentApt, AppointmentPropertyNames.Normal, OnAppointmentRefresh);
setAptToolTipSubject("Lade...");
} else {
setAptToolTipSubject(currentApt.GetSubject());
}
const participationInfos = currentApt.ParticipationInfos;
const resourceInfos = currentApt.ResourceInfos;
const customerInfos = currentApt.CustomerInfos;
logInfo(`Mitarbeiter: ${participationInfos.length}\r\nKlienten: ${customerInfos.length}\r\nRessourcen: ${resourceInfos.length}`);
let bgClass = "";
$("#tool-tip-info").empty();
if(participationInfos.length > 0) {
$("#tool-tip-info").append(`<div id="participation-container"></div><hr class="m-1" />`);
$("#participation-container").append(`<span class="small pr-1">Mitarbeiter:</span>`);
participationInfos.forEach((info) => {
switch(info.ParticipationAnswer) {
case 1:
bgClass = "badge-bewo-apt-confirm";
break;
case 2:
bgClass = "badge-bewo-apt-decline";
break;
case 3:
bgClass = "badge-bewo-apt-maybe";
break;
default:
bgClass = "badge-light border";
break;
}
$("#participation-container").append(`<span class="badge ${bgClass}">${info.EmployeeName}</span>`);
});
}
if(customerInfos.length > 0) {
$("#tool-tip-info").append(`<div id="customers-container"></div><hr class="m-1" />`);
$("#customers-container").append(`<span class="small pr-1">Klienten:</span>`);
customerInfos.forEach((info) => {
$("#customers-container").append(`<span class="badge badge-light border">${info.CustomerName}</span>`);
});
}
if(resourceInfos.length > 0) {
$("#tool-tip-info").append(`<div id="resources-container"></div><hr class="m-1" />`);
$("#resources-container").append(`<span class="small pr-1">Ressourcen:</span>`);
resourceInfos.forEach((info) => {
logInfo2(`Farbe der Ressource <<${info.ResourceName}>>: ${info.ResourceColor}`);
$("#resources-container").append(`<span class="badge badge-light border"><div class="mr-1" style="display:inline-block;border-radius:3px;vertical-align:middle;width:10px;height:10px;border:1px slategray;background-color: ${info.ResourceColor};"></div>${info.ResourceName}</span>`);
});
}
$("#tool-tip-info").append(`<div id="originator-container"><span class="small">Angelegt von: ${currentApt.OriginatorName}</span></div>`);
const textInterval = e.toolTip.ConvertIntervalToString(currentApt.interval);
$('#tool-tip-title').html(textInterval);
if(currentApt.CanBeDeleted === false) {
$("#aptToolTipDelete").hide();
}
if(currentApt.CanBeEdited === false) {
if(currentApt.CanBeViewed) {
$("#aptToolTipEdit").text("Ansehen");
} else {
$("#aptToolTipEdit").hide();
}
}
}
function setAptToolTipSubject(text) {
$('#aptToolTipSubject').html(ASPx.Str.EncodeHtml(text));
}
function onAppointmentRefresh(apt) {
apt.updated = true;
setAptToolTipSubject(apt.GetSubject());
}
function getCurrentApt() {
return toolTipContext.data.GetAppointment();
}
function onAptToolTipDeleteClick() {
scheduler.DeleteAppointment(GetCurrentApt());
}
function onAptToolTipEditClick() {
scheduler.ShowAppointmentFormByClientId(getCurrentApt().GetId());
}
function onAptToolTipShowMenuClick() {
toolTipContext.toolTip.ShowAppointmentMenu();
}
</script>
<div class="card p-1" style="min-width: 200px;">
<div class="card-body p-1">
<p class="card-title font-weight-bold p-0" id="tool-tip-title"></p>
<div id="tool-tip-info">
<div id="employees-container"></div>
<div id="customers-container"></div>
<div id="resources-container"></div>
<div id="originator-container"></div>
</div>
</div>
</div>

View File

@@ -5,23 +5,30 @@
var areAllSelected = Model.SelectedCustomerOids.AreListEqual(Model.PossibleCustomers.Select(customer => customer.CustomerOid).ToList()); var areAllSelected = Model.SelectedCustomerOids.AreListEqual(Model.PossibleCustomers.Select(customer => customer.CustomerOid).ToList());
var allChecked = areAllSelected ? "checked" : string.Empty; var allChecked = areAllSelected ? "checked" : string.Empty;
var canEdit = Model.Oid.HasValue && Model.HasRightKalenderKlientenTermineAendern;
var canCreate = Model.Oid is null && Model.HasRightKalenderKlientenTermineAnlegen;
var checkBoxEnabled = canEdit || canCreate;
var disabled = checkBoxEnabled ? string.Empty : "disabled";
} }
<div class="dropdown w-100" id="customers-dropdown"> <div class="dropdown w-100" id="customers-dropdown">
<button class="btn btn-bewo-customers dropdown-toggle w-100" type="button" data-toggle="dropdown"> <button class="btn btn-bewo-customers dropdown-toggle w-100" type="button" data-toggle="dropdown">
Klienten <span class="badge badge-light">@Model.SelectedCustomerOids.Count</span> Klienten <span class="badge badge-light" id="apt-cus-badge">@Model.SelectedCustomerOids.Count</span>
</button> </button>
<div class="dropdown-menu" onclick="event.stopPropagation();"> <div class="dropdown-menu" onclick="event.stopPropagation();">
<div class="dropdown-item py-1 px-2"> <div class="dropdown-item py-1 px-2">
<div class="input-group input-group-sm"> <div class="input-group input-group-sm">
<div class="input-group-prepend"> <div class="input-group-prepend">
<div class="input-group-text"> <div class="input-group-text">
<input type="checkbox" @allChecked onclick="selectAllEmployeeCustomerResource('cus')" id="apt-cus-select-all"> <input type="checkbox" @disabled @allChecked onclick="selectAllEmployeeCustomerResource('cus')" id="apt-cus-select-all">
</div> </div>
</div> </div>
<input type="text" class="form-control" id="cus-drop-search-input" placeholder="Suchen ..." oninput="onNewSearchInput('cus')"> <input type="text" class="form-control" @disabled id="cus-drop-search-input" placeholder="Suchen ..." oninput="onNewSearchInput('cus')">
<div class="input-group-append"> <div class="input-group-append">
<button type="button" class="btn btn-outline-secondary" onclick="resetNewSearch('cus')"> <button type="button" class="btn btn-outline-secondary" @disabled onclick="resetNewSearch('cus')">
<span class="fas fa-times-circle"></span> <span class="fas fa-times-circle"></span>
</button> </button>
</div> </div>
@@ -39,7 +46,7 @@
<div class="dropdown-item w-100 @dNone" id="dropdown-item-@i"> <div class="dropdown-item w-100 @dNone" id="dropdown-item-@i">
<form class="form-inline justify-content-between"> <form class="form-inline justify-content-between">
<div class="form-group form-check"> <div class="form-group form-check">
<input class="form-check-input" type="checkbox" id="apt-edit-cus-@customer.CustomerOid" @isChecked onclick="updateEmployeeCustomerResourceSelection('cus')" /> <input class="form-check-input" @disabled type="checkbox" id="apt-edit-cus-@customer.CustomerOid" @isChecked onclick="updateEmployeeCustomerResourceSelection('cus')" />
<label for="apt-edit-cus-@customer.CustomerOid" class="form-check-label"> <label for="apt-edit-cus-@customer.CustomerOid" class="form-check-label">
@customer.DetailDescription @customer.DetailDescription
</label> </label>

View File

@@ -33,26 +33,32 @@
} }
@{ @{
var areAllSelected = Model.SelectedEmployee2SchedulerAppointments.Select(x => x.Employee.EmployeeOid).ToList().AreListEqual(Model.PossibleEmployees.Select(employee => employee.EmployeeOid).ToList()); var areAllSelected = Model.SelectedEmployee2SchedulerAppointments.Select(x => x.Employee.EmployeeOid).ToList().AreListEqual(Model.PossibleEmployees.Select(employee => employee.EmployeeOid).ToList());
var allChecked = areAllSelected ? "checked" : string.Empty; var allChecked = areAllSelected ? "checked" : string.Empty;
var isNew = Model.Oid is null;
var isEdit = isNew is false;
var checkBoxEnabled = isEdit && Model.HasRightKalenderMitarbeiterTermineAendern || isNew && Model.HasRightKalenderMitarbeiterTermineAnlegen;
var disabled = checkBoxEnabled is false || (Model.CanBeEdited is false && isNew is false) ? "disabled" : string.Empty;
} }
<div class="dropdown w-100" id="employees-dropdown"> <div class="dropdown w-100" id="employees-dropdown">
<button class="btn btn-bewo-employee dropdown-toggle w-100" type="button" data-toggle="dropdown"> <button class="btn btn-bewo-employee dropdown-toggle w-100" type="button" data-toggle="dropdown">
Mitarbeiter <span class="badge badge-light">@Model.SelectedEmployee2SchedulerAppointments.Count</span> Mitarbeiter <span class="badge badge-light" id="apt-emp-badge">@Model.SelectedEmployee2SchedulerAppointments.Count</span>
</button> </button>
<div class="dropdown-menu" onclick="event.stopPropagation();"> <div class="dropdown-menu" onclick="event.stopPropagation();">
<div class="dropdown-item py-1 px-2"> <div class="dropdown-item py-1 px-2">
<div class="input-group input-group-sm"> <div class="input-group input-group-sm">
<div class="input-group-prepend"> <div class="input-group-prepend">
<div class="input-group-text"> <div class="input-group-text">
<input type="checkbox" @allChecked onclick="selectAllEmployeeCustomerResource('emp')" id="apt-emp-select-all"> <input type="checkbox" @disabled @allChecked onclick="selectAllEmployeeCustomerResource('emp')" id="apt-emp-select-all">
</div> </div>
</div> </div>
<input type="text" class="form-control" id="emp-drop-search-input" placeholder="Suchen ..." oninput="onNewSearchInput('emp')"> <input type="text" class="form-control" @disabled id="emp-drop-search-input" placeholder="Suchen ..." oninput="onNewSearchInput('emp')">
<div class="input-group-append"> <div class="input-group-append">
<button type="button" class="btn btn-outline-secondary" onclick="resetNewSearch('emp')"> <button type="button" class="btn btn-outline-secondary" @disabled onclick="resetNewSearch('emp')">
<span class="fas fa-times-circle"></span> <span class="fas fa-times-circle"></span>
</button> </button>
</div> </div>
@@ -75,7 +81,7 @@
<div class="dropdown-item w-100 @dNone" id="dropdown-item-@i"> <div class="dropdown-item w-100 @dNone" id="dropdown-item-@i">
<form class="form-inline justify-content-between"> <form class="form-inline justify-content-between">
<div class="form-group form-check"> <div class="form-group form-check">
<input class="form-check-input" type="checkbox" id="apt-edit-emp-@employee.EmployeeOid" @isChecked onclick="updateEmployeeCustomerResourceSelection('emp')" /> <input class="form-check-input" @disabled type="checkbox" id="apt-edit-emp-@employee.EmployeeOid" @isChecked onclick="updateEmployeeCustomerResourceSelection('emp')" />
<label for="apt-edit-emp-@employee.EmployeeOid" class="form-check-label"> <label for="apt-edit-emp-@employee.EmployeeOid" class="form-check-label">
@employee.DetailDescription @employee.DetailDescription
</label> </label>

View File

@@ -19,18 +19,30 @@
} }
var checkedValue = areAllSelected ? "checked" : string.Empty; var checkedValue = areAllSelected ? "checked" : string.Empty;
var isOriginator = Model.OriginatorOid.HasValue && Model.OriginatorOid.Value == Model.LoggedInCompactEmployee.EmployeeOid;
var isNew = Model.Oid is null;
var canEditResApt = Model.HasRightKalenderRessourcenTermineAendern;
var canEditOthersResApt = Model.HasRightKalenderRessourcenTermineAndererAendern;
var canCreateResApt = Model.HasRightKalenderRessourcenTermineAnlegen;
var isDisabled = isNew is false && isOriginator is false && canEditOthersResApt is false ||
isNew is false && isOriginator && canEditResApt is false ||
isNew && canCreateResApt is false;
var disabled = isDisabled ? "disabled" : string.Empty;
} }
<div class="dropdown w-100" id="resources-dropdown"> <div class="dropdown w-100" id="resources-dropdown">
<button class="btn btn-bewo-resource dropdown-toggle w-100" type="button" data-toggle="dropdown"> <button class="btn btn-bewo-resource dropdown-toggle w-100" type="button" data-toggle="dropdown">
Ressourcen <span class="badge badge-light">@Model.SelectedResourceOids.Count</span> Ressourcen <span class="badge badge-light" id="apt-res-badge">@Model.SelectedResourceOids.Count</span>
</button> </button>
<div class="dropdown-menu" onclick="event.stopPropagation();"> <div class="dropdown-menu" onclick="event.stopPropagation();">
<div class="dropdown-item py-1 px-2"> <div class="dropdown-item py-1 px-2">
<div class="input-group input-group-sm"> <div class="input-group input-group-sm">
<div class="input-group-prepend"> <div class="input-group-prepend">
<div class="input-group-text"> <div class="input-group-text">
<input type="checkbox" @checkedValue onclick="selectAllEmployeeCustomerResource('res')" id="apt-res-select-all"> <input type="checkbox" @checkedValue @disabled onclick="selectAllEmployeeCustomerResource('res')" id="apt-res-select-all">
</div> </div>
</div> </div>
<input type="text" class="form-control" id="res-drop-search-input" placeholder="Suchen ..." oninput="onNewResourceSeachInput()"> <input type="text" class="form-control" id="res-drop-search-input" placeholder="Suchen ..." oninput="onNewResourceSeachInput()">
@@ -69,7 +81,7 @@
<form class="form-inline justify-content-between"> <form class="form-inline justify-content-between">
<div class="form-group form-check"> <div class="form-group form-check">
<input class="form-check-input" type="checkbox" id="apt-edit-res-@resource.ResourceOid.Value" @isChecked onclick="updateEmployeeCustomerResourceSelection('res')"/> <input class="form-check-input" @disabled type="checkbox" id="apt-edit-res-@resource.ResourceOid.Value" @isChecked onclick="updateEmployeeCustomerResourceSelection('res')"/>
<label for="apt-edit-res-@resource.ResourceOid.Value" class="form-check-label"> <label for="apt-edit-res-@resource.ResourceOid.Value" class="form-check-label">
@resource.DetailDescription @resource.DetailDescription
</label> </label>

View File

@@ -0,0 +1,14 @@
namespace BeWoPlanerMobil.Views.DevExpressScheduler
{
public class CustomerInfoObject
{
public long? AppointmentOid { get; }
public string CustomerName { get; }
public CustomerInfoObject(long? appointmentOid, string customerName)
{
AppointmentOid = appointmentOid;
CustomerName = customerName;
}
}
}

View File

@@ -1,50 +0,0 @@
@model BeWoPlanerMobil.Models.AppointmentModel
@using BS.Shared.DataContracts.Compact
@using DevExpress.Web.Mvc.UI
@Html.DevExpress().GridLookup(settings =>
{
settings.Name = "CustomerGridLookup";
settings.GridViewProperties.CallbackRouteValues = new { controller = "DevExpressScheduler", Action = "CustomerMultiSelectPartial" };
settings.KeyFieldName = nameof(CompactCustomerDC.CustomerOid);
settings.CommandColumn.ShowSelectCheckbox = true;
settings.CommandColumn.Visible = true;
settings.Columns.Add(c =>
{
c.FieldName = nameof(CompactCustomerDC.CustomerOid);
c.Visible = false;
});
settings.Columns.Add(c =>
{
c.FieldName = nameof(CompactCustomerDC.DetailDescription);
c.Caption = nameof(CompactCustomerDC.DetailDescription);
});
settings.Width = Unit.Percentage(100);
settings.Properties.SelectionMode = GridLookupSelectionMode.Multiple;
settings.Properties.TextFormatString = "{1}";
settings.Properties.MultiTextSeparator = "; ";
settings.Properties.Width = 250;
settings.Properties.NullText = "Klienten";
settings.GridViewProperties.Settings.ShowFilterRow = true;
settings.GridViewProperties.Settings.ShowStatusBar = GridViewStatusBarMode.Visible;
settings.GridViewProperties.SettingsPager.EnableAdaptivity = true;
settings.GridViewProperties.SettingsPager.PageSize = 7;
settings.GridViewProperties.SetStatusBarTemplateContent(c =>
{
ViewContext.Writer.Write("<div style=\"padding: 2px 8px 2px 0; float: right\">");
Html.DevExpress().Button(btnSettings =>
{
btnSettings.Name = "btnClose";
btnSettings.UseSubmitBehavior = false;
btnSettings.Text = "Schließen";
btnSettings.ClientSideEvents.Click = "CloseCustomerGridLookup";
}).Render();
ViewContext.Writer.Write("</div>");
});
}).BindList(Model.PossibleCustomers).Bind(Model.SelectedCustomerOids).GetHtml()

View File

@@ -1,4 +1,5 @@
@model BeWoPlanerMobil.Models.DevExpressSchedulerModel @using BeWoPlanerMobil.Util
@model BeWoPlanerMobil.Models.DevExpressSchedulerModel
@{ @{
ViewBag.Title = "DevExpressScheduler"; ViewBag.Title = "DevExpressScheduler";
@@ -96,28 +97,20 @@
} }
} }
function OnAppointmentFormCancel(s, e) {
scheduler.AppointmentFormCancel();
}
function OnAppointmentFormDelete(s, e) {
scheduler.AppointmentFormDelete();
}
function IsValidAppointment() { function IsValidAppointment() {
$.validator.unobtrusive.parse("form"); $.validator.unobtrusive.parse("form");
return $("form").valid(); return $("form").valid();
} }
function CloseCustomerGridLookup() {
CustomerGridLookup.ConfirmCurrentSelection();
CustomerGridLookup.HideDropDown();
}
// ToDo: Löschen
function CloseEmployeeGridLookup() {
EmployeeGridLookup.ConfirmCurrentSelection();
EmployeeGridLookup.HideDropDown();
}
function CloseResourceGridLookup() {
ResourceGridLookup.ConfirmCurrentSelection();
ResourceGridLookup.HideDropDown();
}
ASPxClientControl.GetControlCollection().ControlsInitialized.AddHandler(function(s, e) { ASPxClientControl.GetControlCollection().ControlsInitialized.AddHandler(function(s, e) {
UpdateSchedulerHeight(); UpdateSchedulerHeight();
}); });
@@ -255,12 +248,16 @@
}); });
} }
function performReload() { function performReload(shouldDoReloadNotifications) {
if(shouldDoReloadNotifications === false) {
return;
}
$("#scheduler-notification-container").load("@Url.Action("GetNotifications")"); $("#scheduler-notification-container").load("@Url.Action("GetNotifications")");
} }
function reloadScheduler() { function reloadScheduler(shouldDoReloadNotifications) {
scheduler.PerformCallback({ apptID: "", actionId: "Reload", args: null }, () => { performReload(); hideSpinner(); }); scheduler.PerformCallback({apptID: "", actionId: "Reload", args: null}, () => {performReload(shouldDoReloadNotifications); hideSpinner(); });
} }
@* CustomECRSelectionPartial *@ @* CustomECRSelectionPartial *@
@@ -424,7 +421,7 @@
function updateEmployeeCustomerResourceSelection(prefix) { function updateEmployeeCustomerResourceSelection(prefix) {
const checkedBoxes = $(`#dropdown-${prefix}-itm-container input[type=checkbox]:checked`); const checkedBoxes = $(`#dropdown-${prefix}-itm-container input[type=checkbox]:checked`);
var url = ""; var url = "";
switch(prefix) { switch(prefix) {
@@ -443,21 +440,24 @@
checkedBoxes.each(function() { checkedBoxes.each(function() {
const id = $(this).prop("id"); const id = $(this).prop("id");
const employeeOid = id.split("-")[3]; const employeeOid = id.split("-")[3];
selectedOids.push(employeeOid.toString()); selectedOids.push(employeeOid.toString());
}); });
showSpinner(); showSpinner();
$.get( $.get(
url, url,
{ selectedOids: selectedOids.join(", ") }, { selectedOids: selectedOids.join(", ") },
function() { function(elementCount) {
$(`#apt-${prefix}-badge`).text(elementCount);
hideSpinner(); hideSpinner();
}); });
} }
function selectAllEmployeeCustomerResource(prefix) { function selectAllEmployeeCustomerResource(prefix) {
const isChecked = $(`#apt-${prefix}-select-all`).prop("checked"); const isChecked = $(`#apt-${prefix}-select-all`).prop("checked");
@@ -505,7 +505,7 @@
} }
const resources = $(item).find("form"); const resources = $(item).find("form");
resources.hide(); resources.hide();
$.each(resources, function(resourceIndex, resourceItem) { $.each(resources, function(resourceIndex, resourceItem) {
@@ -550,10 +550,30 @@
$(form).show(); $(form).show();
}); });
}); });
collapse.collapse("show"); collapse.collapse("show");
} }
@* /CustomECRSelectionPartial *@ @* /CustomECRSelectionPartial *@
@* ToolTip *@
var toolTipContext;
function onToolTipDisplaying(s, e) {
toolTipContext = e;
switch(e.toolTip.type) {
case MVCxSchedulerToolTipType.Appointment:
onAppointmentTipDisplaying(s, e);
case MVCxSchedulerToolTipType.AppointmentDrag:
onAppointmentDragTipDisplaying(s, e);
break;
}
}
</script> </script>
<div class="dropdown"> <div class="dropdown">
@@ -569,113 +589,119 @@
} }
<div class="d-flex justify-content-center align-items-center"> <div class="d-flex justify-content-center align-items-center">
<button class="btn btn-primary dropdown-toggle m-1" type="button" data-toggle="dropdown"> @*@if(Html.IsInDebugMode())
{
<button type="button" class="btn btn-bewo-dev m-1" onclick='scheduler.PerformCallback({ apptID: "", actionId: "debug_DummyAppointments", args: null }, () => { performReload(true);hideSpinner(); });'>
Testtermine
</button>
}*@
<button class="btn btn-sm btn-primary dropdown-toggle m-1" type="button" data-toggle="dropdown">
Filtern Filtern
</button> </button>
<div class="dropdown-menu" id="filter-menu"> <div class="dropdown-menu" id="filter-menu">
<div class="dropdown-item"> <div class="dropdown-item">
<form class="form-inline"> <form class="form-inline">
<div class="form-group form-check"> <div class="form-group form-check">
<input type="checkbox" class="form-check-input" id="only-my-own-appointments-cb2" @isOnlyOwnAptsChecked onclick="filterAppointments()"> <input type="checkbox" class="form-check-input" id="only-my-own-appointments-cb2" @isOnlyOwnAptsChecked onclick="filterAppointments()">
<label class="form-check-label" for="only-my-own-appointments-cb2">Nur meine Termine</label> <label class="form-check-label" for="only-my-own-appointments-cb2">Nur meine Termine</label>
</div> </div>
</form> </form>
</div> </div>
<div class="dropdown-item"> <div class="dropdown-item">
<form class="form-inline"> <form class="form-inline">
<div class="form-group form-check"> <div class="form-group form-check">
<input type="checkbox" class="form-check-input" id="only-private-appointments-cb2" @isOnlyPrivateAptsChecked onclick="filterAppointments()"> <input type="checkbox" class="form-check-input" id="only-private-appointments-cb2" @isOnlyPrivateAptsChecked onclick="filterAppointments()">
<label class="form-check-label" for="only-private-appointments-cb2">Nur private Termine</label> <label class="form-check-label" for="only-private-appointments-cb2">Nur private Termine</label>
</div> </div>
</form> </form>
</div> </div>
<div class="dropdown-divider"></div> <div class="dropdown-divider"></div>
<div class="dropdown-item"> <div class="dropdown-item">
<form class="form-inline"> <form class="form-inline">
<div class="form-group form-check"> <div class="form-group form-check">
<input type="checkbox" class="form-check-input" id="employee-colors-cb2" @isEmployeeColorsChecked onclick="filterAppointments()"> <input type="checkbox" class="form-check-input" id="employee-colors-cb2" @isEmployeeColorsChecked onclick="filterAppointments()">
<label class="form-check-label" for="employee-colors-cb2">Mitarbeiterfarben</label> <label class="form-check-label" for="employee-colors-cb2">Mitarbeiterfarben</label>
</div> </div>
</form> </form>
</div> </div>
<div class="dropdown-item"> <div class="dropdown-item">
<form class="form-inline"> <form class="form-inline">
<div class="form-group form-check"> <div class="form-group form-check">
<input type="checkbox" class="form-check-input" id="absence-times-cb2" @isAbsenceTimesChecked onclick="filterAppointments()"> <input type="checkbox" class="form-check-input" id="absence-times-cb2" @isAbsenceTimesChecked onclick="filterAppointments()">
<label class="form-check-label" for="absence-times-cb2">Abwesenheiten</label> <label class="form-check-label" for="absence-times-cb2">Abwesenheiten</label>
</div> </div>
</form> </form>
</div> </div>
<div class="dropdown-item"> <div class="dropdown-item">
<form class="form-inline"> <form class="form-inline">
<div class="form-group form-check"> <div class="form-group form-check">
<input type="checkbox" class="form-check-input" id="tasks-cb2" @isTasksChecked onclick="filterAppointments()"> <input type="checkbox" class="form-check-input" id="tasks-cb2" @isTasksChecked onclick="filterAppointments()">
<label class="form-check-label" for="tasks-cb2">Aufgaben</label> <label class="form-check-label" for="tasks-cb2">Aufgaben</label>
</div> </div>
</form> </form>
</div> </div>
<div class="dropdown-divider"></div> <div class="dropdown-divider"></div>
<div class="dropdown-item"> <div class="dropdown-item">
<form class="form-inline"> <form class="form-inline">
<div class="form-group form-check"> <div class="form-group form-check">
<input type="checkbox" class="form-check-input" id="only-employees-cb2" @isOnlyEmployeesChecked onclick="filterAppointments()"> <input type="checkbox" class="form-check-input" id="only-employees-cb2" @isOnlyEmployeesChecked onclick="filterAppointments()">
<label class="form-check-label" for="only-employees-cb2">Nur Mitarbeiter</label> <label class="form-check-label" for="only-employees-cb2">Nur Mitarbeiter</label>
</div> </div>
</form> </form>
</div> </div>
<div class="dropdown-item"> <div class="dropdown-item">
<form class="form-inline"> <form class="form-inline">
<div class="form-group form-check"> <div class="form-group form-check">
<input type="checkbox" class="form-check-input" id="only-customers-cb2" @isOnlyCustomersChecked onclick="filterAppointments()"> <input type="checkbox" class="form-check-input" id="only-customers-cb2" @isOnlyCustomersChecked onclick="filterAppointments()">
<label class="form-check-label" for="only-customers-cb2">Nur Klienten</label> <label class="form-check-label" for="only-customers-cb2">Nur Klienten</label>
</div> </div>
</form> </form>
</div> </div>
<div class="dropdown-item"> <div class="dropdown-item">
<form class="form-inline"> <form class="form-inline">
<div class="form-group form-check"> <div class="form-group form-check">
<input type="checkbox" class="form-check-input" id="only-resources-cb2" @isOnlyResourcesChecked onclick="filterAppointments()"> <input type="checkbox" class="form-check-input" id="only-resources-cb2" @isOnlyResourcesChecked onclick="filterAppointments()">
<label class="form-check-label" for="only-resources-cb2">Nur Ressourcen</label> <label class="form-check-label" for="only-resources-cb2">Nur Ressourcen</label>
</div> </div>
</form> </form>
</div> </div>
<div class="dropdown-divider"></div> <div class="dropdown-divider"></div>
<div class="btn-toolbar dropdown-item justify-content-between" role="toolbar"> <div class="btn-toolbar dropdown-item justify-content-between" role="toolbar">
<a href="#" class="text-dark" onclick="$('#employees-popup-apt-flt').modal('show')"> <a href="#" class="text-dark" onclick="$('#employees-popup-apt-flt').modal('show')">
<i class="fas fa-user text-bewo-employee"></i> <i class="fas fa-user text-bewo-employee"></i>
Mitarbeiter Mitarbeiter
<span class="badge badge-bewo-employee" id="sel-emp-bdg">@Model.SelectedEmployeeOidsForFiltering.Count</span> <span class="badge badge-bewo-employee" id="sel-emp-bdg">@Model.SelectedEmployeeOidsForFiltering.Count</span>
</a> </a>
<button type="button" class="btn btn-sm btn-outline-danger" onclick="resetFilterSelection('employee')"> <button type="button" class="btn btn-sm btn-outline-danger" onclick="resetFilterSelection('employee')">
<i class="fas fa-times-circle"></i> <i class="fas fa-times-circle"></i>
</button> </button>
</div> </div>
<div class="btn-toolbar dropdown-item justify-content-between" role="toolbar"> <div class="btn-toolbar dropdown-item justify-content-between" role="toolbar">
<a href="#" class="text-dark" onclick="$('#customers-popup-apt-flt').modal('show')"> <a href="#" class="text-dark" onclick="$('#customers-popup-apt-flt').modal('show')">
<i class="fas fa-user text-bewo-customers"></i> <i class="fas fa-user text-bewo-customers"></i>
Klienten Klienten
<span class="badge badge-bewo-customers" id="sel-cus-bdg">@Model.SelectedCustomerOidsForFiltering.Count</span> <span class="badge badge-bewo-customers" id="sel-cus-bdg">@Model.SelectedCustomerOidsForFiltering.Count</span>
</a> </a>
<button type="button" class="btn btn-sm btn-outline-danger" onclick="resetFilterSelection('customer')"> <button type="button" class="btn btn-sm btn-outline-danger" onclick="resetFilterSelection('customer')">
<i class="fas fa-times-circle"></i> <i class="fas fa-times-circle"></i>
</button> </button>
</div> </div>
<div class="btn-toolbar dropdown-item justify-content-between" role="toolbar"> <div class="btn-toolbar dropdown-item justify-content-between" role="toolbar">
<a href="#" class="text-dark" onclick="$('#resources-popup-apt-flt').modal('show')"> <a href="#" class="text-dark" onclick="$('#resources-popup-apt-flt').modal('show')">
<i class="fas fa-cubes text-bewo-resource"></i> <i class="fas fa-cubes text-bewo-resource"></i>
Ressourcen Ressourcen
<span class="badge badge-bewo-resource" id="sel-res-bdg">@Model.SelectedResourceOidsForFiltering.Count</span> <span class="badge badge-bewo-resource" id="sel-res-bdg">@Model.SelectedResourceOidsForFiltering.Count</span>
</a> </a>
<button type="button" class="btn btn-sm btn-outline-danger" onclick="resetFilterSelection('resource')"> <button type="button" class="btn btn-sm btn-outline-danger" onclick="resetFilterSelection('resource')">
<i class="fas fa-times-circle"></i> <i class="fas fa-times-circle"></i>
</button> </button>
</div> </div>
</div> </div>
<button class="btn btn-success m-1 ml-0" type="button" onclick="scheduler.PerformCallback({apptID: '', actionId: 'Reload'}); performReload();"> <button class="btn btn-sm btn-success m-1 ml-0" type="button" onclick="scheduler.PerformCallback({ apptID: '', actionId: 'Reload' });performReload();">
<i class="fas fa-sync-alt"></i> <i class="fas fa-sync-alt"></i>
</button> </button>

View File

@@ -1,55 +0,0 @@
@model BeWoPlanerMobil.Models.AppointmentModel
@using BS.Shared.DataContracts.Compact
@using DevExpress.Web.Mvc.UI
@Html.DevExpress().GridLookup(settings =>
{
settings.Name = "EmployeeGridLookup";
settings.GridViewProperties.CallbackRouteValues = new { controller = "DevExpressScheduler", Action = "EmployeeGridLookupPartial" };
settings.KeyFieldName = nameof(CompactEmployeeDC.EmployeeOid);
settings.CommandColumn.ShowSelectCheckbox = true;
settings.CommandColumn.Visible = true;
settings.Columns.Add(c =>
{
c.FieldName = nameof(CompactEmployeeDC.EmployeeOid);
c.Visible = false;
});
settings.Columns.Add(c =>
{
c.FieldName = nameof(CompactEmployeeDC.DetailDescription);
c.Caption = "Name";
});
settings.Columns.Add(c =>
{
c.Width = Unit.Pixel(8);
c.CellStyle.BackColor = Color.Crimson;
});
settings.Width = Unit.Percentage(100);
settings.Properties.SelectionMode = GridLookupSelectionMode.Multiple;
settings.Properties.TextFormatString = "{1}";
settings.Properties.MultiTextSeparator = "; ";
settings.Properties.Width = 250;
settings.Properties.NullText = "Mitarbeiter";
settings.GridViewProperties.Settings.ShowFilterRow = true;
settings.GridViewProperties.Settings.ShowStatusBar = GridViewStatusBarMode.Visible;
settings.GridViewProperties.SettingsPager.EnableAdaptivity = true;
settings.GridViewProperties.SettingsPager.PageSize = 7;
settings.GridViewProperties.SetStatusBarTemplateContent(c =>
{
ViewContext.Writer.Write("<div style=\"padding: 2px 8px 2px 0; float: right\">");
Html.DevExpress().Button(btnSettings =>
{
btnSettings.Name = "btnClose3";
btnSettings.UseSubmitBehavior = false;
btnSettings.Text = "Schließen";
btnSettings.ClientSideEvents.Click = "CloseEmployeeGridLookup";
}).Render();
ViewContext.Writer.Write("</div>");
});
}).BindList(Model.PossibleEmployees).Bind(Model.SelectedEmployeeOids).GetHtml()

View File

@@ -1,11 +1,15 @@
@using BeWoPlanerMobil.Util @using BeWoPlanerMobil.Service
@using BeWoPlanerMobil.Util
@using BS.Shared.DataContracts @using BS.Shared.DataContracts
@using BS.Shared.DataContracts.Compact
@model DevExpress.XtraScheduler.Appointment @model DevExpress.XtraScheduler.Appointment
@functions @functions
{ {
string GetSubjectAndLocation() string GetSubjectAndLocation()
{ {
var locationPart = false == string.IsNullOrWhiteSpace(Model.Location) ? $" ({Model.Location})" : string.Empty; var locationPart = false == string.IsNullOrWhiteSpace(Model.Location) ? $" ({Model.Location})" : string.Empty;
return $" {Model.Subject}{locationPart}"; return $" {Model.Subject}{locationPart}";

View File

@@ -1,77 +0,0 @@
@model BeWoPlanerMobil.Models.DevExpressSchedulerModel
@{
var betreff = Model.Appointment2Answer?.Subject ?? string.Empty;
var ort = Model.Appointment2Answer?.Location ?? string.Empty;
var organisator = Model.Appointment2Answer?.Originator?.SimpleDescription ?? string.Empty;
var start = Model.Appointment2Answer?.HtmlInputStartFormat ?? string.Empty;
var ende = Model.Appointment2Answer?.HtmlInputEndFormat ?? string.Empty;
var notiz = Model.Appointment2Answer?.Description ?? string.Empty;
}
@if(Model.Appointment2Answer?.StartDate < DateTime.Now)
{
<div class="alert alert-danger mb-1" role="alert">
Dieser Termin liegt in der Vergangenheit
</div>
}
<div class="input-group mb-1">
<div class="input-group-prepend">
<span class="input-group-text notifications-prepend-text">Betreff</span>
</div>
<input class="form-control" type="text" disabled value="@betreff" />
</div>
<div class="input-group mb-1">
<div class="input-group-prepend">
<span class="input-group-text notifications-prepend-text">Ort</span>
</div>
<input class="form-control" type="text" disabled value="@ort" />
</div>
<div class="input-group mb-1">
<div class="input-group-prepend">
<span class="input-group-text notifications-prepend-text">Organisator</span>
</div>
<input class="form-control" type="text" disabled value="@organisator" />
</div>
<div class="input-group mb-1">
<div class="input-group-prepend">
<span class="input-group-text notifications-prepend-text">Start</span>
</div>
<input class="form-control" type="datetime-local" disabled value="@start" />
</div>
<div class="input-group mb-1">
<div class="input-group-prepend">
<span class="input-group-text notifications-prepend-text">Ende</span>
</div>
<input class="form-control" type="datetime-local" disabled value="@ende" />
</div>
<div class="input-group mb-1">
<div class="input-group-prepend">
<span class="input-group-text">Notiz</span>
</div>
<textarea class="form-control" disabled>@notiz</textarea>
</div>
<div class="btn-toolbar justify-content-between" role="toolbar">
@if(Model.OpenAppointments?.Any(openAppointment => openAppointment.EndDate is null || openAppointment.EndDate.Value > DateTime.Now) ?? false)
{
<button type="button" class="btn btn-primary" onclick="confirmAllOpenAppointments()">Allen zusagen</button>
}
@if(Model.Appointment2Answer != null)
{
if(Model.Appointment2Answer.EndDate is null || Model.Appointment2Answer.EndDate > DateTime.Now)
{
<div class="btn-group" role="group">
<button type="button" class="btn btn-outline-bewo-apt-confirm" onclick="answerAppointment(1)">Zusagen</button>
<button type="button" class="btn btn-outline-bewo-apt-maybe" onclick="answerAppointment(3)">Mit Vorbehalt</button>
<button type="button" class="btn btn-outline-bewo-apt-decline" onclick="answerAppointment(2)">Absagen</button>
</div>
}
else
{
<button type="button" class="btn btn-primary" onclick="answerAppointment(4)">OK</button>
}
}
</div>

View File

@@ -0,0 +1,10 @@
@model BeWoPlanerMobil.Models.DevExpressSchedulerModel
@if(Model.NotificationCount == 0)
{
<a href="#" class="disabled h-100 align-middle" style="text-decoration: underline;">keine Benachrichtigungen</a>
}
else
{
<a href="#" onclick="$('#notifications-popup').modal('show');">@Model.GetNotificationInfo()</a>
}

View File

@@ -2,31 +2,11 @@
<div class="row"> <div class="row">
<div class="col-4"> <div class="col-4">
<div class="list-group"> <div class="list-group" id="open-emp-app-list">
@if(Model.OpenAppointments != null) @Html.Partial("OpenEmployee2AppointmentListPartial", Model)
{
foreach(var appointment in Model.OpenAppointments)
{
var active = string.Empty;
if(Model.Appointment2Answer?.SchedulerAppointmentOid != null && appointment.SchedulerAppointmentOid.HasValue)
{
if(Model.Appointment2Answer.SchedulerAppointmentOid.Value == appointment.SchedulerAppointmentOid.Value)
{
active = "active";
}
}
var text = $"{appointment.StartDate:dd.MM.yyyy}: {appointment.Subject}";
<a href="#" class="list-group-item list-group-item-action open-apt-list-group-item @active" id="open-apt-@appointment.SchedulerAppointmentOid" onclick="selectAppointmentToAnswer(@appointment.SchedulerAppointmentOid)">
@text
</a>
}
}
</div> </div>
</div> </div>
<div class="col-8" id="apt-answering-form"> <div class="col-8" id="apt-answering-form">
@Html.Partial("NotificationPopupContent", Model) @Html.Partial("SelectedOpenEmployee2AppointmentFormPartial", Model)
</div> </div>
</div> </div>

View File

@@ -0,0 +1,64 @@
@using BS.Shared
@using BS.Shared.DataContracts
@model BeWoPlanerMobil.Models.DevExpressSchedulerModel
@functions
{
string GetInfoString(Employee2SchedulerAppointmentDC employee2AppointmentRel, SchedulerAppointmentDC appointment)
{
var timeAndDateInfo = $"{appointment.StartDate:dd.MM.yyyy}:";
if(employee2AppointmentRel.Employee.Equals(Model.LoggedInCompactEmployee))
{
return $"{timeAndDateInfo} {appointment.Subject}";
}
var employeeName = employee2AppointmentRel.Employee.DetailDescription;
var participationAnswer = employee2AppointmentRel.ParticipationAnswer;
var answer = string.Empty;
switch(participationAnswer)
{
case ParticipationAnswer.Zusage:
answer = "zugesagt";
break;
case ParticipationAnswer.Vorbehalt:
answer = "mit Vorbehalt zugesagt";
break;
case ParticipationAnswer.Absage:
answer = "abgesagt";
break;
}
return $"{timeAndDateInfo} {employeeName} hat {answer}";
}
}
@if(Model.OpenEmployee2AppointmentRels != null)
{
foreach(var employee2AppointmentRel in Model.OpenEmployee2AppointmentRels)
{
var appointment = Model.GetAppointment2AnswerByOid(employee2AppointmentRel.SchedulerAppointmentOid.Value);
if(appointment is null)
{
continue;
}
var active = string.Empty;
if(Model.AppointmentToAnswerOrUpdate?.SchedulerAppointmentOid != null && employee2AppointmentRel.SchedulerAppointmentOid.HasValue)
{
if(Model.AppointmentToAnswerOrUpdate.SchedulerAppointmentOid.Value == employee2AppointmentRel.SchedulerAppointmentOid.Value)
{
active = "active";
}
}
<a href="#" class="list-group-item list-group-item-action open-apt-list-group-item @active" id="open-apt-@employee2AppointmentRel.Employee2SchedulerAppointmentOid" onclick="selectAppointmentToAnswer(@employee2AppointmentRel.Employee2SchedulerAppointmentOid)">
@GetInfoString(employee2AppointmentRel, appointment)
</a>
}
}

View File

@@ -0,0 +1,18 @@
namespace BeWoPlanerMobil.Views.DevExpressScheduler
{
public class ParticipationInfoObject
{
public string EmployeeName { get; }
public long Employee2AppointmentOid { get; }
public long AppointmentOid { get; }
public int ParticipationAnswer { get; }
public ParticipationInfoObject(string employeeName, long employee2AppointmentOid, int participationAnswer, long appointmentOid)
{
EmployeeName = employeeName;
Employee2AppointmentOid = employee2AppointmentOid;
ParticipationAnswer = participationAnswer;
AppointmentOid = appointmentOid;
}
}
}

View File

@@ -0,0 +1,20 @@
namespace BeWoPlanerMobil.Views.DevExpressScheduler
{
public class ResourceInfoObject
{
public long? AppointmentOid { get; }
public string ResourceName { get; }
public string ResourceColor { get; }
public ResourceInfoObject(long? appointmentOid, string resourceName, string resourceColor)
{
AppointmentOid = appointmentOid;
ResourceName = resourceName;
if(resourceColor?.Length > 0)
{
ResourceColor = "#" + resourceColor.Substring(3);
}
}
}
}

View File

@@ -1,48 +0,0 @@
@model BeWoPlanerMobil.Models.AppointmentModel
@using BS.Shared.DataContracts
@using DevExpress.Web.Mvc.UI
@Html.DevExpress().GridLookup(settings =>
{
settings.Name = "ResourceGridLookup";
settings.GridViewProperties.CallbackRouteValues = new { Controller = "DevExpressScheduler", Action = "ResourceGridLookupPartial" };
settings.KeyFieldName = nameof(ResourceDC.ResourceOid);
settings.CommandColumn.ShowSelectCheckbox = true;
settings.CommandColumn.Visible = true;
settings.Columns.Add(c =>
{
c.FieldName = nameof(ResourceDC.ResourceOid);
c.Visible = false;
});
settings.Columns.Add(c =>
{
c.FieldName = nameof(ResourceDC.Name);
c.Caption = nameof(ResourceDC.Name);
});
settings.Width = Unit.Percentage(100);
settings.Properties.SelectionMode = GridLookupSelectionMode.Multiple;
settings.Properties.TextFormatString = "{1}";
settings.Properties.MultiTextSeparator = "; ";
settings.Properties.NullText = "Ressourcen";
settings.GridViewProperties.Settings.ShowFilterRow = true;
settings.GridViewProperties.Settings.ShowStatusBar = GridViewStatusBarMode.Visible;
settings.GridViewProperties.SettingsPager.EnableAdaptivity = true;
settings.GridViewProperties.SettingsPager.PageSize = 7;
settings.GridViewProperties.SetStatusBarTemplateContent(c =>
{
ViewContext.Writer.Write("<div style=\"padding: 2px 8px 2px 0; float: right\">");
Html.DevExpress().Button(btnSettings =>
{
btnSettings.Name = "btnClose2";
btnSettings.UseSubmitBehavior = false;
btnSettings.Text = "Schließen";
btnSettings.ClientSideEvents.Click = "CloseResourceGridLookup";
}).Render();
ViewContext.Writer.Write("</div>");
});
}).BindList(Model.PossibleResources).Bind(Model.SelectedResourceOids).GetHtml()

View File

@@ -54,6 +54,10 @@ namespace BeWoPlanerMobil.Views.DevExpressScheduler
appointmentStorage.CustomFieldMappings.Add(new ASPxAppointmentCustomFieldMapping("CompletedUser", "CompletedUser")); appointmentStorage.CustomFieldMappings.Add(new ASPxAppointmentCustomFieldMapping("CompletedUser", "CompletedUser"));
appointmentStorage.CustomFieldMappings.Add(new ASPxAppointmentCustomFieldMapping("TaskDescription", "TaskDescription")); appointmentStorage.CustomFieldMappings.Add(new ASPxAppointmentCustomFieldMapping("TaskDescription", "TaskDescription"));
appointmentStorage.CustomFieldMappings.Add(new ASPxAppointmentCustomFieldMapping("ShowEmployeeColors", "ShowEmployeeColors"));
appointmentStorage.CustomFieldMappings.Add(new ASPxAppointmentCustomFieldMapping("CanBeViewed", "CanBeViewed"));
appointmentStorage.CustomFieldMappings.Add(new ASPxAppointmentCustomFieldMapping("CanBeDeleted", "CanBeDeleted"));
return appointmentStorage; return appointmentStorage;
} }

View File

@@ -1,22 +1,5 @@
@model BeWoPlanerMobil.Models.DevExpressSchedulerModel @model BeWoPlanerMobil.Models.DevExpressSchedulerModel
@functions
{
string GetNotificationInfo()
{
return $"{Model.NotificationCount} Benachrichtigung{(Model.NotificationCount == 1 ? string.Empty : "en")}";
}
}
@if(Model.NotificationCount == 0)
{
<a href="#" class="disabled h-100 align-middle" style="text-decoration: underline;">keine Benachrichtigungen</a>
}
else
{
<a href="#" onclick="$('#notifications-popup').modal('show');">@GetNotificationInfo()</a>
}
<script type="text/javascript"> <script type="text/javascript">
$(document).ready(function() { $(document).ready(function() {
$("#notifications-popup").on("shown.bs.modal", function(e) { $("#notifications-popup").on("shown.bs.modal", function(e) {
@@ -50,37 +33,59 @@ else
} }
function answerAppointment(answer) { function answerAppointment(answer) {
showSpinner(); showSpinner();
$("#notifications-popup-modal-body").load("@Url.Action("AnswerOpenAppointment")", {answer: answer}, () => { $("#notifications-popup-modal-body").load("@Url.Action("AnswerOpenAppointment")", {answer: answer}, () => {
reloadScheduler(); $("#notifications-popup").modal("show");
reloadScheduler(false);
$("#open-emp-app-list").load("@Url.Action("ReloadOpenAppointments")");
$.get("@Url.Action("GetOpenEmp2AppRelCount")", function(openRelCount) {
const count = parseInt(openRelCount);
const text = count === 0 ? "Keine Benachrichtigungen" : count === 1 ? "1 Benachrichtigung" : `${count} Benachrichtigungen`;
$("#notifications-popup-header").text(text);
$("#link-partial-container").load("@Url.Action("UpdateOpenEmp2AppCount")");
if(count === 0) {
$("#notifications-popup").modal("hide");
}
});
}); });
} }
function confirmAllOpenAppointments() { function confirmAllOpenAppointments() {
showSpinner(); showSpinner();
$("#notifications-popup-modal-body").load("@Url.Action("ConfirmAllOpenAppointments")", () => { $("#notifications-popup-modal-body").load("@Url.Action("ConfirmAllOpenAppointments")", () => {
$("#notifications-popup").modal("hide"); $("#link-partial-container").load("@Url.Action("UpdateOpenEmp2AppCount")", () => {
$("#notifications-popup").modal("hide");
reloadScheduler();
});
});
}
reloadScheduler(); @if(Model.OpenEmployee2AppointmentRelOids.Count == 0)
});
}
@if(Model.OpenAppointments.Count == 0)
{ {
<text> <text>
$("#notifications-popup").modal("hide"); $("#notifications-popup").modal("hide");
</text> </text>
} }
</script> </script>
<div id="link-partial-container">
@Html.Partial("NotificationsLinkPartial", Model)
</div>
<div class="modal" tabindex="-1" role="dialog" id="notifications-popup"> <div class="modal" tabindex="-1" role="dialog" id="notifications-popup">
<div class="modal-dialog modal-dialog-scrollable modal-lg" role="document"> <div class="modal-dialog modal-dialog-scrollable modal-lg" role="document">
<div class="modal-content"> <div class="modal-content">
<div class="modal-header"> <div class="modal-header">
<h6 class="modal-title text-center w-100 font-weight-bold"> <h6 class="modal-title text-center w-100 font-weight-bold" id="notifications-popup-header">
@GetNotificationInfo() @Model.GetNotificationInfo()
</h6> </h6>
<button type="button" class="close" data-dismiss="modal"> <button type="button" class="close" data-dismiss="modal">
<span>&times;</span> <span>&times;</span>

View File

@@ -149,6 +149,37 @@
} }
} }
} }
void AllowAppointmentEdit(object o, AppointmentOperationEventArgs e)
{
var hasRightToViewAppointment = true;
var appointment = e.Appointment;
var isAbsenceTime = appointment.CustomFields["IsAbsenceTime"] is true;
if(isAbsenceTime)
{
e.Allow = false;
return;
}
var originator = appointment.CustomFields["Originator"] as CompactEmployeeDC;
var employeeList = appointment.CustomFields["Employees"] as List<Employee2SchedulerAppointmentDC>;
var isOriginator = originator?.EmployeeOid.Equals(Model.LoggedInUserOid) ?? false;
var isPrivate = appointment.CustomFields["IsPrivate"] is true;
if(false == isOriginator && isPrivate && false == (employeeList?.Any(e2A => Equals(e2A.Employee, Model.LoggedInCompactEmployee)) ?? false))
{
hasRightToViewAppointment = false;
}
e.Allow = hasRightToViewAppointment;
}
void AllowAppointmentCreate(object o, AppointmentOperationEventArgs e)
{
e.Allow = Model.HasRightKalenderAnsehen || Model.HasRightKalenderKlientenTermineAnlegen || Model.HasRightKalenderMitarbeiterTermineAnlegen;
}
} }
@{ @{
@@ -160,24 +191,119 @@
settings.CallbackRouteValues = new { Controller = "DevExpressScheduler", Action = "SchedulerPagePartial" }; settings.CallbackRouteValues = new { Controller = "DevExpressScheduler", Action = "SchedulerPagePartial" };
settings.EditAppointmentRouteValues = new { Controller = "DevExpressScheduler", Action = "EditAppointment" }; settings.EditAppointmentRouteValues = new { Controller = "DevExpressScheduler", Action = "EditAppointment" };
settings.CustomActionRouteValues = new { Controller = "DevExpressScheduler", Action = "CustomCallBackAction" }; settings.CustomActionRouteValues = new { Controller = "DevExpressScheduler", Action = "CustomCallBackAction" };
settings.ClientSideEvents.ToolTipDisplaying = "onToolTipDisplaying";
settings.OptionsToolTips.SetAppointmentToolTipTemplateContent(() =>
{
Html.RenderPartial("CustomAppointmentToolTipPartial");
});
settings.OptionsToolTips.SetAppointmentMobileToolTipTemplateContent(() => { Html.RenderPartial("CustomAppointmentToolTipPartial"); });
settings.OptionsToolTips.SetAppointmentDragToolTipTemplateContent(() =>
{
Html.RenderPartial("CustomAppointmentDragToolTip");
});
settings.OptionsCustomization.AllowInplaceEditor = UsedAppointmentType.None;
settings.OptionsCustomization.AllowDisplayAppointmentFlyout = false;
settings.ActiveViewType = Model.CurrentViewType; settings.ActiveViewType = Model.CurrentViewType;
settings.OptionsView.VerticalScrollBarMode = ScrollBarMode.Auto; settings.OptionsView.VerticalScrollBarMode = ScrollBarMode.Auto;
settings.OptionsToolTips.ShowSelectionToolTip = false; settings.OptionsToolTips.ShowSelectionToolTip = false;
settings.ClientSideEvents.ActiveViewChanging = "onActiveViewChanged"; settings.ClientSideEvents.ActiveViewChanging = "onActiveViewChanged";
settings.ClientSideEvents.MenuItemClicked = "onMenuItemClicked"; settings.ClientSideEvents.MenuItemClicked = "onMenuItemClicked";
settings.OptionsCustomization.AllowAppointmentEdit = UsedAppointmentType.Custom;
settings.OptionsCustomization.AllowAppointmentCopy = UsedAppointmentType.Custom;
settings.OptionsCustomization.AllowAppointmentCreate = UsedAppointmentType.Custom;
settings.OptionsCustomization.AllowAppointmentResize = UsedAppointmentType.Custom;
settings.OptionsCustomization.AllowAppointmentDrag = UsedAppointmentType.Custom;
settings.OptionsCustomization.AllowAppointmentDelete = UsedAppointmentType.Custom;
settings.AllowAppointmentEdit = AllowAppointmentEdit;
settings.AllowAppointmentDrag = AllowAppointmentEdit;
settings.AllowAppointmentResize = AllowAppointmentEdit;
settings.AllowAppointmentCreate = AllowAppointmentCreate;
settings.InitClientAppointment = (send, evargs) => settings.InitClientAppointment = (send, evargs) =>
{ {
var isTask = evargs.Appointment.CustomFields["IsTask"] is true;
var isAbsenceTime = evargs.Appointment.CustomFields["IsAbsenceTime"] is true;
var canBeEdited = evargs.Appointment.CustomFields["CanBeEdited"] is true;
var canBeViewed = evargs.Appointment.CustomFields["CanBeViewed"] is true;
var canBeDeleted = evargs.Appointment.CustomFields["CanBeDeleted"] is true;
var customerList = (List<CompactCustomerDC>) evargs.Appointment.CustomFields["Customers"] ?? new List<CompactCustomerDC>();
var resourceList = (List<ResourceDC>) evargs.Appointment.CustomFields["Resources"] ?? new List<ResourceDC>();
evargs.Properties.Add("IsAbsenceTime", evargs.Appointment.CustomFields["IsAbsenceTime"]); evargs.Properties.Add("IsAbsenceTime", evargs.Appointment.CustomFields["IsAbsenceTime"]);
evargs.Properties.Add("IsTask", evargs.Appointment.CustomFields["IsTask"]); evargs.Properties.Add("IsTask", evargs.Appointment.CustomFields["IsTask"]);
evargs.Properties.Add("CanBeViewed", canBeViewed);
evargs.Properties.Add("CanBeEdited", canBeEdited);
evargs.Properties.Add("CanBeDeleted", canBeDeleted);
var oid = (long?) evargs.Appointment.Id;
var end = evargs.Appointment.End; var end = evargs.Appointment.End;
var originator = (CompactEmployeeDC) evargs.Appointment.CustomFields["Originator"]; var originator = (CompactEmployeeDC) evargs.Appointment.CustomFields["Originator"];
var employeeList = (List<Employee2SchedulerAppointmentDC>) evargs.Appointment.CustomFields["Employees"]; var employeeList = (List<Employee2SchedulerAppointmentDC>) evargs.Appointment.CustomFields["Employees"] ?? new List<Employee2SchedulerAppointmentDC>();
var canConfirm = end > DateTime.Now && evargs.Properties.Add("OriginatorName", originator.DetailDescription);
false == originator.EmployeeOid.Equals(Model.LoggedInUserOid) &&
var participationInfos = new List<ParticipationInfoObject>();
var customerInfos = new List<CustomerInfoObject>();
var resourceInfos = new List<ResourceInfoObject>();
foreach(var employee2Appointment in employeeList)
{
if(employee2Appointment.SchedulerAppointmentOid is null || employee2Appointment.Employee2SchedulerAppointmentOid is null)
{
continue;
}
var parcitipationInfoObject =
new ParticipationInfoObject(
employee2Appointment.Employee.DetailDescription,
employee2Appointment.Employee2SchedulerAppointmentOid.Value,
(int) employee2Appointment.ParticipationAnswer,
employee2Appointment.SchedulerAppointmentOid.Value);
participationInfos.Add(parcitipationInfoObject);
}
foreach(var resource in resourceList)
{
var resourceInfoObject =
new ResourceInfoObject(
oid,
resource.Name,
resource.Color
);
resourceInfos.Add(resourceInfoObject);
}
foreach(var customer in customerList)
{
var customerInfoObject =
new CustomerInfoObject(
oid,
customer.DetailDescription
);
customerInfos.Add(customerInfoObject);
}
evargs.Properties.Add("ParticipationInfos", participationInfos);
evargs.Properties.Add("ResourceInfos", resourceInfos);
evargs.Properties.Add("CustomerInfos", customerInfos);
// originator ist bei einer Aufgabe null
var canConfirm = (false == isTask || false == isAbsenceTime) && end > DateTime.Now &&
false == (originator?.EmployeeOid.Equals(Model.LoggedInUserOid) ?? false) &&
employeeList.Any(employee2Appointment => employee2Appointment.Employee.EmployeeOid.Equals(Model.LoggedInUserOid)); employeeList.Any(employee2Appointment => employee2Appointment.Employee.EmployeeOid.Equals(Model.LoggedInUserOid));
evargs.Properties.Add("CanConfirm", canConfirm); evargs.Properties.Add("CanConfirm", canConfirm);
@@ -234,13 +360,12 @@
var oid = (long?) container.Appointment.Id; var oid = (long?) container.Appointment.Id;
// Die bereits ausgewählten Mitarbeiter-Termin-Relationen beim Bearbeiten:
var employees2Appointment = container.Appointment.CustomFields["Employees"] as List<Employee2SchedulerAppointmentDC> ?? new List<Employee2SchedulerAppointmentDC>(); var employees2Appointment = container.Appointment.CustomFields["Employees"] as List<Employee2SchedulerAppointmentDC> ?? new List<Employee2SchedulerAppointmentDC>();
var customerList = container.Appointment.CustomFields["Customers"] as List<CompactCustomerDC>; var customerList = container.Appointment.CustomFields["Customers"] as List<CompactCustomerDC> ?? new List<CompactCustomerDC>();
var resourceList = container.Appointment.CustomFields["Resources"] as List<ResourceDC>; var resourceList = container.Appointment.CustomFields["Resources"] as List<ResourceDC> ?? new List<ResourceDC>();
var newModel = new AppointmentModel(Model.PossibleCustomers, Model.PossibleResources, Model.PossibleEmployees) var newModel = new AppointmentModel(Model.PossibleCustomers, Model.PossibleResources, Model.PossibleEmployees, Model.LoggedInUser, customerList, resourceList, employees2Appointment)
{ {
Oid = oid, Oid = oid,
Subject = container.Appointment.Subject, Subject = container.Appointment.Subject,
@@ -250,12 +375,6 @@
AllDay = container.Appointment.AllDay, AllDay = container.Appointment.AllDay,
Description = container.Appointment.Description, Description = container.Appointment.Description,
EventType = (int?)container.Appointment.Type, EventType = (int?)container.Appointment.Type,
SelectedEmployee2SchedulerAppointments = employees2Appointment,
SelectedCustomers = customerList,
SelectedResources = resourceList,
SelectedCustomerOids = customerList?.Select(customer => customer.CustomerOid)?.ToList() ?? new List<long>(),
SelectedResourceOids = resourceList?.Select(resource => resource.ResourceOid.Value)?.ToList() ?? new List<long>(),
SelectedEmployeeOids = employees2Appointment.Select(employee2Appointment => employee2Appointment.Employee.EmployeeOid).ToList(),
CompletedNotice = container.Appointment.CustomFields["CompletedNotice"]?.ToString(), CompletedNotice = container.Appointment.CustomFields["CompletedNotice"]?.ToString(),
CompletedUser = container.Appointment.CustomFields["CompletedUser"]?.ToString(), CompletedUser = container.Appointment.CustomFields["CompletedUser"]?.ToString(),
TaskDescription = container.Appointment.CustomFields["TaskDescription"]?.ToString(), TaskDescription = container.Appointment.CustomFields["TaskDescription"]?.ToString(),
@@ -264,7 +383,8 @@
IsPrivate = container.Appointment.CustomFields["IsPrivate"] is true, IsPrivate = container.Appointment.CustomFields["IsPrivate"] is true,
IsTask = container.Appointment.CustomFields["IsTask"] is true, IsTask = container.Appointment.CustomFields["IsTask"] is true,
DueDate = container.Appointment.CustomFields["DueDate"] is DateTime dueDate ? dueDate : null, DueDate = container.Appointment.CustomFields["DueDate"] is DateTime dueDate ? dueDate : null,
CompletedDate = container.Appointment.CustomFields["CompletedDate"] is DateTime completedDate ? completedDate : null CompletedDate = container.Appointment.CustomFields["CompletedDate"] is DateTime completedDate ? completedDate : null,
OriginatorOid = (container.Appointment.CustomFields["Originator"] as CompactEmployeeDC)?.EmployeeOid
}; };
var appointmentModel = ViewData["EditableAppointmentModel"] != null ? (AppointmentModel)ViewData["EditableAppointmentModel"] : newModel; var appointmentModel = ViewData["EditableAppointmentModel"] != null ? (AppointmentModel)ViewData["EditableAppointmentModel"] : newModel;

View File

@@ -0,0 +1,86 @@
@model BeWoPlanerMobil.Models.DevExpressSchedulerModel
@{
var betreff = Model.AppointmentToAnswerOrUpdate?.Subject ?? string.Empty;
var ort = Model.AppointmentToAnswerOrUpdate?.Location ?? string.Empty;
var organisator = Model.AppointmentToAnswerOrUpdate?.Originator?.SimpleDescription ?? string.Empty;
var start = Model.AppointmentToAnswerOrUpdate?.HtmlInputStartFormat ?? string.Empty;
var ende = Model.AppointmentToAnswerOrUpdate?.HtmlInputEndFormat ?? string.Empty;
var notiz = Model.AppointmentToAnswerOrUpdate?.Description ?? string.Empty;
}
@if(Model.AppointmentToAnswerOrUpdate?.StartDate < DateTime.Now)
{
<div class="alert alert-danger mb-1" role="alert">
Dieser Termin liegt in der Vergangenheit
</div>
}
<div class="input-group mb-1">
<div class="input-group-prepend">
<span class="input-group-text notifications-prepend-text">Betreff</span>
</div>
<input class="form-control" type="text" disabled value="@betreff" />
</div>
<div class="input-group mb-1">
<div class="input-group-prepend">
<span class="input-group-text notifications-prepend-text">Ort</span>
</div>
<input class="form-control" type="text" disabled value="@ort" />
</div>
<div class="input-group mb-1">
<div class="input-group-prepend">
<span class="input-group-text notifications-prepend-text">Organisator</span>
</div>
<input class="form-control" type="text" disabled value="@organisator" />
</div>
<div class="input-group mb-1">
<div class="input-group-prepend">
<span class="input-group-text notifications-prepend-text">Start</span>
</div>
<input class="form-control" type="datetime-local" disabled value="@start" />
</div>
<div class="input-group mb-1">
<div class="input-group-prepend">
<span class="input-group-text notifications-prepend-text">Ende</span>
</div>
<input class="form-control" type="datetime-local" disabled value="@ende" />
</div>
<div class="input-group mb-1">
<div class="input-group-prepend">
<span class="input-group-text">Notiz</span>
</div>
<textarea class="form-control" disabled>@notiz</textarea>
</div>
<div class="btn-toolbar justify-content-between" role="toolbar">
@if(Model.CanConfirmAllOpenAppointments())
{
<button type="button" class="btn btn-primary" onclick="confirmAllOpenAppointments()">Allen zusagen</button>
}
@if(Model.AppointmentToAnswerOrUpdate != null)
{
var isOwnAppointment = Model.AppointmentToAnswerOrUpdate.Originator?.Equals(Model.LoggedInCompactEmployee) ?? false;
if(isOwnAppointment)
{
<button type="button" class="btn btn-primary" onclick="answerAppointment(5)">OK</button>
}
else
{
if(Model.AppointmentToAnswerOrUpdate.EndDate is null || Model.AppointmentToAnswerOrUpdate.EndDate > DateTime.Now)
{
<div class="btn-group" role="group">
<button type="button" class="btn btn-outline-bewo-apt-confirm" onclick="answerAppointment(1)">Zusagen</button>
<button type="button" class="btn btn-outline-bewo-apt-maybe" onclick="answerAppointment(3)">Mit Vorbehalt</button>
<button type="button" class="btn btn-outline-bewo-apt-decline" onclick="answerAppointment(2)">Absagen</button>
</div>
}
else
{
<button type="button" class="btn btn-primary" onclick="answerAppointment(4)">OK</button>
}
}
}
</div>

View File

@@ -1,5 +1,7 @@
@using BeWoPlanerMobil.Util @using BeWoPlanerMobil.Service
@using BeWoPlanerMobil.Util
@using BS.Shared.DataContracts @using BS.Shared.DataContracts
@using BS.Shared.DataContracts.Compact
@using DevExpress.Web.ASPxScheduler.Drawing @using DevExpress.Web.ASPxScheduler.Drawing
@model AppointmentViewInfo @model AppointmentViewInfo

View File

@@ -80,6 +80,42 @@
<link type="text/css" rel="stylesheet" href="@Url.Content("~/Content/dx.common.css")" /> <link type="text/css" rel="stylesheet" href="@Url.Content("~/Content/dx.common.css")" />
<link type="text/css" rel="stylesheet" href="@Url.Content("~/Content/dx.light.css")" /> <link type="text/css" rel="stylesheet" href="@Url.Content("~/Content/dx.light.css")" />
@* CSS für den neuen Kalender-Tooltip *@
<style type="text/css">
.toolTipPanel {
box-shadow: 3px 3px 20px Gray;
background-color: White;
width: 300px;
}
.toolTipPanelHeader {
padding-right: 8px !important;
}
.toolTipPanel .dxrpHeader_Metropolis, .toolTipPanel .dxrpHeader_MetropolisBlue {
border-bottom: 1px solid rgba(192, 192, 192, 1);
}
.toolTipLablel {
color: Black;
font-family: Tahoma;
font-size: 10pt;
}
.dxrpHeader_BlackGlass .toolTipLablel, .dxrpHeader_RedWine .toolTipLablel {
color: White;
}
.toolTipCloseButton {
float: right;
}
.toolTipButton {
float: right;
margin: 5px 0px 6px 5px;
}
</style>
@Html.DevExpress().GetStyleSheets( @Html.DevExpress().GetStyleSheets(
ASPxWebClientUIControl.ColorSchemeLight, ASPxWebClientUIControl.ColorSchemeLight,

View File

@@ -1,5 +1,6 @@
using System; using System;
using System.Collections.Generic; using System.Collections.Generic;
using System.Linq;
using BS.Shared.DataContracts; using BS.Shared.DataContracts;
using BS.Shared.Extensions; using BS.Shared.Extensions;

View File

@@ -162,6 +162,10 @@ namespace BS.Shared.DataContracts
[DataMember] [DataMember]
public List<ServiceRecordDC> ServiceRecordList { get; set; } public List<ServiceRecordDC> ServiceRecordList { get; set; }
// Nur im DC, damit man im MoK-Scheduler als CustomField darauf zugreifen kann.
public bool ShowEmployeeColors { get; set; }
public bool CanBeViewed { get; set; } = true;
public bool CanBeDeleted { get; set; } = true;
public long? FormerAbsenceTimeOid { get; set; } public long? FormerAbsenceTimeOid { get; set; }
public DateTime? Krankheitsmeldung { get; set; } public DateTime? Krankheitsmeldung { get; set; }
public AbsenceReasonDC AbsenceReason { get; set; } public AbsenceReasonDC AbsenceReason { get; set; }

View File

@@ -614,7 +614,7 @@ namespace BS.Shared.Extensions
$"{start.ToShortDateString()} {start.ToShortTimeString()} - {end.ToShortTimeString()}"; $"{start.ToShortDateString()} {start.ToShortTimeString()} - {end.ToShortTimeString()}";
} }
public static DateTime MergeDateWithHoursMinutesSeconds(this DateTime date, int hours, int minutes, int seconds = 0) public static DateTime MergeDateWithHoursMinutesSeconds(this DateTime date, int hours, int minutes = 0, int seconds = 0)
{ {
var h = hours >= 0 && hours < 24 ? hours : 0; var h = hours >= 0 && hours < 24 ? hours : 0;
var m = minutes >= 0 && minutes < 60 ? minutes : 0; var m = minutes >= 0 && minutes < 60 ? minutes : 0;