using System.Collections.ObjectModel; using CommunityToolkit.Mvvm.ComponentModel; using CommunityToolkit.Mvvm.Input; using FieldLogger.Models; using FieldLogger.Services; using FieldLogger.Services.Data; namespace FieldLogger.ViewModels; public sealed partial class JobListItem : ObservableObject { public required Job Job { get; init; } [ObservableProperty] private int _pointCount; [ObservableProperty] private bool _isActive; public string Name => Job.Name; public string CreatedLabel => Job.CreatedUtc.ToLocalTime().ToString("g"); } public sealed partial class JobsViewModel : ObservableObject { private readonly AppDatabase _database; private readonly SettingsService _settings; public ObservableCollection Jobs { get; } = new(); [ObservableProperty] private bool _isBusy; public JobsViewModel(AppDatabase database, SettingsService settings) { _database = database; _settings = settings; } public async Task RefreshAsync() { IsBusy = true; try { var jobs = await _database.GetJobsAsync(); var activeId = _settings.ActiveJobId; Jobs.Clear(); foreach (var job in jobs) { Jobs.Add(new JobListItem { Job = job, PointCount = await _database.GetPointCountAsync(job.Id), IsActive = job.Id == activeId, }); } } finally { IsBusy = false; } } [RelayCommand] private async Task NewJobAsync() { var name = await Shell.Current.DisplayPromptAsync("New Job", "Job name:", placeholder: $"Job {DateTime.Now:yyyy-MM-dd}"); if (string.IsNullOrWhiteSpace(name)) return; var job = await _database.CreateJobAsync(name.Trim()); _settings.ActiveJobId = job.Id; await RefreshAsync(); } [RelayCommand] private async Task SetActiveAsync(JobListItem item) { _settings.ActiveJobId = item.Job.Id; foreach (var j in Jobs) j.IsActive = j.Job.Id == item.Job.Id; await Task.CompletedTask; } [RelayCommand] private Task OpenAsync(JobListItem item) => Shell.Current.GoToAsync($"jobdetail?jobId={item.Job.Id}"); [RelayCommand] private async Task DeleteAsync(JobListItem item) { var confirmed = await Shell.Current.DisplayAlert("Delete Job", $"Delete \"{item.Job.Name}\" and its {item.PointCount} logged points?", "Delete", "Cancel"); if (!confirmed) return; await _database.DeleteJobAsync(item.Job.Id); if (_settings.ActiveJobId == item.Job.Id) _settings.ActiveJobId = null; await RefreshAsync(); } }