|
|
@@ -20,373 +20,499 @@ using System.Windows.Media;
|
|
|
using System.Windows.Media.Imaging;
|
|
|
using InABox.Configuration;
|
|
|
using Client = InABox.Clients.Client;
|
|
|
+using System.Windows;
|
|
|
+using InABox.Wpf;
|
|
|
|
|
|
-namespace PRSDesktop.Dashboards
|
|
|
+namespace PRSDesktop.Dashboards;
|
|
|
+
|
|
|
+public class EquipmentSchedulesDashboardProperties : IUserConfigurationSettings, IDashboardProperties
|
|
|
{
|
|
|
- public class EquipmentSchedulesDashboardProperties : IUserConfigurationSettings, IDashboardProperties
|
|
|
- {
|
|
|
+ public bool OnlyShowSchedules { get; set; } = true;
|
|
|
|
|
|
- }
|
|
|
+ public DynamicGridSelectedFilterSettings Filters { get; set; } = new();
|
|
|
+}
|
|
|
|
|
|
- public class ScheduleViewModel : INotifyPropertyChanged
|
|
|
- {
|
|
|
- private Guid employeeID;
|
|
|
- private string? employeeName;
|
|
|
- private string? employeeMobile;
|
|
|
- private string? employeeEmail;
|
|
|
- private BitmapImage? employeeImage;
|
|
|
+public class ScheduleViewModel : INotifyPropertyChanged
|
|
|
+{
|
|
|
+ private Guid employeeID;
|
|
|
+ private string? employeeName;
|
|
|
+ private string? employeeMobile;
|
|
|
+ private string? employeeEmail;
|
|
|
+ private BitmapImage? employeeImage;
|
|
|
|
|
|
- public bool HasEmployee => EmployeeID != Guid.Empty;
|
|
|
+ public bool HasEmployee => EmployeeID != Guid.Empty;
|
|
|
|
|
|
- public Guid ID { get; set; }
|
|
|
+ public Guid ID { get; set; }
|
|
|
|
|
|
- public string Title { get; set; }
|
|
|
+ public string Title { get; set; }
|
|
|
|
|
|
- public DateTime DueDate { get; set; }
|
|
|
+ public DateTime DueDate { get; set; }
|
|
|
|
|
|
- public BitmapImage? EmployeeImage
|
|
|
+ public BitmapImage? EmployeeImage
|
|
|
+ {
|
|
|
+ get => employeeImage;
|
|
|
+ set
|
|
|
{
|
|
|
- get => employeeImage;
|
|
|
- set
|
|
|
- {
|
|
|
- employeeImage = value;
|
|
|
- NotifyPropertyChanged();
|
|
|
- }
|
|
|
+ employeeImage = value;
|
|
|
+ NotifyPropertyChanged();
|
|
|
}
|
|
|
+ }
|
|
|
|
|
|
- public Guid EmployeeID
|
|
|
+ public Guid EmployeeID
|
|
|
+ {
|
|
|
+ get => employeeID;
|
|
|
+ set
|
|
|
{
|
|
|
- get => employeeID;
|
|
|
- set
|
|
|
- {
|
|
|
- employeeID = value;
|
|
|
- NotifyPropertyChanged(nameof(HasEmployee));
|
|
|
- }
|
|
|
+ employeeID = value;
|
|
|
+ NotifyPropertyChanged(nameof(HasEmployee));
|
|
|
}
|
|
|
+ }
|
|
|
|
|
|
- public string? EmployeeName
|
|
|
+ public string? EmployeeName
|
|
|
+ {
|
|
|
+ get => employeeName;
|
|
|
+ set
|
|
|
{
|
|
|
- get => employeeName;
|
|
|
- set
|
|
|
- {
|
|
|
- employeeName = value;
|
|
|
- NotifyPropertyChanged();
|
|
|
- }
|
|
|
+ employeeName = value;
|
|
|
+ NotifyPropertyChanged();
|
|
|
}
|
|
|
+ }
|
|
|
|
|
|
- public string? EmployeeMobile
|
|
|
+ public string? EmployeeMobile
|
|
|
+ {
|
|
|
+ get => employeeMobile;
|
|
|
+ set
|
|
|
{
|
|
|
- get => employeeMobile;
|
|
|
- set
|
|
|
- {
|
|
|
- employeeMobile = value;
|
|
|
- NotifyPropertyChanged();
|
|
|
- NotifyPropertyChanged(nameof(EmployeeContact));
|
|
|
- }
|
|
|
+ employeeMobile = value;
|
|
|
+ NotifyPropertyChanged();
|
|
|
+ NotifyPropertyChanged(nameof(EmployeeContact));
|
|
|
}
|
|
|
+ }
|
|
|
|
|
|
- public string? EmployeeEmail
|
|
|
+ public string? EmployeeEmail
|
|
|
+ {
|
|
|
+ get => employeeEmail;
|
|
|
+ set
|
|
|
{
|
|
|
- get => employeeEmail;
|
|
|
- set
|
|
|
- {
|
|
|
- employeeEmail = value;
|
|
|
- NotifyPropertyChanged();
|
|
|
- NotifyPropertyChanged(nameof(EmployeeContact));
|
|
|
- }
|
|
|
+ employeeEmail = value;
|
|
|
+ NotifyPropertyChanged();
|
|
|
+ NotifyPropertyChanged(nameof(EmployeeContact));
|
|
|
}
|
|
|
+ }
|
|
|
|
|
|
- public string? EmployeeContact
|
|
|
+ public string? EmployeeContact
|
|
|
+ {
|
|
|
+ get
|
|
|
{
|
|
|
- get
|
|
|
+ var str = "";
|
|
|
+ if (EmployeeEmail is not null) str = EmployeeEmail;
|
|
|
+ if(EmployeeMobile is not null)
|
|
|
{
|
|
|
- var str = "";
|
|
|
- if (EmployeeEmail is not null) str = EmployeeEmail;
|
|
|
- if(EmployeeMobile is not null)
|
|
|
+ if (string.IsNullOrWhiteSpace(str))
|
|
|
{
|
|
|
- if (string.IsNullOrWhiteSpace(str))
|
|
|
- {
|
|
|
- str = EmployeeMobile;
|
|
|
- }
|
|
|
- else
|
|
|
- {
|
|
|
- str += $", {EmployeeMobile}";
|
|
|
- }
|
|
|
+ str = EmployeeMobile;
|
|
|
+ }
|
|
|
+ else
|
|
|
+ {
|
|
|
+ str += $", {EmployeeMobile}";
|
|
|
}
|
|
|
-
|
|
|
- return string.IsNullOrWhiteSpace(str) ? null : str;
|
|
|
}
|
|
|
+
|
|
|
+ return string.IsNullOrWhiteSpace(str) ? null : str;
|
|
|
}
|
|
|
+ }
|
|
|
|
|
|
- public event PropertyChangedEventHandler? PropertyChanged;
|
|
|
+ public event PropertyChangedEventHandler? PropertyChanged;
|
|
|
|
|
|
- private void NotifyPropertyChanged([CallerMemberName] string propertyName = "")
|
|
|
- {
|
|
|
- PropertyChanged?.Invoke(this, new PropertyChangedEventArgs(propertyName));
|
|
|
- }
|
|
|
+ private void NotifyPropertyChanged([CallerMemberName] string propertyName = "")
|
|
|
+ {
|
|
|
+ PropertyChanged?.Invoke(this, new PropertyChangedEventArgs(propertyName));
|
|
|
+ }
|
|
|
+}
|
|
|
+
|
|
|
+public class EquipmentScheduleViewModel
|
|
|
+{
|
|
|
+ public bool HasLocation { get; set; }
|
|
|
+
|
|
|
+ public Guid ID { get; set; }
|
|
|
+
|
|
|
+ public string Code { get; set; }
|
|
|
+
|
|
|
+ public string Description { get; set; }
|
|
|
+
|
|
|
+ public List<ScheduleViewModel> Schedules { get; set; }
|
|
|
+}
|
|
|
+
|
|
|
+[ValueConversion(typeof(DateTime), typeof(SolidColorBrush))]
|
|
|
+class ScheduleBackgroundConverter : IValueConverter
|
|
|
+{
|
|
|
+ public Color GetColor(DateTime date)
|
|
|
+ {
|
|
|
+ var diff = date - DateTime.Today;
|
|
|
+ if (diff < TimeSpan.Zero)
|
|
|
+ return Colors.Salmon;
|
|
|
+ else if (diff.TotalDays <= 7)
|
|
|
+ return Colors.Orange;
|
|
|
+ else if (diff.Days <= 30)
|
|
|
+ return Colors.LightYellow;
|
|
|
+ else
|
|
|
+ return Colors.LightGreen;
|
|
|
}
|
|
|
|
|
|
- public class EquipmentScheduleViewModel
|
|
|
+ public object Convert(object value, Type targetType, object parameter, CultureInfo culture)
|
|
|
{
|
|
|
- public bool HasLocation { get; set; }
|
|
|
+ var date = (DateTime)value;
|
|
|
+ var color = GetColor(date);
|
|
|
+ return new SolidColorBrush(color);
|
|
|
+ }
|
|
|
|
|
|
- public Guid ID { get; set; }
|
|
|
+ public object ConvertBack(object value, Type targetType, object parameter, CultureInfo culture)
|
|
|
+ {
|
|
|
+ throw new NotImplementedException();
|
|
|
+ }
|
|
|
+}
|
|
|
+
|
|
|
+/// <summary>
|
|
|
+/// Interaction logic for EquipmentSchedulesDashboard.xaml
|
|
|
+/// </summary>
|
|
|
+public partial class EquipmentSchedulesDashboard : UserControl, IDashboardWidget<EquipmentDashboardGroup, EquipmentSchedulesDashboardProperties>, IHeaderDashboard, IBasePanel
|
|
|
+{
|
|
|
+ public EquipmentSchedulesDashboardProperties Properties { get; set; } = null!;
|
|
|
|
|
|
- public string Code { get; set; }
|
|
|
+ public DashboardHeader Header { get; set; } = new();
|
|
|
|
|
|
- public string Description { get; set; }
|
|
|
+ public event LoadSettings<EquipmentSchedulesDashboardProperties>? LoadSettings;
|
|
|
+ public event SaveSettings<EquipmentSchedulesDashboardProperties>? SaveSettings;
|
|
|
+ public event DataModelUpdateEvent? OnUpdateDataModel;
|
|
|
|
|
|
- public List<ScheduleViewModel> Schedules { get; set; }
|
|
|
+ private Dictionary<Guid, Equipment> Equipment = new();
|
|
|
+
|
|
|
+ private Dictionary<Guid, BitmapImage?> EmployeeImages = new();
|
|
|
+
|
|
|
+ private Dictionary<Guid, Employee> Employees = new();
|
|
|
+
|
|
|
+ private List<EquipmentScheduleViewModel> Models = new();
|
|
|
+
|
|
|
+ public EquipmentSchedulesDashboard()
|
|
|
+ {
|
|
|
+ InitializeComponent();
|
|
|
}
|
|
|
|
|
|
- [ValueConversion(typeof(DateTime), typeof(SolidColorBrush))]
|
|
|
- class ScheduleBackgroundConverter : IValueConverter
|
|
|
+ public void Setup()
|
|
|
{
|
|
|
- public Color GetColor(DateTime date)
|
|
|
- {
|
|
|
- var diff = date - DateTime.Today;
|
|
|
- if (diff < TimeSpan.Zero)
|
|
|
- return Colors.Salmon;
|
|
|
- else if (diff.TotalDays <= 7)
|
|
|
- return Colors.Orange;
|
|
|
- else if (diff.Days <= 30)
|
|
|
- return Colors.LightYellow;
|
|
|
- else
|
|
|
- return Colors.LightGreen;
|
|
|
- }
|
|
|
+ LoadEmployeeImages();
|
|
|
|
|
|
- public object Convert(object value, Type targetType, object parameter, CultureInfo culture)
|
|
|
- {
|
|
|
- var date = (DateTime)value;
|
|
|
- var color = GetColor(date);
|
|
|
- return new SolidColorBrush(color);
|
|
|
- }
|
|
|
+ SetupHeader();
|
|
|
+ }
|
|
|
|
|
|
- public object ConvertBack(object value, Type targetType, object parameter, CultureInfo culture)
|
|
|
- {
|
|
|
- throw new NotImplementedException();
|
|
|
- }
|
|
|
+ #region IBasePanel
|
|
|
+
|
|
|
+ public string SectionName => "EquipmentSchedules";
|
|
|
+
|
|
|
+ public DataModel DataModel(Selection selection)
|
|
|
+ {
|
|
|
+ return new AutoDataModel<Equipment>(new Filter<Equipment>().All());
|
|
|
+ }
|
|
|
+
|
|
|
+ public bool IsReady { get; set; }
|
|
|
+
|
|
|
+ public void CreateToolbarButtons(IPanelHost host)
|
|
|
+ {
|
|
|
}
|
|
|
|
|
|
- /// <summary>
|
|
|
- /// Interaction logic for EquipmentSchedulesDashboard.xaml
|
|
|
- /// </summary>
|
|
|
- public partial class EquipmentSchedulesDashboard : UserControl, IDashboardWidget<EquipmentDashboardGroup, EquipmentSchedulesDashboardProperties>
|
|
|
+ public Dictionary<string, object[]> Selected()
|
|
|
{
|
|
|
- public EquipmentSchedulesDashboardProperties Properties { get; set; } = null!;
|
|
|
- public event LoadSettings<EquipmentSchedulesDashboardProperties>? LoadSettings;
|
|
|
- public event SaveSettings<EquipmentSchedulesDashboardProperties>? SaveSettings;
|
|
|
+ return new();
|
|
|
+ }
|
|
|
|
|
|
- private Dictionary<Guid, Equipment> Equipment = new();
|
|
|
+ public void Heartbeat(TimeSpan time)
|
|
|
+ {
|
|
|
+
|
|
|
+ }
|
|
|
|
|
|
- private Dictionary<Guid, BitmapImage?> EmployeeImages = new();
|
|
|
+ #endregion
|
|
|
|
|
|
- private Dictionary<Guid, Employee> Employees = new();
|
|
|
+ #region Header
|
|
|
|
|
|
- private List<EquipmentScheduleViewModel> Models = new();
|
|
|
+ private CheckBox ShowSchedulesBox = null!;
|
|
|
+ private FilterButton<Equipment> FilterBtn = null!;
|
|
|
|
|
|
- public EquipmentSchedulesDashboard()
|
|
|
+ public void SetupHeader()
|
|
|
+ {
|
|
|
+ ShowSchedulesBox = new CheckBox
|
|
|
{
|
|
|
- InitializeComponent();
|
|
|
- }
|
|
|
-
|
|
|
- public void Setup()
|
|
|
+ Content = "Only show schedules?",
|
|
|
+ IsChecked = Properties.OnlyShowSchedules,
|
|
|
+ VerticalAlignment = VerticalAlignment.Center
|
|
|
+ };
|
|
|
+ ShowSchedulesBox.Checked += ShowSchedulesBox_Checked;
|
|
|
+ ShowSchedulesBox.Unchecked += ShowSchedulesBox_Checked;
|
|
|
+
|
|
|
+ FilterBtn = new FilterButton<Equipment>(
|
|
|
+ new GlobalConfiguration<CoreFilterDefinitions>(nameof(EquipmentSchedulesDashboard)),
|
|
|
+ new UserConfiguration<CoreFilterDefinitions>(nameof(EquipmentSchedulesDashboard)))
|
|
|
{
|
|
|
- LoadEmployeeImages();
|
|
|
- }
|
|
|
+ Width = 25,
|
|
|
+ Height = 25,
|
|
|
+ Padding = new()
|
|
|
+ };
|
|
|
+ FilterBtn.BuiltInFilters.Add(new("Exclude Disposed", () => new Filter<Equipment>(x => x.Disposed).IsEqualTo(null)));
|
|
|
+ FilterBtn.SetSettings(Properties.Filters, false);
|
|
|
+ FilterBtn.OnFiltersSelected += FilterBtn_OnFiltersSelected;
|
|
|
+ FilterBtn.OnFilterRefresh += FilterBtn_OnFilterRefresh;
|
|
|
+
|
|
|
+ Header.BeginUpdate()
|
|
|
+ .Clear()
|
|
|
+ .Add(ShowSchedulesBox)
|
|
|
+ .AddRight(FilterBtn)
|
|
|
+ .EndUpdate();
|
|
|
+ }
|
|
|
+
|
|
|
+ private void ShowSchedulesBox_Checked(object sender, RoutedEventArgs e)
|
|
|
+ {
|
|
|
+ Properties.OnlyShowSchedules = ShowSchedulesBox.IsChecked == true;
|
|
|
+ Refresh();
|
|
|
+ }
|
|
|
+
|
|
|
+ private void FilterBtn_OnFilterRefresh()
|
|
|
+ {
|
|
|
+ Refresh();
|
|
|
+ }
|
|
|
|
|
|
- private void LoadEmployeeImages()
|
|
|
+ private void FilterBtn_OnFiltersSelected(DynamicGridSelectedFilterSettings filters)
|
|
|
+ {
|
|
|
+ Properties.Filters = filters;
|
|
|
+ }
|
|
|
+
|
|
|
+ #endregion
|
|
|
+
|
|
|
+ private void LoadEmployeeImages()
|
|
|
+ {
|
|
|
+ Task.Run(() =>
|
|
|
{
|
|
|
- Task.Run(() =>
|
|
|
- {
|
|
|
- var employees = new Client<Employee>()
|
|
|
- .Query(
|
|
|
- LookupFactory.DefineFilter<Employee>(),
|
|
|
- Columns.None<Employee>().Add(
|
|
|
- x => x.ID,
|
|
|
- x => x.Thumbnail.ID,
|
|
|
- x => x.Name,
|
|
|
- x => x.Mobile,
|
|
|
- x => x.Email))
|
|
|
- .ToObjects<Employee>().ToList();
|
|
|
- var documents = new Client<Document>()
|
|
|
- .Query(
|
|
|
- new Filter<Document>(x => x.ID).InList(employees.Select(x => x.Thumbnail.ID).ToArray()),
|
|
|
- Columns.None<Document>().Add(x => x.ID).Add(x => x.Data))
|
|
|
- .ToDictionary<Document, Guid, byte[]>(x => x.ID, x => x.Data);
|
|
|
- return new { Employees = employees, Documents = documents };
|
|
|
- }).ContinueWith((task) =>
|
|
|
+ var employees = new Client<Employee>()
|
|
|
+ .Query(
|
|
|
+ LookupFactory.DefineFilter<Employee>(),
|
|
|
+ Columns.None<Employee>().Add(
|
|
|
+ x => x.ID,
|
|
|
+ x => x.Thumbnail.ID,
|
|
|
+ x => x.Name,
|
|
|
+ x => x.Mobile,
|
|
|
+ x => x.Email))
|
|
|
+ .ToObjects<Employee>().ToList();
|
|
|
+ var documents = new Client<Document>()
|
|
|
+ .Query(
|
|
|
+ new Filter<Document>(x => x.ID).InList(employees.Select(x => x.Thumbnail.ID).ToArray()),
|
|
|
+ Columns.None<Document>().Add(x => x.ID).Add(x => x.Data))
|
|
|
+ .ToDictionary<Document, Guid, byte[]>(x => x.ID, x => x.Data);
|
|
|
+ return new { Employees = employees, Documents = documents };
|
|
|
+ }).ContinueWith((task) =>
|
|
|
+ {
|
|
|
+ EmployeeImages = task.Result.Employees.ToDictionary(
|
|
|
+ x => x.ID,
|
|
|
+ x =>
|
|
|
+ {
|
|
|
+ var document = task.Result.Documents.GetValueOrDefault(x.Thumbnail.ID);
|
|
|
+ if (document is null)
|
|
|
+ return null;
|
|
|
+
|
|
|
+ return ImageUtils.BitmapImageFromBytes(document);
|
|
|
+ });
|
|
|
+ Employees = task.Result.Employees.ToDictionary(x => x.ID, x => x);
|
|
|
+ lock (Models)
|
|
|
{
|
|
|
- EmployeeImages = task.Result.Employees.ToDictionary(
|
|
|
- x => x.ID,
|
|
|
- x =>
|
|
|
- {
|
|
|
- var document = task.Result.Documents.GetValueOrDefault(x.Thumbnail.ID);
|
|
|
- if (document is null)
|
|
|
- return null;
|
|
|
-
|
|
|
- return ImageUtils.BitmapImageFromBytes(document);
|
|
|
- });
|
|
|
- Employees = task.Result.Employees.ToDictionary(x => x.ID, x => x);
|
|
|
- lock (Models)
|
|
|
+ var anonymous = PRSDesktop.Resources.anonymous.AsBitmapImage();
|
|
|
+ foreach (var model in Models)
|
|
|
{
|
|
|
- var anonymous = PRSDesktop.Resources.anonymous.AsBitmapImage();
|
|
|
- foreach (var model in Models)
|
|
|
+ foreach (var schedule in model.Schedules)
|
|
|
{
|
|
|
- foreach (var schedule in model.Schedules)
|
|
|
- {
|
|
|
- var employee = Employees?.GetValueOrDefault(schedule.EmployeeID);
|
|
|
- schedule.EmployeeImage = EmployeeImages?.GetValueOrDefault(schedule.EmployeeID) ?? anonymous;
|
|
|
- schedule.EmployeeMobile = employee?.Mobile;
|
|
|
- schedule.EmployeeName = employee?.Name;
|
|
|
- schedule.EmployeeEmail = employee?.Email;
|
|
|
- }
|
|
|
+ var employee = Employees?.GetValueOrDefault(schedule.EmployeeID);
|
|
|
+ schedule.EmployeeImage = EmployeeImages?.GetValueOrDefault(schedule.EmployeeID) ?? anonymous;
|
|
|
+ schedule.EmployeeMobile = employee?.Mobile;
|
|
|
+ schedule.EmployeeName = employee?.Name;
|
|
|
+ schedule.EmployeeEmail = employee?.Email;
|
|
|
}
|
|
|
}
|
|
|
- }, TaskScheduler.FromCurrentSynchronizationContext());
|
|
|
- }
|
|
|
+ }
|
|
|
+ }, TaskScheduler.FromCurrentSynchronizationContext());
|
|
|
+ }
|
|
|
|
|
|
- public void Refresh()
|
|
|
+ public void Refresh()
|
|
|
+ {
|
|
|
+ var eqFilter = FilterBtn.GetFilter();
|
|
|
+
|
|
|
+ var results = Client.QueryMultiple(
|
|
|
+ new KeyedQueryDef<Equipment>(
|
|
|
+ eqFilter,
|
|
|
+ Columns.None<Equipment>().Add(x => x.ID)
|
|
|
+ .Add(x => x.Code)
|
|
|
+ .Add(x => x.Description)
|
|
|
+ .Add(x => x.TrackerLink.ID)
|
|
|
+ .Add(x => x.TrackerLink.Location.Latitude)
|
|
|
+ .Add(x => x.TrackerLink.Location.Longitude)
|
|
|
+ .Add(x => x.TrackerLink.Location.Timestamp)),
|
|
|
+ new KeyedQueryDef<Schedule>(
|
|
|
+ new Filter<Schedule>(x => x.DocumentClass).IsEqualTo(typeof(Equipment).EntityName())
|
|
|
+ .And(x => x.IncludeInAggregate).IsEqualTo(true),
|
|
|
+ Columns.None<Schedule>().Add(x => x.ID)
|
|
|
+ .Add(x => x.Title)
|
|
|
+ .Add(x => x.DueDate)
|
|
|
+ .Add(x => x.DocumentID)
|
|
|
+ .Add(x => x.EmployeeLink.ID)));
|
|
|
+
|
|
|
+ var equipmentItems = results.Get<Equipment>().Rows.Select(x => x.ToObject<Equipment>());
|
|
|
+ Equipment = equipmentItems.ToDictionary(x => x.ID, x => x);
|
|
|
+ var schedules = results.Get<Schedule>().Rows
|
|
|
+ .Select(x => x.ToObject<Schedule>())
|
|
|
+ .GroupBy(x => x.DocumentID)
|
|
|
+ .ToDictionary(x => x.Key, x => x.OrderBy(x => x.DueDate).ToList());
|
|
|
+
|
|
|
+ var anonymous = PRSDesktop.Resources.anonymous.AsBitmapImage();
|
|
|
+
|
|
|
+ lock (Models)
|
|
|
{
|
|
|
- var results = Client.QueryMultiple(
|
|
|
- new KeyedQueryDef<Equipment>(
|
|
|
- new Filter<Equipment>().All(),
|
|
|
- Columns.None<Equipment>().Add(x => x.ID)
|
|
|
- .Add(x => x.Code)
|
|
|
- .Add(x => x.Description)
|
|
|
- .Add(x => x.TrackerLink.ID)
|
|
|
- .Add(x => x.TrackerLink.Location.Latitude)
|
|
|
- .Add(x => x.TrackerLink.Location.Longitude)
|
|
|
- .Add(x => x.TrackerLink.Location.Timestamp)),
|
|
|
- new KeyedQueryDef<Schedule>(
|
|
|
- new Filter<Schedule>(x => x.DocumentClass).IsEqualTo(typeof(Equipment).EntityName())
|
|
|
- .And(x => x.IncludeInAggregate).IsEqualTo(true),
|
|
|
- Columns.None<Schedule>().Add(x => x.ID)
|
|
|
- .Add(x => x.Title)
|
|
|
- .Add(x => x.DueDate)
|
|
|
- .Add(x => x.DocumentID)
|
|
|
- .Add(x => x.EmployeeLink.ID)));
|
|
|
-
|
|
|
- var equipmentItems = results.Get<Equipment>().Rows.Select(x => x.ToObject<Equipment>());
|
|
|
- Equipment = equipmentItems.ToDictionary(x => x.ID, x => x);
|
|
|
- var schedules = results.Get<Schedule>().Rows
|
|
|
- .Select(x => x.ToObject<Schedule>())
|
|
|
- .GroupBy(x => x.DocumentID)
|
|
|
- .ToDictionary(x => x.Key, x => x.OrderBy(x => x.DueDate).ToList());
|
|
|
-
|
|
|
- var anonymous = PRSDesktop.Resources.anonymous.AsBitmapImage();
|
|
|
-
|
|
|
- lock (Models)
|
|
|
+ Models = new List<EquipmentScheduleViewModel>();
|
|
|
+ foreach (var equipmentItem in equipmentItems)
|
|
|
{
|
|
|
- Models = new List<EquipmentScheduleViewModel>();
|
|
|
- foreach (var equipmentItem in equipmentItems)
|
|
|
+ var equipmentSchedules = schedules.GetValueOrDefault(equipmentItem.ID);
|
|
|
+ if(equipmentSchedules is null && Properties.OnlyShowSchedules)
|
|
|
+ {
|
|
|
+ continue;
|
|
|
+ }
|
|
|
+
|
|
|
+ var model = new EquipmentScheduleViewModel
|
|
|
{
|
|
|
- var equipmentSchedules = schedules.GetValueOrDefault(equipmentItem.ID);
|
|
|
- if (equipmentSchedules is not null)
|
|
|
+ Code = equipmentItem.Code,
|
|
|
+ Description = equipmentItem.Description,
|
|
|
+ ID = equipmentItem.ID,
|
|
|
+ HasLocation = equipmentItem.TrackerLink.ID != Guid.Empty
|
|
|
+ };
|
|
|
+
|
|
|
+ model.Schedules = (equipmentSchedules ?? Enumerable.Empty<Schedule>())
|
|
|
+ .Select(x =>
|
|
|
{
|
|
|
- var model = new EquipmentScheduleViewModel
|
|
|
+ var employee = Employees.GetValueOrDefault(x.EmployeeLink.ID);
|
|
|
+ return new ScheduleViewModel
|
|
|
{
|
|
|
- Code = equipmentItem.Code,
|
|
|
- Description = equipmentItem.Description,
|
|
|
- ID = equipmentItem.ID,
|
|
|
- HasLocation = equipmentItem.TrackerLink.ID != Guid.Empty
|
|
|
+ Title = x.Title,
|
|
|
+ DueDate = x.DueDate,
|
|
|
+ ID = x.ID,
|
|
|
+ EmployeeImage = EmployeeImages.GetValueOrDefault(x.EmployeeLink.ID) ?? anonymous,
|
|
|
+ EmployeeID = x.EmployeeLink.ID,
|
|
|
+ EmployeeEmail = employee?.Email,
|
|
|
+ EmployeeMobile = employee?.Mobile,
|
|
|
+ EmployeeName = employee?.Name
|
|
|
};
|
|
|
+ })
|
|
|
+ .ToList() ?? [];
|
|
|
|
|
|
- model.Schedules = equipmentSchedules
|
|
|
- .Select(x =>
|
|
|
- {
|
|
|
- var employee = Employees.GetValueOrDefault(x.EmployeeLink.ID);
|
|
|
- return new ScheduleViewModel
|
|
|
- {
|
|
|
- Title = x.Title,
|
|
|
- DueDate = x.DueDate,
|
|
|
- ID = x.ID,
|
|
|
- EmployeeImage = EmployeeImages.GetValueOrDefault(x.EmployeeLink.ID) ?? anonymous,
|
|
|
- EmployeeID = x.EmployeeLink.ID,
|
|
|
- EmployeeEmail = employee?.Email,
|
|
|
- EmployeeMobile = employee?.Mobile,
|
|
|
- EmployeeName = employee?.Name
|
|
|
- };
|
|
|
- })
|
|
|
- .ToList() ?? new List<ScheduleViewModel>();
|
|
|
-
|
|
|
- Models.Add(model);
|
|
|
- }
|
|
|
- }
|
|
|
+ Models.Add(model);
|
|
|
}
|
|
|
- EquipmentList.ItemsSource = Models;
|
|
|
}
|
|
|
+ EquipmentList.ItemsSource = Models;
|
|
|
+ }
|
|
|
+
|
|
|
+ public void Shutdown(CancelEventArgs? cancel)
|
|
|
+ {
|
|
|
+ }
|
|
|
+
|
|
|
+ private void Border_ContextMenuOpening(object sender, ContextMenuEventArgs e)
|
|
|
+ {
|
|
|
+ if (sender is not FrameworkElement element || element.Tag is not Guid equipmentID) return;
|
|
|
+
|
|
|
+ var menu = new ContextMenu();
|
|
|
+ menu.AddItem("View Equipment", null, equipmentID, ViewEquipment_Click);
|
|
|
+ menu.AddItem("Add Schedule", null, equipmentID, CreateSchedule_Click);
|
|
|
+ menu.IsOpen = true;
|
|
|
+
|
|
|
+ e.Handled = true;
|
|
|
+ }
|
|
|
+
|
|
|
+ private void CreateSchedule_Click(Guid equipmentID)
|
|
|
+ {
|
|
|
+ var schedule = new Schedule();
|
|
|
+ schedule.DocumentClass = typeof(Equipment).EntityName();
|
|
|
+ schedule.DocumentID = equipmentID;
|
|
|
|
|
|
- public void Shutdown(CancelEventArgs? cancel)
|
|
|
+ if (DynamicGridUtils.EditEntity(schedule))
|
|
|
{
|
|
|
+ Refresh();
|
|
|
}
|
|
|
+ }
|
|
|
|
|
|
- private void ViewEquipment_Click(object sender, System.Windows.RoutedEventArgs e)
|
|
|
- {
|
|
|
- var equipmentID = (Guid)(sender as MenuItem)!.Tag;
|
|
|
+ private void Grid_ContextMenuOpening(object sender, ContextMenuEventArgs e)
|
|
|
+ {
|
|
|
+ if (sender is not FrameworkElement element || element.Tag is not Guid equipmentID) return;
|
|
|
|
|
|
- var equipment = new Client<Equipment>().Load(
|
|
|
- new Filter<Equipment>(x => x.ID).IsEqualTo(equipmentID)).FirstOrDefault();
|
|
|
- if(equipment != null)
|
|
|
- {
|
|
|
- var grid = DynamicGridUtils.CreateDynamicGrid(typeof(DynamicDataGrid<>), typeof(Equipment));
|
|
|
- if(grid.EditItems(new[] { equipment }))
|
|
|
- {
|
|
|
- new Client<Equipment>().Save(equipment, "Edited by user from schedules dashboard");
|
|
|
- Refresh();
|
|
|
- }
|
|
|
- }
|
|
|
- }
|
|
|
+ var menu = new ContextMenu();
|
|
|
+ menu.AddItem("Add Schedule", null, equipmentID, CreateSchedule_Click);
|
|
|
+ menu.IsOpen = true;
|
|
|
|
|
|
- private void ViewSchedule_Click(object sender, System.Windows.RoutedEventArgs e)
|
|
|
- {
|
|
|
- var scheduleID = (Guid)(sender as MenuItem)!.Tag;
|
|
|
+ e.Handled = true;
|
|
|
+ }
|
|
|
|
|
|
- var schedule = new Client<Schedule>().Load(
|
|
|
- new Filter<Schedule>(x => x.ID).IsEqualTo(scheduleID)).FirstOrDefault();
|
|
|
- if (schedule != null)
|
|
|
- {
|
|
|
- var grid = DynamicGridUtils.CreateDynamicGrid(typeof(DynamicDataGrid<>), typeof(Schedule));
|
|
|
- if (grid.EditItems(new[] { schedule }))
|
|
|
- {
|
|
|
- new Client<Schedule>().Save(schedule, "Edited by user from schedules dashboard");
|
|
|
- Refresh();
|
|
|
- }
|
|
|
- }
|
|
|
- }
|
|
|
+ private void Schedule_ContextMenuOpening(object sender, ContextMenuEventArgs e)
|
|
|
+ {
|
|
|
+ if (sender is not FrameworkElement element || element.Tag is not Guid scheduleID) return;
|
|
|
|
|
|
- private void ViewEmployee_Click(object sender, System.Windows.RoutedEventArgs e)
|
|
|
- {
|
|
|
- var employeeID = (Guid)(sender as MenuItem)!.Tag;
|
|
|
+ var menu = new ContextMenu();
|
|
|
+ menu.AddItem("View Schedule", null, scheduleID, ViewSchedule_Click);
|
|
|
+ menu.IsOpen = true;
|
|
|
|
|
|
- var employee = new Client<Employee>().Load(
|
|
|
- new Filter<Employee>(x => x.ID).IsEqualTo(employeeID)).FirstOrDefault();
|
|
|
- if (employee != null)
|
|
|
- {
|
|
|
- var grid = DynamicGridUtils.CreateDynamicGrid(typeof(DynamicDataGrid<>), typeof(Employee));
|
|
|
- if (grid.EditItems(new[] { employee }))
|
|
|
- {
|
|
|
- new Client<Employee>().Save(employee, "Edited by user from schedules dashboard");
|
|
|
- Refresh();
|
|
|
- }
|
|
|
- }
|
|
|
- }
|
|
|
+ e.Handled = true;
|
|
|
+ }
|
|
|
|
|
|
- private void EquipmentLocation_Click(object sender, System.Windows.RoutedEventArgs e)
|
|
|
+ private void Employee_ContextMenuOpening(object sender, ContextMenuEventArgs e)
|
|
|
+ {
|
|
|
+ if (sender is not FrameworkElement element || element.Tag is not Guid employeeID) return;
|
|
|
+
|
|
|
+ if (employeeID == Guid.Empty) return;
|
|
|
+
|
|
|
+ var menu = new ContextMenu();
|
|
|
+ menu.AddItem("View Employee", null, employeeID, ViewEmployee_Click);
|
|
|
+ menu.IsOpen = true;
|
|
|
+
|
|
|
+ e.Handled = true;
|
|
|
+ }
|
|
|
+
|
|
|
+ private void ViewEquipment_Click(Guid equipmentID)
|
|
|
+ {
|
|
|
+ if (DynamicGridUtils.EditEntity<Equipment>(equipmentID))
|
|
|
{
|
|
|
- var equipmentID = (Guid)(sender as Button)!.Tag;
|
|
|
+ Refresh();
|
|
|
+ }
|
|
|
+ }
|
|
|
|
|
|
- if (!Equipment.TryGetValue(equipmentID, out var equipment))
|
|
|
- return;
|
|
|
+ private void ViewSchedule_Click(Guid scheduleID)
|
|
|
+ {
|
|
|
+ if (DynamicGridUtils.EditEntity<Schedule>(scheduleID))
|
|
|
+ {
|
|
|
+ Refresh();
|
|
|
+ }
|
|
|
+ }
|
|
|
|
|
|
- var form = new MapForm(
|
|
|
- equipment.TrackerLink.Location.Latitude,
|
|
|
- equipment.TrackerLink.Location.Longitude,
|
|
|
- equipment.TrackerLink.Location.Timestamp);
|
|
|
- form.ShowDialog();
|
|
|
+ private void ViewEmployee_Click(Guid employeeID)
|
|
|
+ {
|
|
|
+ if (DynamicGridUtils.EditEntity<Employee>(employeeID))
|
|
|
+ {
|
|
|
+ Refresh();
|
|
|
}
|
|
|
}
|
|
|
|
|
|
- public class EquipmentSchedulesDashboardElement :
|
|
|
- DashboardElement<EquipmentSchedulesDashboard, EquipmentDashboardGroup, EquipmentSchedulesDashboardProperties> { }
|
|
|
+ private void EquipmentLocation_Click(object sender, System.Windows.RoutedEventArgs e)
|
|
|
+ {
|
|
|
+ var equipmentID = (Guid)(sender as Button)!.Tag;
|
|
|
+
|
|
|
+ if (!Equipment.TryGetValue(equipmentID, out var equipment))
|
|
|
+ return;
|
|
|
+
|
|
|
+ var form = new MapForm(
|
|
|
+ equipment.TrackerLink.Location.Latitude,
|
|
|
+ equipment.TrackerLink.Location.Longitude,
|
|
|
+ equipment.TrackerLink.Location.Timestamp);
|
|
|
+ form.ShowDialog();
|
|
|
+ }
|
|
|
}
|
|
|
+
|
|
|
+public class EquipmentSchedulesDashboardElement :
|
|
|
+ DashboardElement<EquipmentSchedulesDashboard, EquipmentDashboardGroup, EquipmentSchedulesDashboardProperties> { }
|