Files
elwig/Elwig/Windows/PaymentVariantsWindow.xaml.cs
Lorenz Stechauner 64832e9a53
All checks were successful
Test / Run tests (push) Successful in 1m49s
[#57] PaymentVariantsWindow: Use Task.Run()
2025-07-07 23:31:03 +02:00

455 lines
21 KiB
C#

using Elwig.Helpers;
using Elwig.Helpers.Billing;
using Elwig.Helpers.Export;
using Elwig.Models.Dtos;
using Elwig.Models.Entities;
using Elwig.Services;
using Elwig.ViewModels;
using Microsoft.EntityFrameworkCore;
using Microsoft.Win32;
using System;
using System.Linq;
using System.Text.Json;
using System.Threading.Tasks;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Input;
namespace Elwig.Windows {
public partial class PaymentVariantsWindow : ContextWindow {
public PaymentVariantsViewModel ViewModel => (PaymentVariantsViewModel)DataContext;
public readonly int Year;
private bool DataValid, DataChanged, NameChanged, CommentChanged, DateValid, DateChanged, TransferDateValid, TransferDateChanged;
private readonly RoutedCommand CtrlL = new("CtrlL", typeof(MemberAdminWindow), [new KeyGesture(Key.L, ModifierKeys.Control)]);
private readonly RoutedCommand CtrlP = new("CtrlP", typeof(MemberAdminWindow), [new KeyGesture(Key.P, ModifierKeys.Control)]);
private readonly RoutedCommand CtrlÜ = new("CtrlÜ", typeof(MemberAdminWindow), [new KeyGesture(Key.Oem1, ModifierKeys.Control)]);
private readonly RoutedCommand CtrlShiftP = new("CtrlShiftP", typeof(MemberAdminWindow), [new KeyGesture(Key.P, ModifierKeys.Control | ModifierKeys.Shift)]);
public PaymentVariantsWindow(int year) {
InitializeComponent();
CommandBindings.Add(new CommandBinding(CtrlL, Menu_ExportSave_Click));
CommandBindings.Add(new CommandBinding(CtrlP, Menu_SummaryShow_Click));
CommandBindings.Add(new CommandBinding(CtrlÜ, Menu_EbicsSave_Click));
CommandBindings.Add(new CommandBinding(CtrlShiftP, Menu_SummaryPrint_Click));
Year = year;
using (var ctx = new AppDbContext()) {
ViewModel.SeasonLocked = ctx.Seasons.Find(Year + 1) != null;
}
Title = $"Auszahlungsvarianten - Lese {Year} - Elwig";
if (!App.Config.Debug) {
DataInput.Visibility = Visibility.Hidden;
}
if (App.Client.IsMatzen) {
ConsiderCustomInput.Content = ConsiderCustomInput.Content.ToString()?.Replace("Benutzerdefinierte", "Bentz.def.").Replace("Mitglied", "Mg.") + " (inkl. Treuebonus)";
} else {
MatzenNote.Visibility = Visibility.Hidden;
}
}
protected override async Task OnRenewContext(AppDbContext ctx) {
ControlUtils.RenewItemsSource(PaymentVariantList, await ctx.PaymentVariants
.Where(v => v.Year == Year)
.OrderBy(v => v.AvNr)
.Include(v => v.Season.Currency)
.ToListAsync());
Update();
}
private void Update() {
if (PaymentVariantList.SelectedItem is PaymentVar v) {
ViewModel.FillInputs(v);
} else {
ViewModel.ClearInputs();
}
UpdateButtons();
}
private void UpdateButtons() {
ViewModel.SaveIsEnabled = PaymentVariantList.SelectedItem != null &&
((DataChanged && DataValid) || NameChanged || CommentChanged ||
(DateChanged && DateValid) ||
(TransferDateChanged && TransferDateValid) ||
(ViewModel.ConsiderModifiers != ViewModel.BillingData?.ConsiderDelieryModifiers) ||
(ViewModel.ConsiderPenalties != ViewModel.BillingData?.ConsiderContractPenalties) ||
(ViewModel.ConsiderPenalty != ViewModel.BillingData?.ConsiderTotalPenalty) ||
(ViewModel.ConsiderAuto != ViewModel.BillingData?.ConsiderAutoBusinessShares) ||
(ViewModel.ConsiderCustom != ViewModel.BillingData?.ConsiderCustomModifiers) ||
ViewModel.WeightModifierChanged);
ViewModel.CalculateIsEnabled = !ViewModel.SaveIsEnabled && PaymentVariantList.SelectedItem is PaymentVar { TestVariant: true };
ViewModel.CommitIsEnabled = ViewModel.CalculateIsEnabled;
}
private void PaymentVariantList_SelectionChanged(object sender, SelectionChangedEventArgs evt) {
Update();
}
private async void AddButton_Click(object sender, RoutedEventArgs evt) {
try {
var v = await PaymentVariantService.CreatePaymentVariant(Year);
ControlUtils.SelectItem(PaymentVariantList, v);
} catch (Exception exc) {
var str = "Der Eintrag konnte nicht in der Datenbank aktualisiert werden!\n\n" + exc.Message;
if (exc.InnerException != null) str += "\n\n" + exc.InnerException.Message;
MessageBox.Show(str, "Auszahlungsvariante erstellen", MessageBoxButton.OK, MessageBoxImage.Error);
}
}
private async void CopyButton_Click(object sender, RoutedEventArgs evt) {
if (PaymentVariantList.SelectedItem is not PaymentVar orig)
return;
Mouse.OverrideCursor = Cursors.Wait;
try {
PaymentVar n = await orig.Duplicate();
ControlUtils.SelectItem(PaymentVariantList, n);
} catch (Exception exc) {
var str = "Der Eintrag konnte nicht in der Datenbank aktualisiert werden!\n\n" + exc.Message;
if (exc.InnerException != null) str += "\n\n" + exc.InnerException.Message;
MessageBox.Show(str, "Auszahlungsvariante kopieren", MessageBoxButton.OK, MessageBoxImage.Error);
}
Mouse.OverrideCursor = null;
}
private async void DeleteButton_Click(object sender, RoutedEventArgs evt) {
if (PaymentVariantList.SelectedItem is not PaymentVar v || !v.TestVariant)
return;
Mouse.OverrideCursor = Cursors.Wait;
try {
await PaymentVariantService.DeletePaymentVariant(v.Year, v.AvNr);
} catch (Exception exc) {
var str = "Der Eintrag konnte nicht in der Datenbank aktualisiert werden!\n\n" + exc.Message;
if (exc.InnerException != null) str += "\n\n" + exc.InnerException.Message;
MessageBox.Show(str, "Auszahlungsvariante löschen", MessageBoxButton.OK, MessageBoxImage.Error);
}
Mouse.OverrideCursor = null;
}
private async void CalculateButton_Click(object sender, RoutedEventArgs evt) {
if (PaymentVariantList.SelectedItem is not PaymentVar v)
return;
ViewModel.CalculateIsEnabled = false;
Mouse.OverrideCursor = Cursors.Wait;
try {
await PaymentVariantService.Calculate(v.Year, v.AvNr);
} catch (Exception exc) {
MessageBox.Show(exc.Message, "Berechnungsfehler", MessageBoxButton.OK, MessageBoxImage.Error);
}
Mouse.OverrideCursor = null;
ViewModel.CalculateIsEnabled = true;
}
private void EditButton_Click(object sender, RoutedEventArgs evt) {
if (PaymentVariantList.SelectedItem is not PaymentVar v)
return;
App.FocusChartWindow(v.Year, v.AvNr);
}
private void PaymentAdjustmentButton_Click(object sender, RoutedEventArgs evt) {
App.FocusPaymentAdjustment(Year);
}
private async void MailButton_Click(object sender, RoutedEventArgs evt) {
if (PaymentVariantList.SelectedItem is not PaymentVar pv)
return;
using var ctx = new AppDbContext();
var vars = await ctx.PaymentVariants
.Where(v => pv.Year == v.Year)
.OrderBy(v => v.AvNr)
.Select(v => v.AvNr)
.ToArrayAsync();
var w = App.FocusMailWindow(pv.Year);
w.AddCreditNote(Array.IndexOf(vars, pv.AvNr));
}
private async void Menu_SummaryExport_Click(object sender, RoutedEventArgs evt) {
if (PaymentVariantList.SelectedItem is not PaymentVar v)
return;
await PaymentVariantService.GenerateSummary(v, ExportMode.SaveList);
}
private async void Menu_SummaryShow_Click(object sender, RoutedEventArgs evt) {
if (PaymentVariantList.SelectedItem is not PaymentVar v)
return;
await PaymentVariantService.GenerateSummary(v, ExportMode.Show);
}
private async void Menu_SummarySave_Click(object sender, RoutedEventArgs evt) {
if (PaymentVariantList.SelectedItem is not PaymentVar v)
return;
await PaymentVariantService.GenerateSummary(v, ExportMode.SavePdf);
}
private async void Menu_SummaryPrint_Click(object sender, RoutedEventArgs evt) {
if (PaymentVariantList.SelectedItem is not PaymentVar v)
return;
await PaymentVariantService.GenerateSummary(v, ExportMode.Print);
}
private async void CommitButton_Click(object sender, RoutedEventArgs evt) {
if (PaymentVariantList.SelectedItem is not PaymentVar v)
return;
ViewModel.CommitIsEnabled = false;
Mouse.OverrideCursor = Cursors.Wait;
try {
await PaymentVariantService.Commit(v.Year, v.AvNr);
} catch (Exception exc) {
MessageBox.Show(exc.Message, "Fehler", MessageBoxButton.OK, MessageBoxImage.Error);
}
Mouse.OverrideCursor = null;
ViewModel.RevertIsEnabled = true;
}
private async void RevertButton_Click(object sender, RoutedEventArgs evt) {
if (PaymentVariantList.SelectedItem is not PaymentVar v)
return;
var res = MessageBox.Show(
"Sollen wirklich alle festgesetzten Traubengutschriften der ausgewählten Auszahlungsvariante unwiderruflich gelöscht werden?\n\n" +
"Dies ist im Allgemeinen nie empfohlen. Handelt es sich um die aktuellste Auszahlungsvariante könnte das eine Ausnahme sein.",
"Traubengutschriften löschen", MessageBoxButton.YesNo, MessageBoxImage.Warning, MessageBoxResult.No);
if (res != MessageBoxResult.Yes)
return;
ViewModel.RevertIsEnabled = false;
Mouse.OverrideCursor = Cursors.Wait;
try {
await PaymentVariantService.Revert(v.Year, v.AvNr);
} catch (Exception exc) {
MessageBox.Show(exc.Message, "Fehler", MessageBoxButton.OK, MessageBoxImage.Error);
}
Mouse.OverrideCursor = null;
ViewModel.CommitIsEnabled = true;
}
private async void Menu_EbicsSave_Click(object sender, RoutedEventArgs evt) {
if (PaymentVariantList.SelectedItem is not PaymentVar v) {
return;
} else if (v.TransferDate == null) {
MessageBox.Show("Überweisungsdatum muss gesetzt sein!", "Exportieren nicht möglich", MessageBoxButton.OK, MessageBoxImage.Error);
return;
}
await PaymentVariantService.GenerateEbics(v.Year, v.AvNr);
}
private async void Menu_ExportSave_Click(object sender, RoutedEventArgs evt) {
if (PaymentVariantList.SelectedItem is not PaymentVar v)
return;
await PaymentVariantService.GenerateAccountingList(v.Year, v.AvNr, v.Name);
}
private async void SaveButton_Click(object sender, RoutedEventArgs evt) {
if (PaymentVariantList.SelectedItem is not PaymentVar v || ViewModel.BillingData == null)
return;
Mouse.OverrideCursor = Cursors.Wait;
try {
await ViewModel.UpdatePaymentVariant(v.Year, v.AvNr);
} catch (Exception exc) {
await HintContextChange();
var str = "Der Eintrag konnte nicht in der Datenbank aktualisiert werden!\n\n" + exc.Message;
if (exc.InnerException != null) str += "\n\n" + exc.InnerException.Message;
MessageBox.Show(str, "Auszahlungsvariante aktualisieren", MessageBoxButton.OK, MessageBoxImage.Error);
}
Mouse.OverrideCursor = null;
await HintContextChange();
CommentInput_TextChanged(null, null);
DateInput_TextChanged(null, null);
TransferDateInput_TextChanged(null, null);
ConsiderModifiersInput_Changed(null, null);
ConsiderPenaltiesInput_Changed(null, null);
ConsiderPenaltyInput_Changed(null, null);
ConsiderAutoInput_Changed(null, null);
ConsiderCustomInput_Changed(null, null);
WeightModifierInput_TextChanged(null, null);
}
private void ModifierButton_Click(object sender, RoutedEventArgs evt) {
App.FocusBaseDataSeason(Year);
}
private void NameInput_TextChanged(object sender, TextChangedEventArgs evt) {
if (PaymentVariantList.SelectedItem is not PaymentVar v) {
ControlUtils.ClearInputState(NameInput);
return;
}
if (NameInput.Text != v.Name) {
ControlUtils.SetInputChanged(NameInput);
NameChanged = true;
} else {
ControlUtils.ClearInputState(NameInput);
NameChanged = false;
}
UpdateButtons();
}
private void CommentInput_TextChanged(object? sender, TextChangedEventArgs? evt) {
if (PaymentVariantList.SelectedItem is not PaymentVar v) {
ControlUtils.ClearInputState(CommentInput);
return;
}
if (CommentInput.Text != (v.Comment ?? "")) {
ControlUtils.SetInputChanged(CommentInput);
CommentChanged = true;
} else {
ControlUtils.ClearInputState(CommentInput);
CommentChanged = false;
}
UpdateButtons();
}
private void DateInput_TextChanged(object? sender, TextChangedEventArgs? evt) {
if (PaymentVariantList.SelectedItem is not PaymentVar v) {
ControlUtils.ClearInputState(DateInput);
return;
}
var res = Validator.CheckDate(DateInput, true);
if (!res.IsValid) {
ControlUtils.SetInputInvalid(DateInput);
DateValid = false;
} else if (DateInput.Text != $"{v.Date:dd.MM.yyyy}") {
ControlUtils.SetInputChanged(DateInput);
DateValid = true;
DateChanged = true;
} else {
ControlUtils.ClearInputState(DateInput);
DateValid = true;
DateChanged = false;
}
UpdateButtons();
}
private void TransferDateInput_TextChanged(object? sender, TextChangedEventArgs? evt) {
if (PaymentVariantList.SelectedItem is not PaymentVar v) {
ControlUtils.ClearInputState(TransferDateInput);
return;
}
var res = Validator.CheckDate(TransferDateInput, false);
if (!res.IsValid) {
ControlUtils.SetInputInvalid(TransferDateInput);
TransferDateValid = false;
} else if (TransferDateInput.Text != $"{v.TransferDate:dd.MM.yyyy}") {
ControlUtils.SetInputChanged(TransferDateInput);
TransferDateValid = true;
TransferDateChanged = true;
} else {
ControlUtils.ClearInputState(TransferDateInput);
TransferDateValid = true;
TransferDateChanged = false;
}
UpdateButtons();
}
private void DataInput_TextChanged(object sender, TextChangedEventArgs evt) {
if (PaymentVariantList.SelectedItem is not PaymentVar v) {
ControlUtils.ClearInputState(DataInput);
return;
}
try {
var data = BillingData.FromJson(DataInput.Text);
var origJson = v.Data;
try {
origJson = JsonSerializer.Serialize(BillingData.FromJson(v.Data).Data);
} catch { }
DataValid = true;
if (JsonSerializer.Serialize(data.Data) != origJson) {
ControlUtils.SetInputChanged(DataInput);
DataChanged = true;
} else {
ControlUtils.ClearInputState(DataInput);
DataChanged = false;
}
} catch {
ControlUtils.SetInputInvalid(DataInput);
DataValid = false;
}
UpdateButtons();
}
private void ConsiderModifiersInput_Changed(object? sender, RoutedEventArgs? evt) {
if (ViewModel.BillingData == null) {
ControlUtils.ClearInputState(ConsiderModifiersInput);
return;
}
if (ViewModel.BillingData.ConsiderDelieryModifiers != ConsiderModifiersInput.IsChecked) {
ControlUtils.SetInputChanged(ConsiderModifiersInput);
} else {
ControlUtils.ClearInputState(ConsiderModifiersInput);
}
UpdateButtons();
}
private void ConsiderPenaltiesInput_Changed(object? sender, RoutedEventArgs? evt) {
if (ViewModel.BillingData == null) {
ControlUtils.ClearInputState(ConsiderPenaltiesInput);
return;
}
if (ViewModel.BillingData.ConsiderContractPenalties != ConsiderPenaltiesInput.IsChecked) {
ControlUtils.SetInputChanged(ConsiderPenaltiesInput);
} else {
ControlUtils.ClearInputState(ConsiderPenaltiesInput);
}
UpdateButtons();
}
private void ConsiderPenaltyInput_Changed(object? sender, RoutedEventArgs? evt) {
if (ViewModel.BillingData == null) {
ControlUtils.ClearInputState(ConsiderPenaltyInput);
return;
}
if (ViewModel.BillingData.ConsiderTotalPenalty != ConsiderPenaltyInput.IsChecked) {
ControlUtils.SetInputChanged(ConsiderPenaltyInput);
} else {
ControlUtils.ClearInputState(ConsiderPenaltyInput);
}
UpdateButtons();
}
private void ConsiderAutoInput_Changed(object? sender, RoutedEventArgs? evt) {
if (ViewModel.BillingData == null) {
ControlUtils.ClearInputState(ConsiderAutoInput);
return;
}
if (ViewModel.BillingData.ConsiderAutoBusinessShares != ConsiderAutoInput.IsChecked) {
ControlUtils.SetInputChanged(ConsiderAutoInput);
} else {
ControlUtils.ClearInputState(ConsiderAutoInput);
}
UpdateButtons();
}
private void ConsiderCustomInput_Changed(object? sender, RoutedEventArgs? evt) {
if (ViewModel.BillingData == null) {
ControlUtils.ClearInputState(ConsiderCustomInput);
return;
}
if (ViewModel.BillingData.ConsiderCustomModifiers != ConsiderCustomInput.IsChecked) {
ControlUtils.SetInputChanged(ConsiderCustomInput);
} else {
ControlUtils.ClearInputState(ConsiderCustomInput);
}
UpdateButtons();
}
private void WeightModifierInput_TextChanged(object? sender, TextChangedEventArgs? evt) {
var res = Validator.CheckDecimal(WeightModifierInput, false, 3, 2, true);
if (ViewModel.BillingData == null) {
ControlUtils.ClearInputState(WeightModifierInput);
return;
}
var val = WeightModifierInput.Text.Length > 0 && res.IsValid ? double.Parse(WeightModifierInput.Text) : 0;
ViewModel.WeightModifierChanged = (val != Math.Round(ViewModel.BillingData.NetWeightModifier * 100.0, 8) && val != Math.Round(ViewModel.BillingData.GrossWeightModifier * 100.0, 8)) ||
(val == 0 && (ViewModel.BillingData.NetWeightModifier != 0 || ViewModel.BillingData.GrossWeightModifier != 0));
if (ViewModel.WeightModifierChanged) {
ControlUtils.SetInputChanged(WeightModifierInput);
} else {
ControlUtils.ClearInputState(WeightModifierInput);
}
UpdateButtons();
}
private void WeightModifierInput_LostFocus(object sender, RoutedEventArgs evt) {
if (WeightModifierInput.Text.EndsWith(','))
WeightModifierInput.Text = WeightModifierInput.Text[..^1];
}
}
}