Compare commits
32 Commits
64832e9a53
...
dev
Author | SHA1 | Date | |
---|---|---|---|
7e21d9e2e4 | |||
4e2eca295d | |||
1f165055c1 | |||
7b953fa73e | |||
d3157e4d48 | |||
73fe4531cc | |||
b6c03892b1 | |||
91950ad9fd | |||
77c3f388e7 | |||
6f3e1a8905 | |||
466c8a322c | |||
ab7c7404e2 | |||
ea3ea5ca83 | |||
93e920f61a | |||
9b48242f0e | |||
7153bfab6f | |||
4b27ebf81b | |||
c26e4a2dbd | |||
fad1e28c06 | |||
c61c2e3fcd | |||
267aa3d47c | |||
7e9a27c75d | |||
53d82604a1 | |||
bb65a1f20e | |||
c6748055fd | |||
e6746f76b1 | |||
e9f389b885 | |||
919ab3356d | |||
39060f6a1e | |||
070dda1bde | |||
b6bfc60ab8 | |||
8aaa22fcb4 |
@@ -1,7 +1,7 @@
|
|||||||
name: Deploy
|
name: Deploy
|
||||||
on:
|
on:
|
||||||
push:
|
push:
|
||||||
tags: ["v[0-9]+.[0-9]+.[0-9]+"]
|
tags: ["v[0-9]+.[0-9]+.[0-9]+.[0-9]+"]
|
||||||
jobs:
|
jobs:
|
||||||
deploy:
|
deploy:
|
||||||
name: Build and Deploy
|
name: Build and Deploy
|
||||||
|
85
CHANGELOG.md
85
CHANGELOG.md
@@ -2,6 +2,91 @@
|
|||||||
Changelog
|
Changelog
|
||||||
=========
|
=========
|
||||||
|
|
||||||
|
[v1.0.0.3][v1.0.0.3] (2025-08-11) {#v1.0.0.3}
|
||||||
|
---------------------------------------------
|
||||||
|
|
||||||
|
### Neue Funktionen {#v1.0.0.3-features}
|
||||||
|
|
||||||
|
* Im Haupt-Fenster (`MainWindow`) ist es nun möglich die gesamte Datenbank zu hochzuladen bzw. herunterzuladen. ([#69][i69])
|
||||||
|
|
||||||
|
### Sonstiges {#v1.0.0.3-misc}
|
||||||
|
|
||||||
|
* Die Intigrität von Elwig-Export-Dateien (`.elwig.zip`) und anderen `.zip` Dateien wir nun überprüft. (d3157e4d48)
|
||||||
|
* Die Herkunftshierarchie wird nun auch automatisch synchronisiert (benötigt für Stamm-KG bei Mitglied, Ried/KG bei Flächenbindung, und Herkunft bei Lieferung). ([#70][i70], b6c03892b1)
|
||||||
|
* Abhängigkeiten aktualisiert. (1f165055c1, 4e2eca295d)
|
||||||
|
|
||||||
|
[v1.0.0.3]: https://git.necronda.net/winzer/elwig/releases/tag/v1.0.0.3
|
||||||
|
[i69]: https://git.necronda.net/winzer/elwig/issues/69
|
||||||
|
[i70]: https://git.necronda.net/winzer/elwig/issues/70
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
[v1.0.0.2][v1.0.0.2] (2025-08-05) {#v1.0.0.2}
|
||||||
|
---------------------------------------------
|
||||||
|
|
||||||
|
### Sonstiges {#v1.0.0.2-misc}
|
||||||
|
|
||||||
|
* Explizit native SQLite-Bibliothek hinzugefügt. (77c3f388e7)
|
||||||
|
|
||||||
|
[v1.0.0.2]: https://git.necronda.net/winzer/elwig/releases/tag/v1.0.0.2
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
[v1.0.0.1][v1.0.0.1] (2025-08-05) {#v1.0.0.1}
|
||||||
|
---------------------------------------------
|
||||||
|
|
||||||
|
### Sonstiges {#v1.0.0.1-misc}
|
||||||
|
|
||||||
|
* Abhängigkeiten aktualisiert. (466c8a322c)
|
||||||
|
* Angepasste Fehlermeldung, wenn Importieren fehlschlägt. (ab7c7404e2)
|
||||||
|
|
||||||
|
[v1.0.0.1]: https://git.necronda.net/winzer/elwig/releases/tag/v1.0.0.1
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
[v1.0.0.0][v1.0.0.0] (2025-07-30) {#v1.0.0.0}
|
||||||
|
---------------------------------------------
|
||||||
|
|
||||||
|
### Neue Funktionen {#v1.0.0.0-features}
|
||||||
|
|
||||||
|
* Es wird nun gespeichert, wann Mitglieder/Flächenbindungen/Lieferungen importiert bzw. exporiert wurden. (4234c7f994)
|
||||||
|
* Im Auszahlungsvarianten-Fenster (`PaymentVariantsWindow`) wird der Auszahlungsbetrag für nicht-festgesetzte Varianten nun überschlagsmäßig angezeigt. (913129f155)
|
||||||
|
* Wenn eine Variante im Auszahlungsvariante-Fenster (`ChartWindow`) gespeichert wird, wird sie nun automatisch auch berechnet. (c6c8fd9b68)
|
||||||
|
* Überall wo Weinsorten vorkommen werden diese jetzt rot oder grün eingefärbt angezeigt. ([#61][i61])
|
||||||
|
* Das Flächenbindungs-Fenster (`AreaComAdminWindow`) wurde überarbeitet. (53d82604a1, 267aa3d47c, [#64][i64])
|
||||||
|
* Auf allen Dokumenten wird der Bio-Kontrollstellen-Code in der Fußzeile angeführt (sofern dieser in den Stammdaten gesetzt wurde). (fad1e28c06)
|
||||||
|
|
||||||
|
### Behobene Fehler {#v1.0.0.0-bugfixes}
|
||||||
|
|
||||||
|
* Bei Traubengutschriften (`CreditNote`) wurde der Rebelzuschlag immer angeführt, auch wenn dieser in der zugrundeliegenden Berechnung nicht berücksichtigt wurde. (336aef5c70)
|
||||||
|
* In den Variantendaten einer Auszahlungsvariante (`PaymentVariantSummary`) wurde neben den Spalten _gebunden_ und _ungebunden_ noch _attributlos gebunden_ hinzugefügt. Ohne diese neue Spalte wären die Werte der anderen beiden falsch. ([#58][i58])
|
||||||
|
* Das erste Laden des Ausgangs-Protokoll-Fensters (`MailLogWindow`) hat nicht funktioniert. ([#65][i65])
|
||||||
|
* Im Lieferungen-Fenster (`DeliveryAdminWindow`) und im Mitglieder-Fenster (`MemberAdminWindow`) wird der Tool-Tip für Gewicht/Gradation mit korrektem Layout angezeigt. (e9f389b885)
|
||||||
|
* Bei Traubengutschriften (`CreditNote`) werden längere Freitexte vollständig angezeigt statt abgeschnitten. ([#62][i62])
|
||||||
|
|
||||||
|
### Sonstiges {#v1.0.0.0-misc}
|
||||||
|
|
||||||
|
* Im Auszahlungsvarianten-Fenster (`PaymentVariantsWindow`) wird angeführt, dass "Zu- und Abschläge bei Lieferungen" auch den Rebelzuschlag umfassen. (0dff3986b7)
|
||||||
|
* Im gesamten Program wird an passenden Stellen statt "Gewicht" nun "Menge" verwendet. (0f3ce39f35)
|
||||||
|
* Verbesserungen der Code-Qualität und der Leistung. ([#59][i59], b580e1bf79, 623f55f5b0, 3493ff6df1, 267797b55d, 41811925be, [#57][i57], 38d0ff969d, e6746f76b1, 7e9a27c75d)
|
||||||
|
* Im Mitglieder-Fenster (`MemberAdminWindow`) werden die Flächenbindungen jetzt für die momentane Saison angezeigt statt für das aktuelle Jahr. (953532cae4)
|
||||||
|
* Abhängigkeiten aktualisiert. (4b27ebf81b, 7153bfab6f, 9b48242f0e)
|
||||||
|
* GPLv3 Lizenz hinzugefügt. (93e920f61a)
|
||||||
|
|
||||||
|
[v1.0.0.0]: https://git.necronda.net/winzer/elwig/releases/tag/v1.0.0.0
|
||||||
|
[i57]: https://git.necronda.net/winzer/elwig/issues/57
|
||||||
|
[i58]: https://git.necronda.net/winzer/elwig/issues/58
|
||||||
|
[i59]: https://git.necronda.net/winzer/elwig/issues/59
|
||||||
|
[i61]: https://git.necronda.net/winzer/elwig/issues/61
|
||||||
|
[i62]: https://git.necronda.net/winzer/elwig/issues/62
|
||||||
|
[i64]: https://git.necronda.net/winzer/elwig/issues/64
|
||||||
|
[i65]: https://git.necronda.net/winzer/elwig/issues/65
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
[v0.13.9][v0.13.9] (2025-05-05) {#v0.13.9}
|
[v0.13.9][v0.13.9] (2025-05-05) {#v0.13.9}
|
||||||
------------------------------------------
|
------------------------------------------
|
||||||
|
@@ -30,17 +30,25 @@
|
|||||||
|
|
||||||
<DataTemplate x:Key="WineVarietyTemplateCollapsed">
|
<DataTemplate x:Key="WineVarietyTemplateCollapsed">
|
||||||
<StackPanel Orientation="Horizontal">
|
<StackPanel Orientation="Horizontal">
|
||||||
<TextBlock Text="{Binding Name}"/>
|
<TextBlock Text="{Binding Name}" Foreground="{Binding Color}"/>
|
||||||
</StackPanel>
|
</StackPanel>
|
||||||
</DataTemplate>
|
</DataTemplate>
|
||||||
<DataTemplate x:Key="WineVarietyTemplateExpanded">
|
<DataTemplate x:Key="WineVarietyTemplateExpanded">
|
||||||
<StackPanel Orientation="Horizontal">
|
<StackPanel Orientation="Horizontal">
|
||||||
<TextBlock Text="{Binding SortId}" MinWidth="36" Margin="0,0,10,0"/>
|
<TextBlock Text="{Binding SortId}" Foreground="{Binding Color}" MinWidth="36" Margin="0,0,10,0"/>
|
||||||
<TextBlock Text="{Binding Name}"/>
|
<TextBlock Text="{Binding Name}" Foreground="{Binding Color}"/>
|
||||||
<TextBlock Text="{Binding CommentFormat}" FontSize="10" VerticalAlignment="Bottom" Margin="0,0,0,2"/>
|
<TextBlock Text="{Binding CommentFormat}" FontSize="10" VerticalAlignment="Bottom" Margin="0,0,0,2"/>
|
||||||
</StackPanel>
|
</StackPanel>
|
||||||
</DataTemplate>
|
</DataTemplate>
|
||||||
|
|
||||||
|
<DataTemplate x:Key="AreaCommitmentTypeTemplate">
|
||||||
|
<StackPanel Orientation="Horizontal">
|
||||||
|
<TextBlock Text="{Binding WineVar.Name}" Foreground="{Binding WineVar.Color}"/>
|
||||||
|
<TextBlock Text="{Binding WineAttr.Name}" Margin="5,0,0,0"/>
|
||||||
|
<TextBlock Text="{Binding Discriminator}" Margin="5,0,0,0"/>
|
||||||
|
</StackPanel>
|
||||||
|
</DataTemplate>
|
||||||
|
|
||||||
<DataTemplate x:Key="ModifierTemplate">
|
<DataTemplate x:Key="ModifierTemplate">
|
||||||
<StackPanel Orientation="Horizontal">
|
<StackPanel Orientation="Horizontal">
|
||||||
<TextBlock Text="{Binding Name}" MinWidth="250" Margin="0,0,10,0"/>
|
<TextBlock Text="{Binding Name}" MinWidth="250" Margin="0,0,10,0"/>
|
||||||
|
@@ -1,20 +1,21 @@
|
|||||||
using System;
|
|
||||||
using System.Data;
|
|
||||||
using System.Linq;
|
|
||||||
using System.Windows;
|
|
||||||
using System.IO;
|
|
||||||
using Elwig.Helpers;
|
|
||||||
using Elwig.Helpers.Weighing;
|
|
||||||
using System.Collections.Generic;
|
|
||||||
using System.Windows.Threading;
|
|
||||||
using System.Reflection;
|
|
||||||
using Elwig.Helpers.Printing;
|
|
||||||
using Elwig.Windows;
|
|
||||||
using Elwig.Dialogs;
|
using Elwig.Dialogs;
|
||||||
using System.Threading.Tasks;
|
using Elwig.Helpers;
|
||||||
using Elwig.Helpers.Billing;
|
using Elwig.Helpers.Billing;
|
||||||
|
using Elwig.Helpers.Export;
|
||||||
|
using Elwig.Helpers.Printing;
|
||||||
|
using Elwig.Helpers.Weighing;
|
||||||
using Elwig.Models.Entities;
|
using Elwig.Models.Entities;
|
||||||
|
using Elwig.Windows;
|
||||||
|
using System;
|
||||||
|
using System.Collections.Generic;
|
||||||
|
using System.Data;
|
||||||
|
using System.IO;
|
||||||
|
using System.Linq;
|
||||||
|
using System.Reflection;
|
||||||
using System.Text;
|
using System.Text;
|
||||||
|
using System.Threading.Tasks;
|
||||||
|
using System.Windows;
|
||||||
|
using System.Windows.Threading;
|
||||||
|
|
||||||
namespace Elwig {
|
namespace Elwig {
|
||||||
public partial class App : Application {
|
public partial class App : Application {
|
||||||
@@ -85,7 +86,7 @@ namespace Elwig {
|
|||||||
}
|
}
|
||||||
|
|
||||||
protected override async void OnStartup(StartupEventArgs evt) {
|
protected override async void OnStartup(StartupEventArgs evt) {
|
||||||
Version = new Version(typeof(App).GetTypeInfo().Assembly.GetCustomAttribute<AssemblyInformationalVersionAttribute>()?.InformationalVersion.Split('+')[0] ?? "0.0.0");
|
Version = new Version(typeof(App).GetTypeInfo().Assembly.GetCustomAttribute<AssemblyInformationalVersionAttribute>()?.InformationalVersion.Split('+')[0] ?? "0.0.0.0");
|
||||||
|
|
||||||
try {
|
try {
|
||||||
await AppDbUpdater.CheckDb();
|
await AppDbUpdater.CheckDb();
|
||||||
@@ -239,6 +240,17 @@ namespace Elwig {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public static async Task ReplaceDatabase(string filename) {
|
||||||
|
try {
|
||||||
|
await ElwigData.ImportDatabase(filename);
|
||||||
|
MessageBox.Show("Das Ersetzen war erfolgreich!\n\nBitte starten Sie Elwig neu!", "Datenbank ersetzen", MessageBoxButton.OK, MessageBoxImage.Information);
|
||||||
|
ForceShutdown = true;
|
||||||
|
Current.Shutdown();
|
||||||
|
} catch (Exception exc) {
|
||||||
|
MessageBox.Show("Fehler beim Ersetzen:\n\n" + exc.Message, "Datenbank ersetzen", MessageBoxButton.OK, MessageBoxImage.Error);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
private static T FocusWindow<T>(Func<T> constructor, Predicate<T>? selector = null) where T : Window {
|
private static T FocusWindow<T>(Func<T> constructor, Predicate<T>? selector = null) where T : Window {
|
||||||
foreach (Window w in CurrentApp.Windows) {
|
foreach (Window w in CurrentApp.Windows) {
|
||||||
if (w is T t && (selector == null || selector(t))) {
|
if (w is T t && (selector == null || selector(t))) {
|
||||||
|
71
Elwig/Dialogs/AreaComModifyDialog.xaml
Normal file
71
Elwig/Dialogs/AreaComModifyDialog.xaml
Normal file
@@ -0,0 +1,71 @@
|
|||||||
|
<Window x:Class="Elwig.Dialogs.AreaComModifyDialog"
|
||||||
|
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
|
||||||
|
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
|
||||||
|
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
|
||||||
|
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
|
||||||
|
xmlns:local="clr-namespace:Elwig.Dialogs"
|
||||||
|
xmlns:ctrl="clr-namespace:Elwig.Controls"
|
||||||
|
ResizeMode="NoResize" ShowInTaskbar="False" Topmost="True"
|
||||||
|
WindowStartupLocation="CenterOwner"
|
||||||
|
DataContext="{Binding RelativeSource={RelativeSource Self}}"
|
||||||
|
Title="Flächenbindungen bearbeiten" Height="220" Width="450">
|
||||||
|
<Window.Resources>
|
||||||
|
<Style TargetType="Label">
|
||||||
|
<Setter Property="HorizontalAlignment" Value="Left"/>
|
||||||
|
<Setter Property="VerticalAlignment" Value="Top"/>
|
||||||
|
<Setter Property="Padding" Value="2,4,2,4"/>
|
||||||
|
<Setter Property="Height" Value="25"/>
|
||||||
|
</Style>
|
||||||
|
<Style TargetType="TextBox">
|
||||||
|
<Setter Property="HorizontalAlignment" Value="Stretch"/>
|
||||||
|
<Setter Property="VerticalAlignment" Value="Top"/>
|
||||||
|
<Setter Property="FontSize" Value="14"/>
|
||||||
|
<Setter Property="Padding" Value="2"/>
|
||||||
|
<Setter Property="Height" Value="25"/>
|
||||||
|
<Setter Property="TextWrapping" Value="NoWrap"/>
|
||||||
|
</Style>
|
||||||
|
<Style TargetType="Button">
|
||||||
|
<Setter Property="HorizontalAlignment" Value="Right"/>
|
||||||
|
<Setter Property="VerticalAlignment" Value="Bottom"/>
|
||||||
|
<Setter Property="Width" Value="100"/>
|
||||||
|
<Setter Property="Height" Value="25"/>
|
||||||
|
</Style>
|
||||||
|
</Window.Resources>
|
||||||
|
<Grid>
|
||||||
|
<TextBlock x:Name="QuestionBlock1" TextAlignment="Center" Margin="0,10,0,0"
|
||||||
|
HorizontalAlignment="Center" VerticalAlignment="Top">
|
||||||
|
Soll die Flächenbindung (<Run Text="{Binding Area}"/> m², <Run Text="{Binding OrigYearFrom}"/>–<Run Text="{Binding OrigYearTo}"/>) rückwirkend bearbeitet werden,<LineBreak/>
|
||||||
|
oder erst ab der angegebenen Saison?
|
||||||
|
</TextBlock>
|
||||||
|
<TextBlock x:Name="QuestionBlock2" TextAlignment="Center" Margin="0,10,0,0" Visibility="Hidden"
|
||||||
|
HorizontalAlignment="Center" VerticalAlignment="Top">
|
||||||
|
Soll die Flächenbindung (<Run Text="{Binding Area}"/> m², <Run Text="{Binding OrigYearFrom}"/>–<Run Text="{Binding OrigYearTo}"/>) rückwirkend gelöscht werden,<LineBreak/>
|
||||||
|
oder erst ab der angegebenen Saison?
|
||||||
|
</TextBlock>
|
||||||
|
|
||||||
|
<Label x:Name="SeasonLabel" Content="Saison:" Margin="0,50,100,0"
|
||||||
|
HorizontalAlignment="Center" VerticalAlignment="Top"/>
|
||||||
|
<ctrl:IntegerUpDown x:Name="SeasonInput" Width="56" Height="25" Margin="0,50,0,0" FontSize="14"
|
||||||
|
Minimum="1900" Maximum="9999"
|
||||||
|
HorizontalAlignment="Center" VerticalAlignment="Top"
|
||||||
|
TextChanged="SeasonInput_TextChanged"/>
|
||||||
|
<CheckBox x:Name="RetroactiveInput" Content="Rückwirkend bearbeiten" Margin="0,80,0,0"
|
||||||
|
HorizontalAlignment="Center" VerticalAlignment="Top"
|
||||||
|
Checked="RetroactiveInput_Changed" Unchecked="RetroactiveInput_Changed"
|
||||||
|
IsChecked="{Binding ModifyRetroactively}"/>
|
||||||
|
|
||||||
|
<TextBlock x:Name="DescBlock1" Margin="0,105,0,0" TextAlignment="Center"
|
||||||
|
HorizontalAlignment="Center" VerticalAlignment="Top">
|
||||||
|
Die Flächenbindung bleibt bis inkl. Saison <Bold><Run x:Name="CancelSeason1"/></Bold> unverändert,<LineBreak/>
|
||||||
|
und wird ab inkl. Saison <Bold><Run x:Name="NewSeason1"/></Bold> in geänderter Form übernommen.
|
||||||
|
</TextBlock>
|
||||||
|
<TextBlock x:Name="DescBlock2" Margin="0,105,0,0" TextAlignment="Center" Visibility="Hidden"
|
||||||
|
HorizontalAlignment="Center" VerticalAlignment="Top">
|
||||||
|
Die Flächenbindung bleibt bis inklusive Saison <Bold><Run x:Name="CancelSeason2"/></Bold> gültig.
|
||||||
|
</TextBlock>
|
||||||
|
|
||||||
|
<Button x:Name="ConfirmButton" Content="Bestätigen" Margin="10,10,115,10" Grid.Column="1"
|
||||||
|
Click="ConfirmButton_Click"/>
|
||||||
|
<Button x:Name="CancelButton" Content="Abbrechen" Margin="10,10,10,10" Grid.Column="1" IsCancel="True"/>
|
||||||
|
</Grid>
|
||||||
|
</Window>
|
62
Elwig/Dialogs/AreaComModifyDialog.xaml.cs
Normal file
62
Elwig/Dialogs/AreaComModifyDialog.xaml.cs
Normal file
@@ -0,0 +1,62 @@
|
|||||||
|
using Elwig.Helpers;
|
||||||
|
using System.Windows;
|
||||||
|
using System.Windows.Controls;
|
||||||
|
|
||||||
|
namespace Elwig.Dialogs {
|
||||||
|
public partial class AreaComModifyDialog : Window {
|
||||||
|
|
||||||
|
public int? YearTo { get; set; }
|
||||||
|
public bool ModifyRetroactively { get; set; }
|
||||||
|
|
||||||
|
public string OrigYearFrom { get; set; }
|
||||||
|
public string OrigYearTo { get; set; }
|
||||||
|
public string Area { get; set; }
|
||||||
|
|
||||||
|
public AreaComModifyDialog(int? yearFrom, int? yearTo, int area, bool delete) {
|
||||||
|
Area = $"{area:N0}";
|
||||||
|
OrigYearFrom = $"{yearFrom}";
|
||||||
|
OrigYearTo = $"{yearTo}";
|
||||||
|
InitializeComponent();
|
||||||
|
Title = delete ? "Flächenbindung löschen" : "Flächenbindung bearbeiten";
|
||||||
|
RetroactiveInput.Content = delete ? "Rückwirkend löschen" : "Rückwirkend bearbeiten";
|
||||||
|
if (delete) {
|
||||||
|
QuestionBlock1.Visibility = Visibility.Hidden;
|
||||||
|
QuestionBlock2.Visibility = Visibility.Visible;
|
||||||
|
DescBlock1.Visibility = Visibility.Hidden;
|
||||||
|
DescBlock2.Visibility = Visibility.Visible;
|
||||||
|
}
|
||||||
|
if ((yearTo.HasValue && yearTo < Utils.CurrentNextSeason) || (yearFrom.HasValue && yearFrom >= Utils.CurrentNextSeason)) {
|
||||||
|
RetroactiveInput.IsChecked = true;
|
||||||
|
} else {
|
||||||
|
SeasonInput.Text = $"{Utils.CurrentNextSeason}";
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private void SeasonInput_TextChanged(object sender, TextChangedEventArgs evt) {
|
||||||
|
YearTo = SeasonInput.Value! - 1;
|
||||||
|
CancelSeason1.Text = $"{YearTo}";
|
||||||
|
CancelSeason2.Text = $"{YearTo}";
|
||||||
|
NewSeason1.Text = $"{YearTo + 1}";
|
||||||
|
}
|
||||||
|
|
||||||
|
private void RetroactiveInput_Changed(object sender, RoutedEventArgs evt) {
|
||||||
|
if (ModifyRetroactively) {
|
||||||
|
SeasonInput.IsEnabled = false;
|
||||||
|
SeasonInput.Text = "";
|
||||||
|
YearTo = null;
|
||||||
|
DescBlock1.Visibility = Visibility.Hidden;
|
||||||
|
DescBlock2.Visibility = Visibility.Hidden;
|
||||||
|
} else {
|
||||||
|
SeasonInput.IsEnabled = true;
|
||||||
|
SeasonInput.Text = $"{Utils.CurrentNextSeason}";
|
||||||
|
DescBlock1.Visibility = QuestionBlock1.Visibility;
|
||||||
|
DescBlock2.Visibility = QuestionBlock2.Visibility;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private void ConfirmButton_Click(object sender, RoutedEventArgs evt) {
|
||||||
|
DialogResult = true;
|
||||||
|
Close();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
@@ -1,4 +1,4 @@
|
|||||||
<Window x:Class="Elwig.Dialogs.AreaComDialog"
|
<Window x:Class="Elwig.Dialogs.AreaComTransferDialog"
|
||||||
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
|
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
|
||||||
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
|
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
|
||||||
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
|
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
|
@@ -3,7 +3,7 @@ using System.Windows;
|
|||||||
using System.Windows.Controls;
|
using System.Windows.Controls;
|
||||||
|
|
||||||
namespace Elwig.Dialogs {
|
namespace Elwig.Dialogs {
|
||||||
public partial class AreaComDialog : Window {
|
public partial class AreaComTransferDialog : Window {
|
||||||
|
|
||||||
public int CancelSeason { get; set; }
|
public int CancelSeason { get; set; }
|
||||||
public int SuccessorSeason => CancelSeason + 1;
|
public int SuccessorSeason => CancelSeason + 1;
|
||||||
@@ -12,7 +12,7 @@ namespace Elwig.Dialogs {
|
|||||||
public string AreaComNum { get; set; }
|
public string AreaComNum { get; set; }
|
||||||
public string Area { get; set; }
|
public string Area { get; set; }
|
||||||
|
|
||||||
public AreaComDialog(string name, int areaComNum, int area) {
|
public AreaComTransferDialog(string name, int areaComNum, int area) {
|
||||||
CancelSeason = Utils.FollowingSeason - 1;
|
CancelSeason = Utils.FollowingSeason - 1;
|
||||||
AreaComNum = $"{areaComNum:N0}";
|
AreaComNum = $"{areaComNum:N0}";
|
||||||
Area = $"{area:N0}";
|
Area = $"{area:N0}";
|
||||||
@@ -29,7 +29,7 @@ namespace Elwig.Dialogs {
|
|||||||
SeasonLabel.Margin = new(0, 40, 100, 0);
|
SeasonLabel.Margin = new(0, 40, 100, 0);
|
||||||
}
|
}
|
||||||
|
|
||||||
public AreaComDialog(string name, string successorName, int areaComNum, int area) {
|
public AreaComTransferDialog(string name, string successorName, int areaComNum, int area) {
|
||||||
CancelSeason = Utils.FollowingSeason - 1;
|
CancelSeason = Utils.FollowingSeason - 1;
|
||||||
AreaComNum = $"{areaComNum:N0}";
|
AreaComNum = $"{areaComNum:N0}";
|
||||||
Area = $"{area:N0}";
|
Area = $"{area:N0}";
|
@@ -136,7 +136,10 @@
|
|||||||
}
|
}
|
||||||
</tbody>
|
</tbody>
|
||||||
<tbody style="break-inside: avoid;">
|
<tbody style="break-inside: avoid;">
|
||||||
@{ decimal penalty = 0; }
|
@{
|
||||||
|
decimal penalty = 0;
|
||||||
|
string? comment = null;
|
||||||
|
}
|
||||||
|
|
||||||
@if (Model.MemberUnderDeliveries != null && Model.MemberUnderDeliveries.Count() > 0) {
|
@if (Model.MemberUnderDeliveries != null && Model.MemberUnderDeliveries.Count() > 0) {
|
||||||
<tr class="small">
|
<tr class="small">
|
||||||
@@ -158,7 +161,13 @@
|
|||||||
penalty += Model.MemberAutoBusinessSharesAmount;
|
penalty += Model.MemberAutoBusinessSharesAmount;
|
||||||
}
|
}
|
||||||
@if (Model.CustomPayment?.Amount != null) {
|
@if (Model.CustomPayment?.Amount != null) {
|
||||||
@Raw(FormatRow(Model.CustomPayment.Comment ?? ((Model.CustomPayment.Amount.Value) < 0 ? "Weitere Abzüge" : "Weitere Zuschläge"), Model.CustomPayment.Amount.Value, add: true));
|
comment = Model.CustomPayment.Comment;
|
||||||
|
string text = (Model.CustomPayment.Amount.Value < 0 ? "Weitere Abzüge" : "Weitere Zuschläge") + (comment != null ? "*" : "");
|
||||||
|
if (comment != null && comment!.Length <= 30) {
|
||||||
|
text = comment;
|
||||||
|
comment = null;
|
||||||
|
}
|
||||||
|
@Raw(FormatRow(text, Model.CustomPayment.Amount.Value, add: true));
|
||||||
penalty += Model.CustomPayment.Amount.Value;
|
penalty += Model.CustomPayment.Amount.Value;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -176,6 +185,9 @@
|
|||||||
}
|
}
|
||||||
</tbody>
|
</tbody>
|
||||||
</table>
|
</table>
|
||||||
|
@if (comment != null) {
|
||||||
|
<p>* @comment</p>
|
||||||
|
}
|
||||||
<p>Überweisung erfolgt auf Konto @(Elwig.Helpers.Utils.FormatIban(Model.Member.Iban ?? "-")).</p>
|
<p>Überweisung erfolgt auf Konto @(Elwig.Helpers.Utils.FormatIban(Model.Member.Iban ?? "-")).</p>
|
||||||
<div style="margin-top: 1em;">
|
<div style="margin-top: 1em;">
|
||||||
@if (Model.Text != null) {
|
@if (Model.Text != null) {
|
||||||
|
@@ -44,8 +44,8 @@ namespace Elwig.Documents {
|
|||||||
.Item(c.Address).Item($"{c.Plz} {c.Ort}").Item("Österreich").Item("Tel.", c.PhoneNr).Item("Fax", c.FaxNr).NextLine()
|
.Item(c.Address).Item($"{c.Plz} {c.Ort}").Item("Österreich").Item("Tel.", c.PhoneNr).Item("Fax", c.FaxNr).NextLine()
|
||||||
.Item(c.EmailAddress != null ? $"<a href=\"mailto:{c.Name} {c.NameSuffix} <{c.EmailAddress}>\">{c.EmailAddress}</a>" : null)
|
.Item(c.EmailAddress != null ? $"<a href=\"mailto:{c.Name} {c.NameSuffix} <{c.EmailAddress}>\">{c.EmailAddress}</a>" : null)
|
||||||
.Item(c.Website != null ? $"<a href=\"http://{c.Website}/\">{c.Website}</a>" : null)
|
.Item(c.Website != null ? $"<a href=\"http://{c.Website}/\">{c.Website}</a>" : null)
|
||||||
.Item("Betriebs-Nr.", c.LfbisNr).Item("UID", c.UstIdNr).NextLine()
|
.Item("Betriebs-Nr.", c.LfbisNr).Item("Bio-KSt.", c.OrganicAuthority).NextLine()
|
||||||
.Item("BIC", c.Bic).Item("IBAN", c.Iban)
|
.Item("UID", c.UstIdNr).Item("BIC", c.Bic).Item("IBAN", c.Iban)
|
||||||
.ToString();
|
.ToString();
|
||||||
Date = DateOnly.FromDateTime(Utils.Today);
|
Date = DateOnly.FromDateTime(Utils.Today);
|
||||||
}
|
}
|
||||||
|
@@ -7,7 +7,7 @@
|
|||||||
<UseWPF>true</UseWPF>
|
<UseWPF>true</UseWPF>
|
||||||
<PreserveCompilationContext>true</PreserveCompilationContext>
|
<PreserveCompilationContext>true</PreserveCompilationContext>
|
||||||
<ApplicationIcon>Resources\Images\Elwig.ico</ApplicationIcon>
|
<ApplicationIcon>Resources\Images\Elwig.ico</ApplicationIcon>
|
||||||
<Version>0.13.9</Version>
|
<Version>1.0.0.3</Version>
|
||||||
<SatelliteResourceLanguages>de-AT</SatelliteResourceLanguages>
|
<SatelliteResourceLanguages>de-AT</SatelliteResourceLanguages>
|
||||||
<AllowUnsafeBlocks>true</AllowUnsafeBlocks>
|
<AllowUnsafeBlocks>true</AllowUnsafeBlocks>
|
||||||
<ApplicationManifest>app.manifest</ApplicationManifest>
|
<ApplicationManifest>app.manifest</ApplicationManifest>
|
||||||
@@ -23,19 +23,21 @@
|
|||||||
<ItemGroup>
|
<ItemGroup>
|
||||||
<PackageReference Include="CommunityToolkit.Mvvm" Version="8.4.0" />
|
<PackageReference Include="CommunityToolkit.Mvvm" Version="8.4.0" />
|
||||||
<PackageReference Include="LinqKit" Version="1.3.8" />
|
<PackageReference Include="LinqKit" Version="1.3.8" />
|
||||||
<PackageReference Include="MailKit" Version="4.12.0" />
|
<PackageReference Include="MailKit" Version="4.13.0" />
|
||||||
<PackageReference Include="Microsoft.AspNetCore.Razor.Language" Version="6.0.36" />
|
<PackageReference Include="Microsoft.AspNetCore.Razor.Language" Version="6.0.36" />
|
||||||
<PackageReference Include="Microsoft.EntityFrameworkCore.Proxies" Version="9.0.4" />
|
<PackageReference Include="Microsoft.EntityFrameworkCore.Proxies" Version="9.0.8" />
|
||||||
<PackageReference Include="Microsoft.EntityFrameworkCore.Sqlite" Version="9.0.4" />
|
<PackageReference Include="Microsoft.EntityFrameworkCore.Sqlite" Version="9.0.8" />
|
||||||
<PackageReference Include="Microsoft.Extensions.Configuration.Ini" Version="9.0.4" />
|
<PackageReference Include="Microsoft.Extensions.Configuration.Ini" Version="9.0.8" />
|
||||||
<PackageReference Include="Microsoft.Web.WebView2" Version="1.0.3179.45" />
|
<PackageReference Include="Microsoft.Web.WebView2" Version="1.0.3405.78" />
|
||||||
<PackageReference Include="NJsonSchema" Version="11.3.2" />
|
<PackageReference Include="NJsonSchema" Version="11.4.0" />
|
||||||
<PackageReference Include="PdfiumViewer" Version="2.13.0" />
|
<PackageReference Include="PdfiumViewer" Version="2.13.0" />
|
||||||
<PackageReference Include="PdfiumViewer.Native.x86_64.no_v8-no_xfa" Version="2018.4.8.256" />
|
<PackageReference Include="PdfiumViewer.Native.x86_64.no_v8-no_xfa" Version="2018.4.8.256" />
|
||||||
<PackageReference Include="RazorLight" Version="2.3.1" />
|
<PackageReference Include="RazorLight" Version="2.3.1" />
|
||||||
<PackageReference Include="ScottPlot.WPF" Version="5.0.55" />
|
<PackageReference Include="ScottPlot.WPF" Version="5.0.55" />
|
||||||
<PackageReference Include="System.IO.Ports" Version="9.0.4" />
|
<PackageReference Include="SQLitePCLRaw.bundle_e_sqlite3" Version="3.0.1" />
|
||||||
<PackageReference Include="System.Text.Encoding.CodePages" Version="9.0.4" />
|
<PackageReference Include="System.IO.Hashing" Version="9.0.8" />
|
||||||
|
<PackageReference Include="System.IO.Ports" Version="9.0.8" />
|
||||||
|
<PackageReference Include="System.Text.Encoding.CodePages" Version="9.0.8" />
|
||||||
</ItemGroup>
|
</ItemGroup>
|
||||||
|
|
||||||
</Project>
|
</Project>
|
||||||
|
@@ -28,10 +28,10 @@ namespace Elwig.Helpers {
|
|||||||
await UpdateDbSchema(cnx, (int)(schemaVers / 100), RequiredSchemaVersion);
|
await UpdateDbSchema(cnx, (int)(schemaVers / 100), RequiredSchemaVersion);
|
||||||
|
|
||||||
var userVers = (long?)await AppDbContext.ExecuteScalar(cnx, "PRAGMA user_version") ?? 0;
|
var userVers = (long?)await AppDbContext.ExecuteScalar(cnx, "PRAGMA user_version") ?? 0;
|
||||||
var v = new Version((int)(userVers >> 24), (int)((userVers >> 16) & 0xFF), (int)(userVers & 0xFFFF));
|
var v = new Version((int)(userVers >> 24), (int)((userVers >> 16) & 0xFF), (int)((userVers >> 8) & 0xFF), (int)(userVers & 0xFF));
|
||||||
|
|
||||||
if (App.Version > v) {
|
if (App.Version > v) {
|
||||||
long vers = (App.Version.Major << 24) | (App.Version.Minor << 16) | App.Version.Build;
|
long vers = (App.Version.Major << 24) | (App.Version.Minor << 16) | (App.Version.Build << 8) | App.Version.Revision;
|
||||||
await AppDbContext.ExecuteBatch(cnx, $"PRAGMA user_version = {vers}");
|
await AppDbContext.ExecuteBatch(cnx, $"PRAGMA user_version = {vers}");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@@ -1,6 +1,7 @@
|
|||||||
using System;
|
using System;
|
||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
using System.Linq;
|
using System.Linq;
|
||||||
|
using System.Windows.Media;
|
||||||
|
|
||||||
namespace Elwig.Helpers.Billing {
|
namespace Elwig.Helpers.Billing {
|
||||||
public class GraphEntry {
|
public class GraphEntry {
|
||||||
@@ -40,6 +41,7 @@ namespace Elwig.Helpers.Billing {
|
|||||||
public string VaributeStringSimple => (Abgewertet ? "Abgew.: " : "") + (Vaributes.Count != 0 ? (Vaributes.Count >= 25 ? "Restliche Sorten" : string.Join(", ", Vaributes.Select(c => c.Listing))) : "-");
|
public string VaributeStringSimple => (Abgewertet ? "Abgew.: " : "") + (Vaributes.Count != 0 ? (Vaributes.Count >= 25 ? "Restliche Sorten" : string.Join(", ", Vaributes.Select(c => c.Listing))) : "-");
|
||||||
public string VaributeString => Vaributes.Count != 0 ? string.Join("\n", Vaributes.Select(c => c.FullName)) : "-";
|
public string VaributeString => Vaributes.Count != 0 ? string.Join("\n", Vaributes.Select(c => c.FullName)) : "-";
|
||||||
public string VaributeStringChange => (Abgewertet ? "A." : "") + string.Join(",", Vaributes.Select(c => c.Listing));
|
public string VaributeStringChange => (Abgewertet ? "A." : "") + string.Join(",", Vaributes.Select(c => c.Listing));
|
||||||
|
public Brush? Color => Vaributes.Select(v => v.Variety?.Color).Distinct().SingleOrDefault();
|
||||||
private readonly int Precision;
|
private readonly int Precision;
|
||||||
|
|
||||||
public GraphEntry(int id, int precision, BillingData.CurveMode mode) {
|
public GraphEntry(int id, int precision, BillingData.CurveMode mode) {
|
||||||
|
@@ -55,6 +55,7 @@ namespace Elwig.Helpers {
|
|||||||
public string? Bic;
|
public string? Bic;
|
||||||
public string? UstIdNr;
|
public string? UstIdNr;
|
||||||
public string? LfbisNr;
|
public string? LfbisNr;
|
||||||
|
public string? OrganicAuthority;
|
||||||
|
|
||||||
public string? PhoneNr;
|
public string? PhoneNr;
|
||||||
public string? FaxNr;
|
public string? FaxNr;
|
||||||
@@ -113,6 +114,7 @@ namespace Elwig.Helpers {
|
|||||||
UstIdNr = parameters.GetValueOrDefault("CLIENT_USTIDNR");
|
UstIdNr = parameters.GetValueOrDefault("CLIENT_USTIDNR");
|
||||||
Bic = parameters.GetValueOrDefault("CLIENT_BIC");
|
Bic = parameters.GetValueOrDefault("CLIENT_BIC");
|
||||||
Iban = parameters.GetValueOrDefault("CLIENT_IBAN");
|
Iban = parameters.GetValueOrDefault("CLIENT_IBAN");
|
||||||
|
OrganicAuthority = parameters.GetValueOrDefault("CLIENT_ORGANIC_AUTHORITY");
|
||||||
|
|
||||||
switch (parameters.GetValueOrDefault("MODE_DELIVERYNOTE_STATS", "SHORT")?.ToUpper()) {
|
switch (parameters.GetValueOrDefault("MODE_DELIVERYNOTE_STATS", "SHORT")?.ToUpper()) {
|
||||||
case "NONE": ModeDeliveryNoteStats = 0; break;
|
case "NONE": ModeDeliveryNoteStats = 0; break;
|
||||||
@@ -257,6 +259,7 @@ namespace Elwig.Helpers {
|
|||||||
("CLIENT_USTIDNR", UstIdNr),
|
("CLIENT_USTIDNR", UstIdNr),
|
||||||
("CLIENT_BIC", Bic),
|
("CLIENT_BIC", Bic),
|
||||||
("CLIENT_IBAN", Iban),
|
("CLIENT_IBAN", Iban),
|
||||||
|
("CLIENT_ORGANIC_AUTHORITY", OrganicAuthority),
|
||||||
("MODE_DELIVERYNOTE_STATS", deliveryNoteStats),
|
("MODE_DELIVERYNOTE_STATS", deliveryNoteStats),
|
||||||
("MODE_WINEQUALITYSTATISTICS", modeWineQualityStatistics),
|
("MODE_WINEQUALITYSTATISTICS", modeWineQualityStatistics),
|
||||||
("ORDERING_MEMBERLIST", orderingMemberList),
|
("ORDERING_MEMBERLIST", orderingMemberList),
|
||||||
|
@@ -41,6 +41,7 @@ namespace Elwig.Helpers.Export {
|
|||||||
Dictionary<string, int> currentLsNrs;
|
Dictionary<string, int> currentLsNrs;
|
||||||
Dictionary<int, List<WbRd>> currentWbRde;
|
Dictionary<int, List<WbRd>> currentWbRde;
|
||||||
Dictionary<int, AT_Kg> kgs;
|
Dictionary<int, AT_Kg> kgs;
|
||||||
|
List<WbGl> currentWbGls;
|
||||||
|
|
||||||
using (var ctx = new AppDbContext()) {
|
using (var ctx = new AppDbContext()) {
|
||||||
branches = await ctx.Branches.ToDictionaryAsync(b => b.ZwstId);
|
branches = await ctx.Branches.ToDictionaryAsync(b => b.ZwstId);
|
||||||
@@ -52,6 +53,7 @@ namespace Elwig.Helpers.Export {
|
|||||||
currentWbRde = await ctx.WbRde
|
currentWbRde = await ctx.WbRde
|
||||||
.GroupBy(r => r.KgNr)
|
.GroupBy(r => r.KgNr)
|
||||||
.ToDictionaryAsync(g => g.Key, g => g.ToList());
|
.ToDictionaryAsync(g => g.Key, g => g.ToList());
|
||||||
|
currentWbGls = await ctx.WbGls.ToListAsync();
|
||||||
kgs = await ctx.Katastralgemeinden.Include(k => k.WbKg).ToDictionaryAsync(k => k.KgNr);
|
kgs = await ctx.Katastralgemeinden.Include(k => k.WbKg).ToDictionaryAsync(k => k.KgNr);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -62,6 +64,8 @@ namespace Elwig.Helpers.Export {
|
|||||||
List<MemberEmailAddr> EmailAddresses,
|
List<MemberEmailAddr> EmailAddresses,
|
||||||
List<AreaCom> AreaCommitments,
|
List<AreaCom> AreaCommitments,
|
||||||
List<WbRd> Riede,
|
List<WbRd> Riede,
|
||||||
|
List<WbKg> WbKgs,
|
||||||
|
List<WbGl> WbGls,
|
||||||
List<Delivery> Deliveries,
|
List<Delivery> Deliveries,
|
||||||
List<DeliveryPart> DeliveryParts,
|
List<DeliveryPart> DeliveryParts,
|
||||||
List<DeliveryPartModifier> Modifiers,
|
List<DeliveryPartModifier> Modifiers,
|
||||||
@@ -75,6 +79,7 @@ namespace Elwig.Helpers.Export {
|
|||||||
foreach (var filename in filenames) {
|
foreach (var filename in filenames) {
|
||||||
// TODO read encrypted files
|
// TODO read encrypted files
|
||||||
using var zip = ZipFile.Open(filename, ZipArchiveMode.Read);
|
using var zip = ZipFile.Open(filename, ZipArchiveMode.Read);
|
||||||
|
await zip.CheckIntegrity();
|
||||||
|
|
||||||
var version = zip.GetEntry("version");
|
var version = zip.GetEntry("version");
|
||||||
using (var reader = new StreamReader(version!.Open(), Utils.UTF8)) {
|
using (var reader = new StreamReader(version!.Open(), Utils.UTF8)) {
|
||||||
@@ -96,13 +101,28 @@ namespace Elwig.Helpers.Export {
|
|||||||
areaComCount, areaComFilters != null ? string.Join(" / ", areaComFilters) : null,
|
areaComCount, areaComFilters != null ? string.Join(" / ", areaComFilters) : null,
|
||||||
deliveryCount, deliveryFilters != null ? string.Join(" / ", deliveryFilters) : null));
|
deliveryCount, deliveryFilters != null ? string.Join(" / ", deliveryFilters) : null));
|
||||||
|
|
||||||
data.Add(new([], [], [], [], [], [], [], new([], [], new() {
|
data.Add(new([], [], [], [], [], [], [], new([], [], [], [], new() {
|
||||||
["member"] = [],
|
["member"] = [],
|
||||||
["area_commitment"] = [],
|
["area_commitment"] = [],
|
||||||
["delivery"] = [],
|
["delivery"] = [],
|
||||||
})));
|
})));
|
||||||
var r = data[^1];
|
var r = data[^1];
|
||||||
|
|
||||||
|
var wbKgsJson = zip.GetEntry("wb_kgs.json");
|
||||||
|
if (wbKgsJson != null) {
|
||||||
|
using var reader = new StreamReader(wbKgsJson.Open(), Utils.UTF8);
|
||||||
|
string? line;
|
||||||
|
while ((line = await reader.ReadLineAsync()) != null) {
|
||||||
|
var obj = JsonNode.Parse(line)!.AsObject();
|
||||||
|
var (k, g) = obj.ToWbKg(currentWbGls);
|
||||||
|
r.WbKgs.Add(k);
|
||||||
|
if (g != null) {
|
||||||
|
currentWbGls[g.GlNr] = g;
|
||||||
|
r.WbGls.Add(g);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
var membersJson = zip.GetEntry("members.json");
|
var membersJson = zip.GetEntry("members.json");
|
||||||
if (membersJson != null) {
|
if (membersJson != null) {
|
||||||
using var reader = new StreamReader(membersJson.Open(), Utils.UTF8);
|
using var reader = new StreamReader(membersJson.Open(), Utils.UTF8);
|
||||||
@@ -125,10 +145,9 @@ namespace Elwig.Helpers.Export {
|
|||||||
string? line;
|
string? line;
|
||||||
while ((line = await reader.ReadLineAsync()) != null) {
|
while ((line = await reader.ReadLineAsync()) != null) {
|
||||||
var obj = JsonNode.Parse(line)!.AsObject();
|
var obj = JsonNode.Parse(line)!.AsObject();
|
||||||
var (areaCom, wbrd, timestamps) = obj.ToAreaCom(kgs, currentWbRde);
|
var (areaCom, wbrd, timestamps) = obj.ToAreaCom(currentWbRde);
|
||||||
r.AreaCommitments.Add(areaCom);
|
r.AreaCommitments.Add(areaCom);
|
||||||
if (wbrd != null) {
|
if (wbrd != null) {
|
||||||
currentWbRde[wbrd.KgNr].Add(wbrd);
|
|
||||||
r.Riede.Add(wbrd);
|
r.Riede.Add(wbrd);
|
||||||
}
|
}
|
||||||
if (timestamps.HasValue)
|
if (timestamps.HasValue)
|
||||||
@@ -142,10 +161,11 @@ namespace Elwig.Helpers.Export {
|
|||||||
string? line;
|
string? line;
|
||||||
while ((line = await reader.ReadLineAsync()) != null) {
|
while ((line = await reader.ReadLineAsync()) != null) {
|
||||||
var obj = JsonNode.Parse(line)!.AsObject();
|
var obj = JsonNode.Parse(line)!.AsObject();
|
||||||
var (d, parts, mods, timestamps) = obj.ToDelivery(currentLsNrs, currentDids);
|
var (d, parts, mods, rde, timestamps) = obj.ToDelivery(currentLsNrs, currentDids, kgs, currentWbRde);
|
||||||
r.Deliveries.Add(d);
|
r.Deliveries.Add(d);
|
||||||
r.DeliveryParts.AddRange(parts);
|
r.DeliveryParts.AddRange(parts);
|
||||||
r.Modifiers.AddRange(mods);
|
r.Modifiers.AddRange(mods);
|
||||||
|
r.Riede.AddRange(rde);
|
||||||
if (timestamps.HasValue)
|
if (timestamps.HasValue)
|
||||||
r.Timestamps["delivery"].Add((d.Year, d.DId, timestamps.Value.CreatedAt, timestamps.Value.ModifiedAt));
|
r.Timestamps["delivery"].Add((d.Year, d.DId, timestamps.Value.CreatedAt, timestamps.Value.ModifiedAt));
|
||||||
}
|
}
|
||||||
@@ -156,12 +176,18 @@ namespace Elwig.Helpers.Export {
|
|||||||
var importedAreaComs = new List<(string FileName, string ZwstId, string Device, int Imported, int NotImported, string Filters)>();
|
var importedAreaComs = new List<(string FileName, string ZwstId, string Device, int Imported, int NotImported, string Filters)>();
|
||||||
var importedDeliveries = new List<(string FileName, string ZwstId, string Device, int New, int Overwritten, int NotImported, string Filters)>();
|
var importedDeliveries = new List<(string FileName, string ZwstId, string Device, int New, int Overwritten, int NotImported, string Filters)>();
|
||||||
|
|
||||||
foreach (var ((members, billingAddresses, telephoneNumbers, emailAddresses, areaCommitments, riede, deliveries, deliveryParts, modifiers, timestamps), meta) in data.Zip(metaData)) {
|
foreach (var ((members, billingAddresses, telephoneNumbers, emailAddresses, areaCommitments, riede, wbKgs, wbGls, deliveries, deliveryParts, modifiers, timestamps), meta) in data.Zip(metaData)) {
|
||||||
var branch = branches[meta.ZwstId];
|
var branch = branches[meta.ZwstId];
|
||||||
var device = meta.Device;
|
var device = meta.Device;
|
||||||
|
|
||||||
using var ctx = new AppDbContext();
|
using var ctx = new AppDbContext();
|
||||||
|
|
||||||
|
var kgnrs = wbKgs.Select(k => k.KgNr).ToList();
|
||||||
|
var duplicateKgNrs = await ctx.WbKgs
|
||||||
|
.Where(k => kgnrs.Contains(k.KgNr))
|
||||||
|
.Select(k => k.KgNr)
|
||||||
|
.ToListAsync();
|
||||||
|
|
||||||
var mgnrs = members.Select(m => m.MgNr).ToList();
|
var mgnrs = members.Select(m => m.MgNr).ToList();
|
||||||
var duplicateMgNrs = await ctx.Members
|
var duplicateMgNrs = await ctx.Members
|
||||||
.Where(m => mgnrs.Contains(m.MgNr))
|
.Where(m => mgnrs.Contains(m.MgNr))
|
||||||
@@ -215,6 +241,12 @@ namespace Elwig.Helpers.Export {
|
|||||||
importDuplicateDeliveries = ImportQuestion(branch.Name, device, "Lieferungen", true, duplicateLsNrs.Count);
|
importDuplicateDeliveries = ImportQuestion(branch.Name, device, "Lieferungen", true, duplicateLsNrs.Count);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (importDuplicateMembers || importNewMembers || importDuplicateDeliveries || importNewDeliveries) {
|
||||||
|
ctx.AddRange(wbGls);
|
||||||
|
ctx.UpdateRange(wbKgs.Where(k => duplicateKgNrs.Contains(k.KgNr)));
|
||||||
|
ctx.AddRange(wbKgs.Where(k => !duplicateKgNrs.Contains(k.KgNr)));
|
||||||
|
}
|
||||||
|
|
||||||
if (importDuplicateMembers) {
|
if (importDuplicateMembers) {
|
||||||
ctx.RemoveRange(ctx.BillingAddresses.Where(a => duplicateMgNrs.Contains(a.MgNr)));
|
ctx.RemoveRange(ctx.BillingAddresses.Where(a => duplicateMgNrs.Contains(a.MgNr)));
|
||||||
ctx.RemoveRange(ctx.MemberTelephoneNrs.Where(n => duplicateMgNrs.Contains(n.MgNr)));
|
ctx.RemoveRange(ctx.MemberTelephoneNrs.Where(n => duplicateMgNrs.Contains(n.MgNr)));
|
||||||
@@ -334,9 +366,9 @@ namespace Elwig.Helpers.Export {
|
|||||||
"Importieren erfolgreich",
|
"Importieren erfolgreich",
|
||||||
MessageBoxButton.OK, MessageBoxImage.Information);
|
MessageBoxButton.OK, MessageBoxImage.Information);
|
||||||
} catch (Exception exc) {
|
} catch (Exception exc) {
|
||||||
var str = "Der Eintrag konnte nicht in der Datenbank aktualisiert werden!\n\n" + exc.Message;
|
var str = "Der Eintrag konnte nicht in der Datenbank aktualisiert werden!\n\nEvtl. muss die Datenbank manuell auf dieses Gerät kopieren werden.\n\n" + exc.Message;
|
||||||
if (exc.InnerException != null) str += "\n\n" + exc.InnerException.Message;
|
if (exc.InnerException != null) str += "\n\n" + exc.InnerException.Message;
|
||||||
MessageBox.Show(str, "Fehler", MessageBoxButton.OK, MessageBoxImage.Error);
|
MessageBox.Show(str, "Fehler beim Importieren", MessageBoxButton.OK, MessageBoxImage.Error);
|
||||||
}
|
}
|
||||||
GC.Collect();
|
GC.Collect();
|
||||||
GC.WaitForPendingFinalizers();
|
GC.WaitForPendingFinalizers();
|
||||||
@@ -351,26 +383,53 @@ namespace Elwig.Helpers.Export {
|
|||||||
) == MessageBoxResult.Yes;
|
) == MessageBoxResult.Yes;
|
||||||
}
|
}
|
||||||
|
|
||||||
public static Task Export(string filename, IEnumerable<Member> members, IEnumerable<string> filters) {
|
public static Task Export(string filename, IEnumerable<Member> members, IEnumerable<WbKg> wbKgs, IEnumerable<string> filters) {
|
||||||
return new ElwigExport {
|
return new ElwigExport {
|
||||||
Members = (members, filters)
|
Members = (members, filters),
|
||||||
|
WbKgs = (wbKgs, ["von exportierten Mitgliedern"]),
|
||||||
}.Export(filename);
|
}.Export(filename);
|
||||||
}
|
}
|
||||||
|
|
||||||
public static Task Export(string filename, IEnumerable<Member> members, IEnumerable<AreaCom> areaComs, IEnumerable<string> filters) {
|
public static Task Export(string filename, IEnumerable<Member> members, IEnumerable<AreaCom> areaComs, IEnumerable<WbKg> wbKgs, IEnumerable<string> filters) {
|
||||||
return new ElwigExport {
|
return new ElwigExport {
|
||||||
Members = (members, filters),
|
Members = (members, filters),
|
||||||
AreaComs = (areaComs, ["von exportierten Mitgliedern"]),
|
AreaComs = (areaComs, ["von exportierten Mitgliedern"]),
|
||||||
|
WbKgs = (wbKgs, ["von exportierten Mitgliedern und Flächenbindungen"]),
|
||||||
}.Export(filename);
|
}.Export(filename);
|
||||||
}
|
}
|
||||||
|
|
||||||
public static Task Export(string filename, IEnumerable<Delivery> deliveries, IEnumerable<string> filters) {
|
public static Task Export(string filename, IEnumerable<Delivery> deliveries, IEnumerable<WbKg> wbKgs, IEnumerable<string> filters) {
|
||||||
return new ElwigExport {
|
return new ElwigExport {
|
||||||
Deliveries = (deliveries, filters)
|
Deliveries = (deliveries, filters),
|
||||||
|
WbKgs = (wbKgs, ["von exportierten Lieferungen"]),
|
||||||
}.Export(filename);
|
}.Export(filename);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public static async Task ImportDatabase(string filename) {
|
||||||
|
var oldName = Path.ChangeExtension(App.Config.DatabaseFile, ".old.sqlite3");
|
||||||
|
var newName = Path.ChangeExtension(App.Config.DatabaseFile, ".new.sqlite3");
|
||||||
|
try {
|
||||||
|
using (var zip = ZipFile.Open(filename, ZipArchiveMode.Read)) {
|
||||||
|
await zip.CheckIntegrity();
|
||||||
|
var db = zip.GetEntry("database.sqlite3")!;
|
||||||
|
db.ExtractToFile(newName, true);
|
||||||
|
}
|
||||||
|
File.Move(App.Config.DatabaseFile, oldName, true);
|
||||||
|
File.Move(newName, App.Config.DatabaseFile, false);
|
||||||
|
} finally {
|
||||||
|
if (File.Exists(newName))
|
||||||
|
File.Delete(newName);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public static void ExportDatabase(string filename) {
|
||||||
|
File.Delete(filename);
|
||||||
|
using var zip = ZipFile.Open(filename, ZipArchiveMode.Create);
|
||||||
|
var db = zip.CreateEntryFromFile(App.Config.DatabaseFile, "database.sqlite3", CompressionLevel.SmallestSize);
|
||||||
|
}
|
||||||
|
|
||||||
public class ElwigExport {
|
public class ElwigExport {
|
||||||
|
public (IEnumerable<WbKg> WbKgs, IEnumerable<string> Filters)? WbKgs { get; set; }
|
||||||
public (IEnumerable<Member> Members, IEnumerable<string> Filters)? Members { get; set; }
|
public (IEnumerable<Member> Members, IEnumerable<string> Filters)? Members { get; set; }
|
||||||
public (IEnumerable<AreaCom> AreaComs, IEnumerable<string> Filters)? AreaComs { get; set; }
|
public (IEnumerable<AreaCom> AreaComs, IEnumerable<string> Filters)? AreaComs { get; set; }
|
||||||
public (IEnumerable<Delivery> Deliveries, IEnumerable<string> Filters)? Deliveries { get; set; }
|
public (IEnumerable<Delivery> Deliveries, IEnumerable<string> Filters)? Deliveries { get; set; }
|
||||||
@@ -391,6 +450,12 @@ namespace Elwig.Helpers.Export {
|
|||||||
["zwstid"] = App.ZwstId,
|
["zwstid"] = App.ZwstId,
|
||||||
["device"] = Environment.MachineName,
|
["device"] = Environment.MachineName,
|
||||||
};
|
};
|
||||||
|
if (WbKgs != null) {
|
||||||
|
obj["wb_kgs"] = new JsonObject {
|
||||||
|
["count"] = WbKgs.Value.WbKgs.Count(),
|
||||||
|
["filters"] = new JsonArray(WbKgs.Value.Filters.Select(f => (JsonNode)f).ToArray()),
|
||||||
|
};
|
||||||
|
}
|
||||||
if (Members != null)
|
if (Members != null)
|
||||||
obj["members"] = new JsonObject {
|
obj["members"] = new JsonObject {
|
||||||
["count"] = Members.Value.Members.Count(),
|
["count"] = Members.Value.Members.Count(),
|
||||||
@@ -411,6 +476,13 @@ namespace Elwig.Helpers.Export {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// TODO encrypt files
|
// TODO encrypt files
|
||||||
|
if (WbKgs != null) {
|
||||||
|
var json = zip.CreateEntry("wb_kgs.json", CompressionLevel.SmallestSize);
|
||||||
|
using var writer = new StreamWriter(json.Open(), Utils.UTF8);
|
||||||
|
foreach (var k in WbKgs.Value.WbKgs) {
|
||||||
|
await writer.WriteLineAsync(k.ToJson().ToJsonString(JsonOpts));
|
||||||
|
}
|
||||||
|
}
|
||||||
if (Members != null) {
|
if (Members != null) {
|
||||||
var json = zip.CreateEntry("members.json", CompressionLevel.SmallestSize);
|
var json = zip.CreateEntry("members.json", CompressionLevel.SmallestSize);
|
||||||
using var writer = new StreamWriter(json.Open(), Utils.UTF8);
|
using var writer = new StreamWriter(json.Open(), Utils.UTF8);
|
||||||
@@ -435,6 +507,34 @@ namespace Elwig.Helpers.Export {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public static JsonObject ToJson(this WbKg k) {
|
||||||
|
return new JsonObject {
|
||||||
|
["kgnr"] = k.KgNr,
|
||||||
|
["großlage"] = k.Gl?.Name,
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
|
public static (WbKg, WbGl?) ToWbKg(this JsonNode json, List<WbGl> gls) {
|
||||||
|
var grosslage = json["großlage"]?.AsValue().GetValue<string>();
|
||||||
|
WbGl? gl = null;
|
||||||
|
bool newGl = false;
|
||||||
|
if (grosslage != null) {
|
||||||
|
gl = gls.FirstOrDefault(g => g.Name == grosslage);
|
||||||
|
if (gl == null) {
|
||||||
|
newGl = true;
|
||||||
|
gl = new WbGl {
|
||||||
|
GlNr = (gls.Count == 0 ? 1 : gls.Max(g => g.GlNr)) + 1,
|
||||||
|
Name = grosslage,
|
||||||
|
};
|
||||||
|
gls[gl.GlNr] = gl;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return (new WbKg {
|
||||||
|
KgNr = json["kgnr"]!.AsValue().GetValue<int>(),
|
||||||
|
GlNr = gl?.GlNr,
|
||||||
|
}, newGl ? gl : null);
|
||||||
|
}
|
||||||
|
|
||||||
public static JsonObject ToJson(this Member m) {
|
public static JsonObject ToJson(this Member m) {
|
||||||
return new JsonObject {
|
return new JsonObject {
|
||||||
["mgnr"] = m.MgNr,
|
["mgnr"] = m.MgNr,
|
||||||
@@ -580,22 +680,23 @@ namespace Elwig.Helpers.Export {
|
|||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
public static (AreaCom, WbRd?, (DateTime CreatedAt, DateTime ModifiedAt)?) ToAreaCom(this JsonNode json, Dictionary<int, AT_Kg> kgs, Dictionary<int, List<WbRd>> riede) {
|
public static (AreaCom, WbRd?, (DateTime CreatedAt, DateTime ModifiedAt)?) ToAreaCom(this JsonNode json, Dictionary<int, List<WbRd>> riede) {
|
||||||
var kgnr = json["kgnr"]!.AsValue().GetValue<int>();
|
var kgnr = json["kgnr"]!.AsValue().GetValue<int>();
|
||||||
var ried = json["ried"]?.AsValue().GetValue<string>();
|
var ried = json["ried"]?.AsValue().GetValue<string>();
|
||||||
WbRd? rd = null;
|
WbRd? rd = null;
|
||||||
bool newRd = false;
|
bool newRd = false;
|
||||||
if (ried != null) {
|
if (ried != null) {
|
||||||
var rde = riede[kgnr] ?? throw new ArgumentException($"Für KG {(kgs.TryGetValue(kgnr, out var k) ? k.Name : "?")} ({kgnr:00000}) ist noch keine Großlage festgelegt!\n(Stammdaten → Herkunftshierarchie)");
|
var rde = riede.GetValueOrDefault(kgnr, []);
|
||||||
rd = rde.FirstOrDefault(r => r.Name == ried);
|
rd = rde.FirstOrDefault(r => r.Name == ried);
|
||||||
if (rd == null) {
|
if (rd == null) {
|
||||||
newRd = true;
|
newRd = true;
|
||||||
rd = new WbRd {
|
rd = new WbRd {
|
||||||
KgNr = kgnr,
|
KgNr = kgnr,
|
||||||
RdNr = (rde.Count == 0 ? 0 : rde.Max(r => r.RdNr)) + 1,
|
RdNr = (rde.Count == 0 ? 1 : rde.Max(r => r.RdNr)) + 1,
|
||||||
Name = ried,
|
Name = ried,
|
||||||
};
|
};
|
||||||
rde.Add(rd);
|
rde.Add(rd);
|
||||||
|
riede[rd.KgNr] = rde;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
var createdAt = json["created_at"]?.AsValue().GetValue<string>();
|
var createdAt = json["created_at"]?.AsValue().GetValue<string>();
|
||||||
@@ -608,7 +709,7 @@ namespace Elwig.Helpers.Export {
|
|||||||
Area = json["area"]!.AsValue().GetValue<int>(),
|
Area = json["area"]!.AsValue().GetValue<int>(),
|
||||||
KgNr = kgnr,
|
KgNr = kgnr,
|
||||||
GstNr = json["gstnr"]?.AsValue().GetValue<string>() ?? "-",
|
GstNr = json["gstnr"]?.AsValue().GetValue<string>() ?? "-",
|
||||||
RdNr = rd?.RdNr,
|
RdNr = rd?.RdNr ?? json["rdnr"]?.AsValue().GetValue<int>(),
|
||||||
YearFrom = json["year_from"]?.AsValue().GetValue<int>(),
|
YearFrom = json["year_from"]?.AsValue().GetValue<int>(),
|
||||||
YearTo = json["year_to"]?.AsValue().GetValue<int>(),
|
YearTo = json["year_to"]?.AsValue().GetValue<int>(),
|
||||||
Comment = json["comment"]?.AsValue().GetValue<string>(),
|
Comment = json["comment"]?.AsValue().GetValue<string>(),
|
||||||
@@ -639,7 +740,7 @@ namespace Elwig.Helpers.Export {
|
|||||||
["qualid"] = p.QualId,
|
["qualid"] = p.QualId,
|
||||||
["hkid"] = p.HkId,
|
["hkid"] = p.HkId,
|
||||||
["kgnr"] = p.KgNr,
|
["kgnr"] = p.KgNr,
|
||||||
["rdnr"] = p.RdNr,
|
["ried"] = p.Rd?.Name,
|
||||||
["net_weight"] = p.IsNetWeight,
|
["net_weight"] = p.IsNetWeight,
|
||||||
["manual_weighing"] = p.IsManualWeighing,
|
["manual_weighing"] = p.IsManualWeighing,
|
||||||
["modids"] = new JsonArray(p.Modifiers.Select(m => (JsonNode)m.ModId).ToArray()),
|
["modids"] = new JsonArray(p.Modifiers.Select(m => (JsonNode)m.ModId).ToArray()),
|
||||||
@@ -664,7 +765,7 @@ namespace Elwig.Helpers.Export {
|
|||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
public static (Delivery, List<DeliveryPart>, List<DeliveryPartModifier>, (DateTime CreatedAt, DateTime ModifiedAt)?) ToDelivery(this JsonNode json, Dictionary<string, int> currentLsNrs, Dictionary<int, int> currentDids) {
|
public static (Delivery, List<DeliveryPart>, List<DeliveryPartModifier>, List<WbRd>, (DateTime CreatedAt, DateTime ModifiedAt)?) ToDelivery(this JsonNode json, Dictionary<string, int> currentLsNrs, Dictionary<int, int> currentDids, Dictionary<int, AT_Kg> kgs, Dictionary<int, List<WbRd>> riede) {
|
||||||
var year = json["year"]!.AsValue().GetValue<int>();
|
var year = json["year"]!.AsValue().GetValue<int>();
|
||||||
var lsnr = json["lsnr"]!.AsValue().GetValue<string>();
|
var lsnr = json["lsnr"]!.AsValue().GetValue<string>();
|
||||||
var did = currentLsNrs.GetValueOrDefault(lsnr, -1);
|
var did = currentLsNrs.GetValueOrDefault(lsnr, -1);
|
||||||
@@ -675,6 +776,7 @@ namespace Elwig.Helpers.Export {
|
|||||||
currentLsNrs[lsnr] = did;
|
currentLsNrs[lsnr] = did;
|
||||||
var createdAt = json["created_at"]?.AsValue().GetValue<string>();
|
var createdAt = json["created_at"]?.AsValue().GetValue<string>();
|
||||||
var modifiedAt = json["modified_at"]?.AsValue().GetValue<string>();
|
var modifiedAt = json["modified_at"]?.AsValue().GetValue<string>();
|
||||||
|
var wbRde = new List<WbRd>();
|
||||||
return (new Delivery {
|
return (new Delivery {
|
||||||
Year = year,
|
Year = year,
|
||||||
DId = did,
|
DId = did,
|
||||||
@@ -686,37 +788,57 @@ namespace Elwig.Helpers.Export {
|
|||||||
MgNr = json["mgnr"]!.AsValue().GetValue<int>(),
|
MgNr = json["mgnr"]!.AsValue().GetValue<int>(),
|
||||||
Comment = json["comment"]?.AsValue().GetValue<string>(),
|
Comment = json["comment"]?.AsValue().GetValue<string>(),
|
||||||
ImportedAt = DateTime.Now,
|
ImportedAt = DateTime.Now,
|
||||||
}, json["parts"]!.AsArray().Select(p => p!.AsObject()).Select(p => new DeliveryPart {
|
}, json["parts"]!.AsArray().Select(p => p!.AsObject()).Select(p => {
|
||||||
Year = year,
|
var kgnr = p["kgnr"]!.AsValue().GetValue<int>();
|
||||||
DId = did,
|
var ried = p["ried"]?.AsValue().GetValue<string>();
|
||||||
DPNr = p["dpnr"]!.AsValue().GetValue<int>(),
|
WbRd? rd = null;
|
||||||
SortId = p["sortid"]!.AsValue().GetValue<string>(),
|
if (ried != null) {
|
||||||
AttrId = p["attrid"]?.AsValue().GetValue<string>(),
|
var rde = riede.GetValueOrDefault(kgnr, []);
|
||||||
CultId = p["cultid"]?.AsValue().GetValue<string>(),
|
rd = rde.FirstOrDefault(r => r.Name == ried);
|
||||||
Weight = p["weight"]!.AsValue().GetValue<int>(),
|
if (rd == null) {
|
||||||
Kmw = p["kmw"]!.AsValue().GetValue<double>(),
|
rd = new WbRd {
|
||||||
QualId = p["qualid"]!.AsValue().GetValue<string>(),
|
KgNr = kgnr,
|
||||||
HkId = p["hkid"]!.AsValue().GetValue<string>(),
|
RdNr = (rde.Count == 0 ? 1 : rde.Max(r => r.RdNr)) + 1,
|
||||||
KgNr = p["kgnr"]?.AsValue().GetValue<int>(),
|
Name = ried,
|
||||||
RdNr = p["rdnr"]?.AsValue().GetValue<int>(),
|
};
|
||||||
IsNetWeight = p["net_weight"]!.AsValue().GetValue<bool>(),
|
rde.Add(rd);
|
||||||
IsManualWeighing = p["manual_weighing"]!.AsValue().GetValue<bool>(),
|
riede[rd.KgNr] = rde;
|
||||||
Comment = p["comment"]?.AsValue().GetValue<string>(),
|
wbRde.Add(rd);
|
||||||
IsSplCheck = p["spl_check"]?.AsValue().GetValue<bool>() ?? false,
|
}
|
||||||
IsHandPicked = p["hand_picked"]?.AsValue().GetValue<bool>(),
|
}
|
||||||
IsLesewagen = p["lesewagen"]?.AsValue().GetValue<bool>(),
|
return new DeliveryPart {
|
||||||
IsGebunden = p["gebunden"]?.AsValue().GetValue<bool>(),
|
Year = year,
|
||||||
Temperature = p["temperature"]?.AsValue().GetValue<double>(),
|
DId = did,
|
||||||
Acid = p["acid"]?.AsValue().GetValue<double>(),
|
DPNr = p["dpnr"]!.AsValue().GetValue<int>(),
|
||||||
ScaleId = p["scale_id"]?.AsValue().GetValue<string>(),
|
SortId = p["sortid"]!.AsValue().GetValue<string>(),
|
||||||
WeighingData = p["weighing_data"]?.AsObject().ToJsonString(JsonOpts),
|
AttrId = p["attrid"]?.AsValue().GetValue<string>(),
|
||||||
WeighingReason = p["weighing_reason"]?.AsValue().GetValue<string>(),
|
CultId = p["cultid"]?.AsValue().GetValue<string>(),
|
||||||
|
Weight = p["weight"]!.AsValue().GetValue<int>(),
|
||||||
|
Kmw = p["kmw"]!.AsValue().GetValue<double>(),
|
||||||
|
QualId = p["qualid"]!.AsValue().GetValue<string>(),
|
||||||
|
HkId = p["hkid"]!.AsValue().GetValue<string>(),
|
||||||
|
KgNr = p["kgnr"]?.AsValue().GetValue<int>(),
|
||||||
|
RdNr = rd?.RdNr ?? p["rdnr"]?.AsValue().GetValue<int>(),
|
||||||
|
IsNetWeight = p["net_weight"]!.AsValue().GetValue<bool>(),
|
||||||
|
IsManualWeighing = p["manual_weighing"]!.AsValue().GetValue<bool>(),
|
||||||
|
Comment = p["comment"]?.AsValue().GetValue<string>(),
|
||||||
|
IsSplCheck = p["spl_check"]?.AsValue().GetValue<bool>() ?? false,
|
||||||
|
IsHandPicked = p["hand_picked"]?.AsValue().GetValue<bool>(),
|
||||||
|
IsLesewagen = p["lesewagen"]?.AsValue().GetValue<bool>(),
|
||||||
|
IsGebunden = p["gebunden"]?.AsValue().GetValue<bool>(),
|
||||||
|
Temperature = p["temperature"]?.AsValue().GetValue<double>(),
|
||||||
|
Acid = p["acid"]?.AsValue().GetValue<double>(),
|
||||||
|
ScaleId = p["scale_id"]?.AsValue().GetValue<string>(),
|
||||||
|
WeighingData = p["weighing_data"]?.AsObject().ToJsonString(JsonOpts),
|
||||||
|
WeighingReason = p["weighing_reason"]?.AsValue().GetValue<string>(),
|
||||||
|
};
|
||||||
}).ToList(), json["parts"]!.AsArray().SelectMany(p => p!["modids"]!.AsArray().Select(m => new DeliveryPartModifier {
|
}).ToList(), json["parts"]!.AsArray().SelectMany(p => p!["modids"]!.AsArray().Select(m => new DeliveryPartModifier {
|
||||||
Year = year,
|
Year = year,
|
||||||
DId = did,
|
DId = did,
|
||||||
DPNr = p["dpnr"]!.AsValue().GetValue<int>(),
|
DPNr = p["dpnr"]!.AsValue().GetValue<int>(),
|
||||||
ModId = m!.AsValue().GetValue<string>(),
|
ModId = m!.AsValue().GetValue<string>(),
|
||||||
})).ToList(),
|
})).ToList(),
|
||||||
|
wbRde,
|
||||||
createdAt == null || modifiedAt == null ? null :
|
createdAt == null || modifiedAt == null ? null :
|
||||||
(DateTime.ParseExact(createdAt, "yyyy-MM-ddTHH:mm:ssK", CultureInfo.InvariantCulture, DateTimeStyles.None),
|
(DateTime.ParseExact(createdAt, "yyyy-MM-ddTHH:mm:ssK", CultureInfo.InvariantCulture, DateTimeStyles.None),
|
||||||
DateTime.ParseExact(modifiedAt, "yyyy-MM-ddTHH:mm:ssK", CultureInfo.InvariantCulture, DateTimeStyles.None)));
|
DateTime.ParseExact(modifiedAt, "yyyy-MM-ddTHH:mm:ssK", CultureInfo.InvariantCulture, DateTimeStyles.None)));
|
||||||
|
@@ -1,5 +1,7 @@
|
|||||||
using System;
|
using System;
|
||||||
using System.IO;
|
using System.IO;
|
||||||
|
using System.IO.Compression;
|
||||||
|
using System.IO.Hashing;
|
||||||
using System.Net.Http;
|
using System.Net.Http;
|
||||||
using System.Runtime.InteropServices;
|
using System.Runtime.InteropServices;
|
||||||
using System.Threading;
|
using System.Threading;
|
||||||
@@ -95,5 +97,16 @@ namespace Elwig.Helpers {
|
|||||||
await download.CopyToAsync(destination, 81920, relativeProgress, cancellationToken);
|
await download.CopyToAsync(destination, 81920, relativeProgress, cancellationToken);
|
||||||
progress.Report(100.0);
|
progress.Report(100.0);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public static async Task CheckIntegrity(this ZipArchive zip) {
|
||||||
|
var crc = new Crc32();
|
||||||
|
foreach (var entry in zip.Entries) {
|
||||||
|
crc.Reset();
|
||||||
|
using var stream = entry.Open();
|
||||||
|
await crc.AppendAsync(stream);
|
||||||
|
if (crc.GetCurrentHashAsUInt32() != entry.Crc32)
|
||||||
|
throw new InvalidDataException($"CRC-32 mismatch in '{entry.FullName}'");
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@@ -457,7 +457,7 @@ namespace Elwig.Helpers {
|
|||||||
url = "https://sync.elwig.at/" + url[25..];
|
url = "https://sync.elwig.at/" + url[25..];
|
||||||
if (!url.EndsWith('/')) url += "/";
|
if (!url.EndsWith('/')) url += "/";
|
||||||
using var client = GetHttpClient(username, password, accept: "application/json");
|
using var client = GetHttpClient(username, password, accept: "application/json");
|
||||||
var content = new StreamContent(new FileStream(zip, FileMode.Open, FileAccess.Read));
|
using var content = new StreamContent(new FileStream(zip, FileMode.Open, FileAccess.Read));
|
||||||
content.Headers.ContentType = new("application/zip");
|
content.Headers.ContentType = new("application/zip");
|
||||||
using var res = await client.PutAsync(url + Path.GetFileName(zip), content);
|
using var res = await client.PutAsync(url + Path.GetFileName(zip), content);
|
||||||
res.EnsureSuccessStatusCode();
|
res.EnsureSuccessStatusCode();
|
||||||
|
@@ -628,5 +628,55 @@ namespace Elwig.Helpers {
|
|||||||
|
|
||||||
return new(true, null);
|
return new(true, null);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public static ValidationResult CheckOrganicAuthorityCode(TextBox input, bool required) {
|
||||||
|
string text = "";
|
||||||
|
int pos = input.CaretIndex;
|
||||||
|
for (int i = 0, v = 0; i < input.Text.Length; i++) {
|
||||||
|
char ch = char.ToUpper(input.Text[i]);
|
||||||
|
if (v < 2 && char.IsAsciiLetter(ch)) {
|
||||||
|
v++;
|
||||||
|
text += ch;
|
||||||
|
} else if ((v == 2 || v == 6) && ch == '-') {
|
||||||
|
v++;
|
||||||
|
text += ch;
|
||||||
|
} else if (v >= 2 && char.IsLetterOrDigit(ch)) {
|
||||||
|
if (text.StartsWith("AT")) {
|
||||||
|
if (v == 3 && ch == 'B' || v == 4 && ch == 'I' || v == 5 && ch == 'O') {
|
||||||
|
v++;
|
||||||
|
text += ch;
|
||||||
|
} else if (v > 6 && char.IsAsciiDigit(ch)) {
|
||||||
|
v++;
|
||||||
|
text += ch;
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
v++;
|
||||||
|
text += ch;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (i == input.CaretIndex - 1) {
|
||||||
|
pos = text.Length;
|
||||||
|
} else if (text.StartsWith("AT") && v >= 10) {
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
input.Text = text;
|
||||||
|
input.CaretIndex = pos;
|
||||||
|
|
||||||
|
if (text.Length == 0)
|
||||||
|
return required ? new(false, "Bio-Kontrollstellen-Code ist nicht optional") : new(true, null);
|
||||||
|
|
||||||
|
if (text.StartsWith("AT")) {
|
||||||
|
if (text.Length != 10) {
|
||||||
|
return new(false, "Bio-Kontrollstellen-Code ist ungültig");
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
return new(false, "Not implemented yet");
|
||||||
|
}
|
||||||
|
|
||||||
|
return new(true, null);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@@ -4,6 +4,7 @@ using System;
|
|||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
using System.ComponentModel.DataAnnotations.Schema;
|
using System.ComponentModel.DataAnnotations.Schema;
|
||||||
using System.Linq;
|
using System.Linq;
|
||||||
|
using System.Windows.Media;
|
||||||
using IndexAttribute = Microsoft.EntityFrameworkCore.IndexAttribute;
|
using IndexAttribute = Microsoft.EntityFrameworkCore.IndexAttribute;
|
||||||
|
|
||||||
namespace Elwig.Models.Entities {
|
namespace Elwig.Models.Entities {
|
||||||
@@ -118,6 +119,9 @@ namespace Elwig.Models.Entities {
|
|||||||
public string SortIdString => string.Join(", ", SortIds);
|
public string SortIdString => string.Join(", ", SortIds);
|
||||||
public string FilteredSortIdString => string.Join(", ", FilteredSortIds);
|
public string FilteredSortIdString => string.Join(", ", FilteredSortIds);
|
||||||
|
|
||||||
|
public Brush? Color => Parts.Select(p => p.Variety.Color).Distinct().SingleOrDefault();
|
||||||
|
public Brush? FilteredColor => FilteredParts.Select(p => p.Variety.Color).Distinct().SingleOrDefault();
|
||||||
|
|
||||||
public IEnumerable<string> Modifiers => Parts
|
public IEnumerable<string> Modifiers => Parts
|
||||||
.SelectMany(p => p.Modifiers)
|
.SelectMany(p => p.Modifiers)
|
||||||
.Select(m => m.Name)
|
.Select(m => m.Name)
|
||||||
|
@@ -6,10 +6,10 @@ namespace Elwig.Models.Entities {
|
|||||||
[Table("wb_gl"), PrimaryKey("GlNr")]
|
[Table("wb_gl"), PrimaryKey("GlNr")]
|
||||||
public class WbGl {
|
public class WbGl {
|
||||||
[Column("glnr")]
|
[Column("glnr")]
|
||||||
public int GlNr { get; private set; }
|
public int GlNr { get; set; }
|
||||||
|
|
||||||
[Column("name")]
|
[Column("name")]
|
||||||
public string Name { get; private set; } = null!;
|
public string Name { get; set; } = null!;
|
||||||
|
|
||||||
[InverseProperty(nameof(WbKg.Gl))]
|
[InverseProperty(nameof(WbKg.Gl))]
|
||||||
public virtual ICollection<WbKg> Kgs { get; private set; } = null!;
|
public virtual ICollection<WbKg> Kgs { get; private set; } = null!;
|
||||||
|
@@ -15,7 +15,7 @@ namespace Elwig.Models.Entities {
|
|||||||
public virtual AT_Kg AtKg { get; private set; } = null!;
|
public virtual AT_Kg AtKg { get; private set; } = null!;
|
||||||
|
|
||||||
[ForeignKey("GlNr")]
|
[ForeignKey("GlNr")]
|
||||||
public virtual WbGl Gl { get; private set; } = null!;
|
public virtual WbGl? Gl { get; private set; } = null!;
|
||||||
|
|
||||||
[InverseProperty(nameof(WbRd.Kg))]
|
[InverseProperty(nameof(WbRd.Kg))]
|
||||||
public virtual ICollection<WbRd> Rds { get; private set; } = null!;
|
public virtual ICollection<WbRd> Rds { get; private set; } = null!;
|
||||||
|
@@ -1,5 +1,6 @@
|
|||||||
using Microsoft.EntityFrameworkCore;
|
using Microsoft.EntityFrameworkCore;
|
||||||
using System.ComponentModel.DataAnnotations.Schema;
|
using System.ComponentModel.DataAnnotations.Schema;
|
||||||
|
using System.Windows.Media;
|
||||||
|
|
||||||
namespace Elwig.Models.Entities {
|
namespace Elwig.Models.Entities {
|
||||||
[Table("wine_variety"), PrimaryKey("SortId")]
|
[Table("wine_variety"), PrimaryKey("SortId")]
|
||||||
@@ -20,6 +21,7 @@ namespace Elwig.Models.Entities {
|
|||||||
|
|
||||||
public bool IsRed => Type == "R";
|
public bool IsRed => Type == "R";
|
||||||
public bool IsWhite => Type == "W";
|
public bool IsWhite => Type == "W";
|
||||||
|
public Brush? Color => IsWhite ? Brushes.DarkGreen : IsRed ? Brushes.DarkRed : null;
|
||||||
|
|
||||||
public WineVar() { }
|
public WineVar() { }
|
||||||
|
|
||||||
|
@@ -106,13 +106,13 @@ namespace Elwig.Services {
|
|||||||
}
|
}
|
||||||
|
|
||||||
public static async Task<int> UpdateAreaCommitment(this AreaComAdminViewModel vm, int? oldFbNr) {
|
public static async Task<int> UpdateAreaCommitment(this AreaComAdminViewModel vm, int? oldFbNr) {
|
||||||
int newFbNr = (int)vm.FbNr!;
|
int newFbNr = vm.FbNr!.Value;
|
||||||
|
|
||||||
await Task.Run(async () => {
|
return await Task.Run(async () => {
|
||||||
using var ctx = new AppDbContext();
|
using var ctx = new AppDbContext();
|
||||||
var a = new AreaCom {
|
var a = new AreaCom {
|
||||||
FbNr = oldFbNr ?? newFbNr,
|
FbNr = oldFbNr ?? newFbNr,
|
||||||
MgNr = (int)vm.MgNr!,
|
MgNr = vm.MgNr!.Value,
|
||||||
YearFrom = vm.YearFrom,
|
YearFrom = vm.YearFrom,
|
||||||
YearTo = vm.YearTo,
|
YearTo = vm.YearTo,
|
||||||
VtrgId = vm.AreaComType!.VtrgId,
|
VtrgId = vm.AreaComType!.VtrgId,
|
||||||
@@ -120,8 +120,8 @@ namespace Elwig.Services {
|
|||||||
Comment = string.IsNullOrEmpty(vm.Comment) ? null : vm.Comment,
|
Comment = string.IsNullOrEmpty(vm.Comment) ? null : vm.Comment,
|
||||||
KgNr = vm.Kg!.KgNr,
|
KgNr = vm.Kg!.KgNr,
|
||||||
RdNr = vm.Rd?.RdNr,
|
RdNr = vm.Rd?.RdNr,
|
||||||
GstNr = vm.GstNr!.Trim(),
|
GstNr = vm.GstNr?.Trim() ?? "-",
|
||||||
Area = (int)vm.Area!,
|
Area = vm.Area!.Value,
|
||||||
};
|
};
|
||||||
|
|
||||||
if (vm.Rd?.RdNr == 0) {
|
if (vm.Rd?.RdNr == 0) {
|
||||||
@@ -141,11 +141,9 @@ namespace Elwig.Services {
|
|||||||
if (newFbNr != a.FbNr) {
|
if (newFbNr != a.FbNr) {
|
||||||
await ctx.Database.ExecuteSqlAsync($"UPDATE area_commitment SET fbnr = {newFbNr} WHERE fbnr = {oldFbNr}");
|
await ctx.Database.ExecuteSqlAsync($"UPDATE area_commitment SET fbnr = {newFbNr} WHERE fbnr = {oldFbNr}");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
return newFbNr;
|
||||||
});
|
});
|
||||||
|
|
||||||
App.HintContextChange();
|
|
||||||
|
|
||||||
return newFbNr;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
private static void AddToolTipCell(Grid grid, string text, int row, int col, int colSpan = 1, bool bold = false, bool alignRight = false, bool alignCenter = false) {
|
private static void AddToolTipCell(Grid grid, string text, int row, int col, int colSpan = 1, bool bold = false, bool alignRight = false, bool alignCenter = false) {
|
||||||
@@ -262,8 +260,6 @@ namespace Elwig.Services {
|
|||||||
ctx.Remove(l);
|
ctx.Remove(l);
|
||||||
await ctx.SaveChangesAsync();
|
await ctx.SaveChangesAsync();
|
||||||
});
|
});
|
||||||
|
|
||||||
App.HintContextChange();
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@@ -211,7 +211,8 @@ namespace Elwig.Services {
|
|||||||
int newMgNr = vm.MgNr!.Value;
|
int newMgNr = vm.MgNr!.Value;
|
||||||
string newSortId = vm.SortId!;
|
string newSortId = vm.SortId!;
|
||||||
|
|
||||||
using (var ctx = new AppDbContext()) {
|
return await Task.Run(async () => {
|
||||||
|
using var ctx = new AppDbContext();
|
||||||
var a = new DeliveryAncmt {
|
var a = new DeliveryAncmt {
|
||||||
Year = oldYear ?? year,
|
Year = oldYear ?? year,
|
||||||
DsNr = oldDsNr ?? dsnr,
|
DsNr = oldDsNr ?? dsnr,
|
||||||
@@ -232,11 +233,9 @@ namespace Elwig.Services {
|
|||||||
if (oldDsNr != null && (oldYear != year || oldDsNr != dsnr || oldMgNr != newMgNr || oldSortId != newSortId)) {
|
if (oldDsNr != null && (oldYear != year || oldDsNr != dsnr || oldMgNr != newMgNr || oldSortId != newSortId)) {
|
||||||
await ctx.Database.ExecuteSqlAsync($"UPDATE delivery_announcement SET year = {year}, dsnr = {dsnr}, mgnr = {newMgNr}, sortid = {newSortId} WHERE (year, dsnr, mgnr, sortid) = ({a.Year}, {a.DsNr}, {a.MgNr}, {a.SortId})");
|
await ctx.Database.ExecuteSqlAsync($"UPDATE delivery_announcement SET year = {year}, dsnr = {dsnr}, mgnr = {newMgNr}, sortid = {newSortId} WHERE (year, dsnr, mgnr, sortid) = ({a.Year}, {a.DsNr}, {a.MgNr}, {a.SortId})");
|
||||||
}
|
}
|
||||||
}
|
|
||||||
|
|
||||||
App.HintContextChange();
|
return (year, dsnr, newMgNr, newSortId);
|
||||||
|
});
|
||||||
return (year, dsnr, newMgNr, newSortId);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
public static async Task GenerateDeliveryAncmtList(this DeliveryAncmtAdminViewModel vm, ExportSubject subject, ExportMode mode) {
|
public static async Task GenerateDeliveryAncmtList(this DeliveryAncmtAdminViewModel vm, ExportSubject subject, ExportMode mode) {
|
||||||
@@ -269,25 +268,29 @@ namespace Elwig.Services {
|
|||||||
Title = $"{DeliveryAncmtList.Name} speichern unter - Elwig"
|
Title = $"{DeliveryAncmtList.Name} speichern unter - Elwig"
|
||||||
};
|
};
|
||||||
if (d.ShowDialog() == true) {
|
if (d.ShowDialog() == true) {
|
||||||
Mouse.OverrideCursor = Cursors.AppStarting;
|
Mouse.OverrideCursor = Cursors.Wait;
|
||||||
try {
|
await Task.Run(async () => {
|
||||||
var data = await DeliveryAncmtListData.FromQuery(query, filterNames);
|
try {
|
||||||
using var ods = new OdsFile(d.FileName);
|
var data = await DeliveryAncmtListData.FromQuery(query, filterNames);
|
||||||
await ods.AddTable(data);
|
using var ods = new OdsFile(d.FileName);
|
||||||
} catch (Exception exc) {
|
await ods.AddTable(data);
|
||||||
MessageBox.Show(exc.Message, "Fehler", MessageBoxButton.OK, MessageBoxImage.Error);
|
} catch (Exception exc) {
|
||||||
}
|
MessageBox.Show(exc.Message, "Fehler", MessageBoxButton.OK, MessageBoxImage.Error);
|
||||||
|
}
|
||||||
|
});
|
||||||
Mouse.OverrideCursor = null;
|
Mouse.OverrideCursor = null;
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
Mouse.OverrideCursor = Cursors.AppStarting;
|
Mouse.OverrideCursor = Cursors.Wait;
|
||||||
try {
|
await Task.Run(async () => {
|
||||||
var data = await DeliveryAncmtListData.FromQuery(query, filterNames);
|
try {
|
||||||
using var doc = new DeliveryAncmtList(string.Join(" / ", filterNames), data);
|
var data = await DeliveryAncmtListData.FromQuery(query, filterNames);
|
||||||
await Utils.ExportDocument(doc, mode);
|
using var doc = new DeliveryAncmtList(string.Join(" / ", filterNames), data);
|
||||||
} catch (Exception exc) {
|
await Utils.ExportDocument(doc, mode);
|
||||||
MessageBox.Show(exc.Message, "Fehler", MessageBoxButton.OK, MessageBoxImage.Error);
|
} catch (Exception exc) {
|
||||||
}
|
MessageBox.Show(exc.Message, "Fehler", MessageBoxButton.OK, MessageBoxImage.Error);
|
||||||
|
}
|
||||||
|
});
|
||||||
Mouse.OverrideCursor = null;
|
Mouse.OverrideCursor = null;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@@ -152,7 +152,8 @@ namespace Elwig.Services {
|
|||||||
public static async Task UpdateDeliverySchedule(this DeliveryScheduleAdminViewModel vm, int? oldYear, int? oldDsNr) {
|
public static async Task UpdateDeliverySchedule(this DeliveryScheduleAdminViewModel vm, int? oldYear, int? oldDsNr) {
|
||||||
int year = vm.Date!.Value.Year;
|
int year = vm.Date!.Value.Year;
|
||||||
|
|
||||||
using (var ctx = new AppDbContext()) {
|
await Task.Run(async () => {
|
||||||
|
using var ctx = new AppDbContext();
|
||||||
var s = new DeliverySchedule {
|
var s = new DeliverySchedule {
|
||||||
Year = oldYear ?? year,
|
Year = oldYear ?? year,
|
||||||
DsNr = oldDsNr ?? await ctx.NextDsNr(year),
|
DsNr = oldDsNr ?? await ctx.NextDsNr(year),
|
||||||
@@ -181,9 +182,7 @@ namespace Elwig.Services {
|
|||||||
.ToList(), vm.MainVarieties.Select(v => (v, 1)).Union(vm.OtherVarieties.Select(v => (v, 2))).ToList());
|
.ToList(), vm.MainVarieties.Select(v => (v, 1)).Union(vm.OtherVarieties.Select(v => (v, 2))).ToList());
|
||||||
|
|
||||||
await ctx.SaveChangesAsync();
|
await ctx.SaveChangesAsync();
|
||||||
}
|
});
|
||||||
|
|
||||||
App.HintContextChange();
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@@ -430,7 +430,7 @@ namespace Elwig.Services {
|
|||||||
}
|
}
|
||||||
|
|
||||||
public static async Task<DeliveryPart> UpdateDeliveryPart(this DeliveryAdminViewModel vm, int? oldYear, int? oldDid, int? oldDpnr, bool dateHasChanged, bool timeHasChanged, bool timeIsDefault) {
|
public static async Task<DeliveryPart> UpdateDeliveryPart(this DeliveryAdminViewModel vm, int? oldYear, int? oldDid, int? oldDpnr, bool dateHasChanged, bool timeHasChanged, bool timeIsDefault) {
|
||||||
var p = await Task.Run(async () => {
|
return await Task.Run(async () => {
|
||||||
DeliveryPart p;
|
DeliveryPart p;
|
||||||
|
|
||||||
using var ctx = new AppDbContext();
|
using var ctx = new AppDbContext();
|
||||||
@@ -528,14 +528,10 @@ namespace Elwig.Services {
|
|||||||
|
|
||||||
return p;
|
return p;
|
||||||
});
|
});
|
||||||
|
|
||||||
App.HintContextChange();
|
|
||||||
|
|
||||||
return p;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
public static async Task<Delivery> SplitDeliveryToMember(int year, int did, int[] weights, int mgnr) {
|
public static async Task<Delivery> SplitDeliveryToMember(int year, int did, int[] weights, int mgnr) {
|
||||||
var n = await Task.Run(async () => {
|
return await Task.Run(async () => {
|
||||||
Delivery n;
|
Delivery n;
|
||||||
|
|
||||||
using var ctx = new AppDbContext();
|
using var ctx = new AppDbContext();
|
||||||
@@ -584,14 +580,10 @@ namespace Elwig.Services {
|
|||||||
|
|
||||||
return n;
|
return n;
|
||||||
});
|
});
|
||||||
|
|
||||||
App.HintContextChange();
|
|
||||||
|
|
||||||
return n;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
public static async Task<Delivery> SplitDeliveryToLsNr(int year, int did, int[] weights, string lsnr) {
|
public static async Task<Delivery> SplitDeliveryToLsNr(int year, int did, int[] weights, string lsnr) {
|
||||||
var n = await Task.Run(async () => {
|
return await Task.Run(async () => {
|
||||||
Delivery n;
|
Delivery n;
|
||||||
using var ctx = new AppDbContext();
|
using var ctx = new AppDbContext();
|
||||||
var anyLeft = false;
|
var anyLeft = false;
|
||||||
@@ -625,10 +617,6 @@ namespace Elwig.Services {
|
|||||||
|
|
||||||
return n;
|
return n;
|
||||||
});
|
});
|
||||||
|
|
||||||
App.HintContextChange();
|
|
||||||
|
|
||||||
return n;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
public static async Task DepreciateDelivery(int year, int did, int[] weights) {
|
public static async Task DepreciateDelivery(int year, int did, int[] weights) {
|
||||||
@@ -658,8 +646,6 @@ namespace Elwig.Services {
|
|||||||
}
|
}
|
||||||
await ctx.SaveChangesAsync();
|
await ctx.SaveChangesAsync();
|
||||||
});
|
});
|
||||||
|
|
||||||
App.HintContextChange();
|
|
||||||
}
|
}
|
||||||
|
|
||||||
public static async Task GenerateDeliveryNote(int year, int did, ExportMode mode) {
|
public static async Task GenerateDeliveryNote(int year, int did, ExportMode mode) {
|
||||||
@@ -741,13 +727,22 @@ namespace Elwig.Services {
|
|||||||
Mouse.OverrideCursor = Cursors.Wait;
|
Mouse.OverrideCursor = Cursors.Wait;
|
||||||
await Task.Run(async () => {
|
await Task.Run(async () => {
|
||||||
try {
|
try {
|
||||||
await ElwigData.Export(d.FileName, await query
|
var list = await query
|
||||||
.Select(p => p.Delivery)
|
.Select(p => p.Delivery)
|
||||||
.Distinct()
|
.Distinct()
|
||||||
.Include(d => d.Parts)
|
.Include(d => d.Parts).ThenInclude(p => p.PartModifiers)
|
||||||
.ThenInclude(p => p.PartModifiers)
|
.Include(d => d.Parts).ThenInclude(p => p.Rd)
|
||||||
|
.Include(d => d.Parts).ThenInclude(p => p.Kg!.Gl)
|
||||||
.AsSplitQuery()
|
.AsSplitQuery()
|
||||||
.ToListAsync(), filterNames);
|
.ToListAsync();
|
||||||
|
var wbKgs = list
|
||||||
|
.SelectMany(d => d.Parts)
|
||||||
|
.Where(p => p.Kg != null)
|
||||||
|
.Select(p => p.Kg!)
|
||||||
|
.DistinctBy(k => k.KgNr)
|
||||||
|
.OrderBy(k => k.KgNr)
|
||||||
|
.ToList();
|
||||||
|
await ElwigData.Export(d.FileName, list, wbKgs, filterNames);
|
||||||
} catch (Exception exc) {
|
} catch (Exception exc) {
|
||||||
MessageBox.Show(exc.Message, "Fehler", MessageBoxButton.OK, MessageBoxImage.Error);
|
MessageBox.Show(exc.Message, "Fehler", MessageBoxButton.OK, MessageBoxImage.Error);
|
||||||
}
|
}
|
||||||
@@ -763,15 +758,23 @@ namespace Elwig.Services {
|
|||||||
var list = await query
|
var list = await query
|
||||||
.Select(p => p.Delivery)
|
.Select(p => p.Delivery)
|
||||||
.Distinct()
|
.Distinct()
|
||||||
.Include(d => d.Parts)
|
.Include(d => d.Parts).ThenInclude(p => p.PartModifiers)
|
||||||
.ThenInclude(p => p.PartModifiers)
|
.Include(d => d.Parts).ThenInclude(p => p.Rd)
|
||||||
|
.Include(d => d.Parts).ThenInclude(p => p.Kg!.Gl)
|
||||||
.AsSplitQuery()
|
.AsSplitQuery()
|
||||||
.ToListAsync();
|
.ToListAsync();
|
||||||
|
var wbKgs = list
|
||||||
|
.SelectMany(d => d.Parts)
|
||||||
|
.Where(p => p.Kg != null)
|
||||||
|
.Select(p => p.Kg!)
|
||||||
|
.DistinctBy(k => k.KgNr)
|
||||||
|
.OrderBy(k => k.KgNr)
|
||||||
|
.ToList();
|
||||||
if (list.Count == 0) {
|
if (list.Count == 0) {
|
||||||
MessageBox.Show("Es wurden keine Lieferungen zum Hochladen ausgewählt!", "Lieferungen hochladen",
|
MessageBox.Show("Es wurden keine Lieferungen zum Hochladen ausgewählt!", "Lieferungen hochladen",
|
||||||
MessageBoxButton.OK, MessageBoxImage.Error);
|
MessageBoxButton.OK, MessageBoxImage.Error);
|
||||||
} else {
|
} else {
|
||||||
await ElwigData.Export(path, list, filterNames);
|
await ElwigData.Export(path, list, wbKgs, filterNames);
|
||||||
await Utils.UploadExportData(path, App.Config.SyncUrl, App.Config.SyncUsername, App.Config.SyncPassword);
|
await Utils.UploadExportData(path, App.Config.SyncUrl, App.Config.SyncUsername, App.Config.SyncPassword);
|
||||||
MessageBox.Show($"Hochladen von {list.Count:N0} Lieferungen erfolgreich!", "Lieferungen hochgeladen",
|
MessageBox.Show($"Hochladen von {list.Count:N0} Lieferungen erfolgreich!", "Lieferungen hochgeladen",
|
||||||
MessageBoxButton.OK, MessageBoxImage.Information);
|
MessageBoxButton.OK, MessageBoxImage.Information);
|
||||||
@@ -1074,7 +1077,7 @@ namespace Elwig.Services {
|
|||||||
wGrid.ColumnDefinitions.Add(new() { Width = new(50) });
|
wGrid.ColumnDefinitions.Add(new() { Width = new(50) });
|
||||||
int rowNum = 0;
|
int rowNum = 0;
|
||||||
foreach (var row in weightData) {
|
foreach (var row in weightData) {
|
||||||
if (rowNum == 1 || (rowNum != 0 && row.Item1 != null)) rowNum++;
|
if (rowNum != 0 && row.Item2 == null) rowNum++;
|
||||||
AddWeightToolTipRow(wGrid, rowNum++, row.Item1, row.Item2, row.Item3, row.Item4, row.Item5);
|
AddWeightToolTipRow(wGrid, rowNum++, row.Item1, row.Item2, row.Item3, row.Item4, row.Item5);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -1089,7 +1092,7 @@ namespace Elwig.Services {
|
|||||||
AddToolTipCell(gGrid, "Max.", 0, 4, 1, false, false, true);
|
AddToolTipCell(gGrid, "Max.", 0, 4, 1, false, false, true);
|
||||||
rowNum = 1;
|
rowNum = 1;
|
||||||
foreach (var row in gradationData) {
|
foreach (var row in gradationData) {
|
||||||
if (rowNum == 2 || (rowNum != 1 && row.Item1 != null)) rowNum++;
|
if (rowNum != 1 && row.Item2 == null) rowNum++;
|
||||||
AddGradationToolTipRow(gGrid, rowNum++, row.Item1, row.Item2, row.Item3, row.Item4, row.Item5);
|
AddGradationToolTipRow(gGrid, rowNum++, row.Item1, row.Item2, row.Item3, row.Item4, row.Item5);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -1102,8 +1105,6 @@ namespace Elwig.Services {
|
|||||||
await ctx.Deliveries.Where(d => d.LsNr == lsnr).ExecuteDeleteAsync();
|
await ctx.Deliveries.Where(d => d.LsNr == lsnr).ExecuteDeleteAsync();
|
||||||
await ctx.SaveChangesAsync();
|
await ctx.SaveChangesAsync();
|
||||||
});
|
});
|
||||||
|
|
||||||
App.HintContextChange();
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@@ -509,13 +509,22 @@ namespace Elwig.Services {
|
|||||||
.Include(m => m.BillingAddress)
|
.Include(m => m.BillingAddress)
|
||||||
.Include(m => m.TelephoneNumbers)
|
.Include(m => m.TelephoneNumbers)
|
||||||
.Include(m => m.EmailAddresses)
|
.Include(m => m.EmailAddresses)
|
||||||
|
.Include(m => m.DefaultWbKg!.Gl)
|
||||||
.AsSplitQuery()
|
.AsSplitQuery()
|
||||||
.ToListAsync();
|
.ToListAsync();
|
||||||
var areaComs = await query
|
var areaComs = await query
|
||||||
.SelectMany(m => m.AreaCommitments)
|
.SelectMany(m => m.AreaCommitments)
|
||||||
.Include(c => c.Rd)
|
.Include(c => c.Rd)
|
||||||
|
.Include(c => c.Kg.Gl)
|
||||||
.ToListAsync();
|
.ToListAsync();
|
||||||
await ElwigData.Export(d.FileName, members, areaComs, filterNames);
|
var wbKgs = members
|
||||||
|
.Where(m => m.DefaultWbKg != null)
|
||||||
|
.Select(m => m.DefaultWbKg!)
|
||||||
|
.Union(areaComs.Select(c => c.Kg))
|
||||||
|
.Distinct()
|
||||||
|
.OrderBy(k => k.KgNr)
|
||||||
|
.ToList();
|
||||||
|
await ElwigData.Export(d.FileName, members, areaComs, wbKgs, filterNames);
|
||||||
} catch (Exception exc) {
|
} catch (Exception exc) {
|
||||||
MessageBox.Show(exc.Message, "Fehler", MessageBoxButton.OK, MessageBoxImage.Error);
|
MessageBox.Show(exc.Message, "Fehler", MessageBoxButton.OK, MessageBoxImage.Error);
|
||||||
}
|
}
|
||||||
@@ -533,17 +542,27 @@ namespace Elwig.Services {
|
|||||||
.Include(m => m.BillingAddress)
|
.Include(m => m.BillingAddress)
|
||||||
.Include(m => m.TelephoneNumbers)
|
.Include(m => m.TelephoneNumbers)
|
||||||
.Include(m => m.EmailAddresses)
|
.Include(m => m.EmailAddresses)
|
||||||
|
.Include(m => m.DefaultWbKg!.Gl)
|
||||||
.AsSplitQuery()
|
.AsSplitQuery()
|
||||||
.ToListAsync();
|
.ToListAsync();
|
||||||
var areaComs = await query
|
var areaComs = await query
|
||||||
.SelectMany(m => m.AreaCommitments)
|
.SelectMany(m => m.AreaCommitments)
|
||||||
|
.OrderBy(c => c.MgNr).ThenBy(c => c.FbNr)
|
||||||
.Include(c => c.Rd)
|
.Include(c => c.Rd)
|
||||||
|
.Include(c => c.Kg.Gl)
|
||||||
.ToListAsync();
|
.ToListAsync();
|
||||||
|
var wbKgs = members
|
||||||
|
.Where(m => m.DefaultWbKg != null)
|
||||||
|
.Select(m => m.DefaultWbKg!)
|
||||||
|
.Union(areaComs.Select(c => c.Kg))
|
||||||
|
.Distinct()
|
||||||
|
.OrderBy(k => k.KgNr)
|
||||||
|
.ToList();
|
||||||
if (members.Count == 0) {
|
if (members.Count == 0) {
|
||||||
MessageBox.Show("Es wurden keine Mitglieder zum Hochladen ausgewählt!", "Mitglieder hochladen",
|
MessageBox.Show("Es wurden keine Mitglieder zum Hochladen ausgewählt!", "Mitglieder hochladen",
|
||||||
MessageBoxButton.OK, MessageBoxImage.Error);
|
MessageBoxButton.OK, MessageBoxImage.Error);
|
||||||
} else {
|
} else {
|
||||||
await ElwigData.Export(path, members, areaComs, filterNames);
|
await ElwigData.Export(path, members, areaComs, wbKgs, filterNames);
|
||||||
await Utils.UploadExportData(path, App.Config.SyncUrl, App.Config.SyncUsername, App.Config.SyncPassword);
|
await Utils.UploadExportData(path, App.Config.SyncUrl, App.Config.SyncUsername, App.Config.SyncPassword);
|
||||||
MessageBox.Show($"Hochladen von {members.Count:N0} Mitgliedern erfolgreich!", "Mitglieder hochgeladen",
|
MessageBox.Show($"Hochladen von {members.Count:N0} Mitgliedern erfolgreich!", "Mitglieder hochgeladen",
|
||||||
MessageBoxButton.OK, MessageBoxImage.Information);
|
MessageBoxButton.OK, MessageBoxImage.Information);
|
||||||
@@ -611,7 +630,7 @@ namespace Elwig.Services {
|
|||||||
ContactViaEmail = vm.ContactViaEmail,
|
ContactViaEmail = vm.ContactViaEmail,
|
||||||
};
|
};
|
||||||
|
|
||||||
await Task.Run(async () => {
|
return await Task.Run(async () => {
|
||||||
using var ctx = new AppDbContext();
|
using var ctx = new AppDbContext();
|
||||||
if (oldMgNr != null) {
|
if (oldMgNr != null) {
|
||||||
ctx.Update(m);
|
ctx.Update(m);
|
||||||
@@ -695,11 +714,9 @@ namespace Elwig.Services {
|
|||||||
if (newMgNr != m.MgNr) {
|
if (newMgNr != m.MgNr) {
|
||||||
await ctx.Database.ExecuteSqlAsync($"UPDATE member SET mgnr = {newMgNr} WHERE mgnr = {oldMgNr}");
|
await ctx.Database.ExecuteSqlAsync($"UPDATE member SET mgnr = {newMgNr} WHERE mgnr = {oldMgNr}");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
return newMgNr;
|
||||||
});
|
});
|
||||||
|
|
||||||
App.HintContextChange();
|
|
||||||
|
|
||||||
return newMgNr;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
public static async Task DeleteMember(int mgnr, bool deletePaymentData, bool deleteDeliveries, bool deleteAreaComs) {
|
public static async Task DeleteMember(int mgnr, bool deletePaymentData, bool deleteDeliveries, bool deleteAreaComs) {
|
||||||
@@ -718,8 +735,6 @@ namespace Elwig.Services {
|
|||||||
ctx.Remove(l);
|
ctx.Remove(l);
|
||||||
await ctx.SaveChangesAsync();
|
await ctx.SaveChangesAsync();
|
||||||
});
|
});
|
||||||
|
|
||||||
App.HintContextChange();
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@@ -287,8 +287,7 @@ namespace Elwig.Services {
|
|||||||
}
|
}
|
||||||
|
|
||||||
public static async Task<PaymentVar> CreatePaymentVariant(int year) {
|
public static async Task<PaymentVar> CreatePaymentVariant(int year) {
|
||||||
Mouse.OverrideCursor = Cursors.Wait;
|
return await Task.Run(async () => {
|
||||||
var v = await Task.Run(async () => {
|
|
||||||
using var ctx = new AppDbContext();
|
using var ctx = new AppDbContext();
|
||||||
var v = new PaymentVar {
|
var v = new PaymentVar {
|
||||||
Year = year,
|
Year = year,
|
||||||
@@ -302,13 +301,10 @@ namespace Elwig.Services {
|
|||||||
await ctx.SaveChangesAsync();
|
await ctx.SaveChangesAsync();
|
||||||
return v;
|
return v;
|
||||||
});
|
});
|
||||||
App.HintContextChange();
|
|
||||||
Mouse.OverrideCursor = null;
|
|
||||||
return v;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
public static async Task<PaymentVar> Duplicate(this PaymentVar orig) {
|
public static async Task<PaymentVar> Duplicate(this PaymentVar orig) {
|
||||||
var n = await Task.Run(async () => {
|
return await Task.Run(async () => {
|
||||||
using var ctx = new AppDbContext();
|
using var ctx = new AppDbContext();
|
||||||
var n = new PaymentVar {
|
var n = new PaymentVar {
|
||||||
Year = orig.Year,
|
Year = orig.Year,
|
||||||
@@ -322,8 +318,6 @@ namespace Elwig.Services {
|
|||||||
await ctx.SaveChangesAsync();
|
await ctx.SaveChangesAsync();
|
||||||
return n;
|
return n;
|
||||||
});
|
});
|
||||||
App.HintContextChange();
|
|
||||||
return n;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
public static async Task<(int, int)> UpdatePaymentVariant(this PaymentVariantsViewModel vm, int? oldYear, int? oldAvNr) {
|
public static async Task<(int, int)> UpdatePaymentVariant(this PaymentVariantsViewModel vm, int? oldYear, int? oldAvNr) {
|
||||||
@@ -357,7 +351,6 @@ namespace Elwig.Services {
|
|||||||
await ctx.SaveChangesAsync();
|
await ctx.SaveChangesAsync();
|
||||||
});
|
});
|
||||||
vm.WeightModifierChanged = false;
|
vm.WeightModifierChanged = false;
|
||||||
App.HintContextChange();
|
|
||||||
return (year, avnr);
|
return (year, avnr);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -368,7 +361,6 @@ namespace Elwig.Services {
|
|||||||
ctx.Remove(v);
|
ctx.Remove(v);
|
||||||
await ctx.SaveChangesAsync();
|
await ctx.SaveChangesAsync();
|
||||||
});
|
});
|
||||||
App.HintContextChange();
|
|
||||||
}
|
}
|
||||||
|
|
||||||
public static async Task Calculate(int year, int avnr) {
|
public static async Task Calculate(int year, int avnr) {
|
||||||
@@ -376,7 +368,6 @@ namespace Elwig.Services {
|
|||||||
var b = new BillingVariant(year, avnr);
|
var b = new BillingVariant(year, avnr);
|
||||||
await b.Calculate();
|
await b.Calculate();
|
||||||
});
|
});
|
||||||
App.HintContextChange();
|
|
||||||
}
|
}
|
||||||
|
|
||||||
public static async Task Commit(int year, int avnr) {
|
public static async Task Commit(int year, int avnr) {
|
||||||
@@ -384,7 +375,6 @@ namespace Elwig.Services {
|
|||||||
var b = new BillingVariant(year, avnr);
|
var b = new BillingVariant(year, avnr);
|
||||||
await b.Commit();
|
await b.Commit();
|
||||||
});
|
});
|
||||||
App.HintContextChange();
|
|
||||||
}
|
}
|
||||||
|
|
||||||
public static async Task Revert(int year, int avnr) {
|
public static async Task Revert(int year, int avnr) {
|
||||||
@@ -392,7 +382,6 @@ namespace Elwig.Services {
|
|||||||
var b = new BillingVariant(year, avnr);
|
var b = new BillingVariant(year, avnr);
|
||||||
await b.Revert();
|
await b.Revert();
|
||||||
});
|
});
|
||||||
App.HintContextChange();
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@@ -570,6 +570,14 @@ namespace Elwig.Windows {
|
|||||||
InputLostFocus((TextBox)sender, Validator.CheckLfbisNr);
|
InputLostFocus((TextBox)sender, Validator.CheckLfbisNr);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
protected void OrganicAuthorityCodeInput_TextChanged(object sender, TextChangedEventArgs? evt) {
|
||||||
|
InputTextChanged((TextBox)sender, Validator.CheckOrganicAuthorityCode);
|
||||||
|
}
|
||||||
|
|
||||||
|
protected void OrganicAuthorityCodeInput_LostFocus(object sender, RoutedEventArgs? evt) {
|
||||||
|
InputLostFocus((TextBox)sender, Validator.CheckOrganicAuthorityCode);
|
||||||
|
}
|
||||||
|
|
||||||
protected void UpperCaseInput_TextChanged(object sender, TextChangedEventArgs? evt) {
|
protected void UpperCaseInput_TextChanged(object sender, TextChangedEventArgs? evt) {
|
||||||
InputTextChanged((TextBox)sender, Validator.CheckUpperCase);
|
InputTextChanged((TextBox)sender, Validator.CheckUpperCase);
|
||||||
}
|
}
|
||||||
|
@@ -7,7 +7,7 @@
|
|||||||
xmlns:local="clr-namespace:Elwig.Windows"
|
xmlns:local="clr-namespace:Elwig.Windows"
|
||||||
xmlns:ctrl="clr-namespace:Elwig.Controls"
|
xmlns:ctrl="clr-namespace:Elwig.Controls"
|
||||||
xmlns:vm="clr-namespace:Elwig.ViewModels"
|
xmlns:vm="clr-namespace:Elwig.ViewModels"
|
||||||
Title="{Binding Title}" Height="550" MinHeight="450" Width="920" MinWidth="860"
|
Title="{Binding Title}" Height="600" MinHeight="450" Width="1000" MinWidth="860"
|
||||||
Loaded="Window_Loaded">
|
Loaded="Window_Loaded">
|
||||||
<Window.DataContext>
|
<Window.DataContext>
|
||||||
<vm:AreaComAdminViewModel/>
|
<vm:AreaComAdminViewModel/>
|
||||||
@@ -57,7 +57,7 @@
|
|||||||
<RowDefinition Height="24"/>
|
<RowDefinition Height="24"/>
|
||||||
</Grid.RowDefinitions>
|
</Grid.RowDefinitions>
|
||||||
<Grid.ColumnDefinitions>
|
<Grid.ColumnDefinitions>
|
||||||
<ColumnDefinition Width="2*" MinWidth="555"/>
|
<ColumnDefinition Width="3*" MinWidth="500"/>
|
||||||
<ColumnDefinition Width="5"/>
|
<ColumnDefinition Width="5"/>
|
||||||
<ColumnDefinition Width="*" MinWidth="280"/>
|
<ColumnDefinition Width="*" MinWidth="280"/>
|
||||||
</Grid.ColumnDefinitions>
|
</Grid.ColumnDefinitions>
|
||||||
@@ -102,25 +102,35 @@
|
|||||||
CanUserDeleteRows="False" CanUserResizeRows="False" CanUserAddRows="False" SelectionChanged="AreaCommitmentList_SelectionChanged" Grid.Column="0" Grid.Row="1"
|
CanUserDeleteRows="False" CanUserResizeRows="False" CanUserAddRows="False" SelectionChanged="AreaCommitmentList_SelectionChanged" Grid.Column="0" Grid.Row="1"
|
||||||
Margin="5,0,5,0" FontSize="14" Grid.ColumnSpan="3" Background="#e2e2e2">
|
Margin="5,0,5,0" FontSize="14" Grid.ColumnSpan="3" Background="#e2e2e2">
|
||||||
<DataGrid.Columns>
|
<DataGrid.Columns>
|
||||||
<DataGridTextColumn Header="FbNr." Binding="{Binding FbNr}" Width="50"/>
|
<DataGridTextColumn Header="FbNr." Binding="{Binding FbNr, StringFormat='{}{0} '}" Width="50">
|
||||||
<DataGridTextColumn Header="Katastralgemeinde" Binding="{Binding Kg.AtKg.Name}" Width="150"/>
|
|
||||||
<DataGridTextColumn Header="Ried" Binding="{Binding Rd.Name}" Width="130"/>
|
|
||||||
<DataGridTextColumn Header="Parzelle" Binding="{Binding GstNr}" Width="120"/>
|
|
||||||
<DataGridTextColumn Header="Fläche" Binding="{Binding Area, StringFormat='{}{0:N0} m²'}" Width="80">
|
|
||||||
<DataGridTextColumn.CellStyle>
|
<DataGridTextColumn.CellStyle>
|
||||||
<Style>
|
<Style>
|
||||||
<Setter Property="TextBlock.TextAlignment" Value="Right"/>
|
<Setter Property="TextBlock.TextAlignment" Value="Right"/>
|
||||||
</Style>
|
</Style>
|
||||||
</DataGridTextColumn.CellStyle>
|
</DataGridTextColumn.CellStyle>
|
||||||
</DataGridTextColumn>
|
</DataGridTextColumn>
|
||||||
<DataGridTextColumn Header="Sorte" Binding="{Binding AreaComType.WineVar.SortId}" Width="70">
|
<DataGridTextColumn Header="Katastralgemeinde" Binding="{Binding Kg.AtKg.Name}" Width="130"/>
|
||||||
|
<DataGridTextColumn Header="Sorte" Binding="{Binding AreaComType.WineVar.SortId}" Width="50">
|
||||||
<DataGridTextColumn.CellStyle>
|
<DataGridTextColumn.CellStyle>
|
||||||
<Style>
|
<Style>
|
||||||
|
<Setter Property="TextBlock.Foreground" Value="{Binding AreaComType.WineVar.Color}"/>
|
||||||
<Setter Property="TextBlock.TextAlignment" Value="Center"/>
|
<Setter Property="TextBlock.TextAlignment" Value="Center"/>
|
||||||
</Style>
|
</Style>
|
||||||
</DataGridTextColumn.CellStyle>
|
</DataGridTextColumn.CellStyle>
|
||||||
</DataGridTextColumn>
|
</DataGridTextColumn>
|
||||||
<DataGridTextColumn Header="Attribut" Binding="{Binding AreaComType.WineAttr.Name}" Width="120"/>
|
<DataGridTextColumn Header="Fläche" Binding="{Binding Area, StringFormat='{}{0:N0} m² '}" Width="80">
|
||||||
|
<DataGridTextColumn.CellStyle>
|
||||||
|
<Style>
|
||||||
|
<Setter Property="TextBlock.TextAlignment" Value="Right"/>
|
||||||
|
</Style>
|
||||||
|
</DataGridTextColumn.CellStyle>
|
||||||
|
</DataGridTextColumn>
|
||||||
|
<DataGridTextColumn Header="Attribut" Binding="{Binding AreaComType.WineAttr.Name}" Width="100"/>
|
||||||
|
<DataGridTextColumn Header="Ried" Binding="{Binding Rd.Name}" Width="130"/>
|
||||||
|
<DataGridTextColumn Header="Parzelle" Binding="{Binding GstNr}" Width="130"/>
|
||||||
|
<DataGridTextColumn Header="Bewirt." Binding="{Binding WineCult.Name}" Width="60"/>
|
||||||
|
<DataGridTextColumn Header="Von" Binding="{Binding YearFrom}" Width="48"/>
|
||||||
|
<DataGridTextColumn Header="Bis" Binding="{Binding YearTo}" Width="48"/>
|
||||||
</DataGrid.Columns>
|
</DataGrid.Columns>
|
||||||
</DataGrid>
|
</DataGrid>
|
||||||
|
|
||||||
@@ -143,19 +153,19 @@
|
|||||||
</Button.ToolTip>
|
</Button.ToolTip>
|
||||||
</Button>
|
</Button>
|
||||||
|
|
||||||
<Button x:Name="AreaCommitmentSaveButton" Content="Speichern" Click="AreaCommitmentSaveButton_Click" IsEnabled="False" Visibility="Hidden"
|
<Button x:Name="SaveButton" Content="Speichern" Click="SaveButton_Click" IsEnabled="False" Visibility="Hidden"
|
||||||
HorizontalAlignment="Stretch" VerticalAlignment="Bottom" Margin="5,5,2.5,10" Grid.Column="0" Grid.Row="2">
|
HorizontalAlignment="Stretch" VerticalAlignment="Bottom" Margin="5,5,2.5,10" Grid.Column="0" Grid.Row="2">
|
||||||
<Button.ToolTip>
|
<Button.ToolTip>
|
||||||
<TextBlock FontWeight="Bold">Strg+S</TextBlock>
|
<TextBlock FontWeight="Bold">Strg+S</TextBlock>
|
||||||
</Button.ToolTip>
|
</Button.ToolTip>
|
||||||
</Button>
|
</Button>
|
||||||
<Button x:Name="AreaCommitmentResetButton" Content="Zurücksetzen" Click="AreaCommitmentResetButton_Click" IsEnabled="False" Visibility="Hidden"
|
<Button x:Name="ResetButton" Content="Zurücksetzen" Click="ResetButton_Click" IsEnabled="False" Visibility="Hidden"
|
||||||
HorizontalAlignment="Stretch" VerticalAlignment="Bottom" Margin="2.5,5,2.5,10" Grid.Column="1" Grid.Row="2">
|
HorizontalAlignment="Stretch" VerticalAlignment="Bottom" Margin="2.5,5,2.5,10" Grid.Column="1" Grid.Row="2">
|
||||||
<Button.ToolTip>
|
<Button.ToolTip>
|
||||||
<TextBlock FontWeight="Bold">Strg+Z</TextBlock>
|
<TextBlock FontWeight="Bold">Strg+Z</TextBlock>
|
||||||
</Button.ToolTip>
|
</Button.ToolTip>
|
||||||
</Button>
|
</Button>
|
||||||
<Button x:Name="AreaCommitmentCancelButton" Content="Abbrechen" Click="AreaCommitmentCancelButton_Click" IsEnabled="False" Visibility="Hidden" IsCancel="True"
|
<Button x:Name="CancelButton" Content="Abbrechen" Click="CancelButton_Click" IsEnabled="False" Visibility="Hidden" IsCancel="True"
|
||||||
HorizontalAlignment="Stretch" VerticalAlignment="Bottom" Margin="2.5,5,5,10" Grid.Column="2" Grid.Row="2">
|
HorizontalAlignment="Stretch" VerticalAlignment="Bottom" Margin="2.5,5,5,10" Grid.Column="2" Grid.Row="2">
|
||||||
<Button.ToolTip>
|
<Button.ToolTip>
|
||||||
<TextBlock FontWeight="Bold">Esc</TextBlock>
|
<TextBlock FontWeight="Bold">Esc</TextBlock>
|
||||||
@@ -175,33 +185,32 @@
|
|||||||
<Grid>
|
<Grid>
|
||||||
<Grid.ColumnDefinitions>
|
<Grid.ColumnDefinitions>
|
||||||
<ColumnDefinition Width="80"/>
|
<ColumnDefinition Width="80"/>
|
||||||
<ColumnDefinition Width="*"/>
|
<ColumnDefinition Width="48"/>
|
||||||
<ColumnDefinition Width="50"/>
|
<ColumnDefinition Width="60"/>
|
||||||
<ColumnDefinition Width="*"/>
|
<ColumnDefinition Width="*"/>
|
||||||
</Grid.ColumnDefinitions>
|
</Grid.ColumnDefinitions>
|
||||||
|
|
||||||
<Label Content="FbNr.:" Margin="10,10,0,0" Grid.Column="0"/>
|
<Label Content="MgNr.:" Margin="10,10,0,0" Grid.Column="0"/>
|
||||||
|
<TextBox x:Name="MgNrInput" Text="{Binding MgNrString, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}" IsEnabled="False"
|
||||||
|
Margin="0,10,0,0" Width="48" HorizontalAlignment="Left" Grid.Column="1" TextAlignment="Right"/>
|
||||||
|
|
||||||
|
<Label Content="FbNr.:" Margin="10,10,0,0" Grid.Column="2"/>
|
||||||
<TextBox x:Name="FbNrInput" Text="{Binding FbNrString, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"
|
<TextBox x:Name="FbNrInput" Text="{Binding FbNrString, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"
|
||||||
Margin="0,10,10,0" Grid.Column="1" TextAlignment="Right"
|
Margin="0,10,10,0" Width="56" HorizontalAlignment="Left" Grid.Column="3" TextAlignment="Right"
|
||||||
TextChanged="FbNrInput_TextChanged" LostFocus="FbNrInput_LostFocus"/>
|
TextChanged="FbNrInput_TextChanged" LostFocus="FbNrInput_LostFocus"/>
|
||||||
|
|
||||||
<Label Content="MgNr.:" Margin="10,40,0,0" Grid.Column="0"/>
|
<Label Content="Zeitraum:" Margin="10,40,0,0" Grid.Column="0"/>
|
||||||
<TextBox x:Name="MgNrInput" Text="{Binding MgNrString, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}" IsEnabled="False"
|
|
||||||
Margin="0,40,10,0" Grid.Column="1" TextAlignment="Right"/>
|
|
||||||
|
|
||||||
<Label Content="Von:" Margin="10,10,0,0" Grid.Column="2"/>
|
|
||||||
<TextBox x:Name="YearFromInput" Text="{Binding YearFromString, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"
|
<TextBox x:Name="YearFromInput" Text="{Binding YearFromString, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"
|
||||||
Margin="0,10,10,0" Grid.Column="3" TextAlignment="Right"
|
Margin="0,40,10,0" Width="40" HorizontalAlignment="Left" Grid.Column="1" Grid.ColumnSpan="2" TextAlignment="Right"
|
||||||
TextChanged="IntegerInput_TextChanged"/>
|
TextChanged="IntegerInput_TextChanged"/>
|
||||||
|
<Label Content="–" Grid.Column="1" Grid.ColumnSpan="3" Margin="45,40,0,0"/>
|
||||||
<Label Content="Bis:" Margin="10,40,0,0" Grid.Column="2"/>
|
|
||||||
<TextBox x:Name="YearToInput" Text="{Binding YearToString, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"
|
<TextBox x:Name="YearToInput" Text="{Binding YearToString, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"
|
||||||
Margin="0,40,10,0" Grid.Column="3" TextAlignment="Right"
|
Margin="60,40,10,0" Width="40" HorizontalAlignment="Left" Grid.Column="1" Grid.ColumnSpan="3" TextAlignment="Right"
|
||||||
TextChanged="IntegerInput_TextChanged"/>
|
TextChanged="IntegerInput_TextChanged"/>
|
||||||
|
|
||||||
<Label Content="Vertragsart:" Margin="10,70,0,0" Grid.Column="0" Grid.ColumnSpan="2"/>
|
<Label Content="Vertragsart:" Margin="10,70,0,0" Grid.Column="0" Grid.ColumnSpan="2"/>
|
||||||
<ComboBox x:Name="AreaComTypeInput" SelectedItem="{Binding AreaComType, Mode=TwoWay}" ItemsSource="{Binding AreaComTypeSource, Mode=TwoWay}"
|
<ComboBox x:Name="AreaComTypeInput" SelectedItem="{Binding AreaComType, Mode=TwoWay}" ItemsSource="{Binding AreaComTypeSource, Mode=TwoWay}"
|
||||||
DisplayMemberPath="DisplayName" TextSearch.TextPath="DisplayName"
|
ItemTemplate="{StaticResource AreaCommitmentTypeTemplate}" TextSearch.TextPath="DisplayName"
|
||||||
HorizontalAlignment="Stretch" Margin="0,70,40,10" Grid.Column="1" Grid.ColumnSpan="3"/>
|
HorizontalAlignment="Stretch" Margin="0,70,40,10" Grid.Column="1" Grid.ColumnSpan="3"/>
|
||||||
<Button x:Name="AreaComTypeDetailsButton" Content="" FontFamily="Segoe MDL2 Assets" FontSize="14" Padding="0,1,0,0"
|
<Button x:Name="AreaComTypeDetailsButton" Content="" FontFamily="Segoe MDL2 Assets" FontSize="14" Padding="0,1,0,0"
|
||||||
Click="AreaComTypeDetailsButton_Click"
|
Click="AreaComTypeDetailsButton_Click"
|
||||||
|
@@ -1,13 +1,14 @@
|
|||||||
using Microsoft.EntityFrameworkCore;
|
using Elwig.Dialogs;
|
||||||
using System.Linq;
|
|
||||||
using System.Windows;
|
|
||||||
using System.Windows.Controls;
|
|
||||||
using Elwig.Helpers;
|
using Elwig.Helpers;
|
||||||
using Elwig.Models.Entities;
|
using Elwig.Models.Entities;
|
||||||
using System;
|
|
||||||
using System.Threading.Tasks;
|
|
||||||
using Elwig.ViewModels;
|
|
||||||
using Elwig.Services;
|
using Elwig.Services;
|
||||||
|
using Elwig.ViewModels;
|
||||||
|
using Microsoft.EntityFrameworkCore;
|
||||||
|
using System;
|
||||||
|
using System.Linq;
|
||||||
|
using System.Threading.Tasks;
|
||||||
|
using System.Windows;
|
||||||
|
using System.Windows.Controls;
|
||||||
using System.Windows.Input;
|
using System.Windows.Input;
|
||||||
|
|
||||||
namespace Elwig.Windows {
|
namespace Elwig.Windows {
|
||||||
@@ -25,8 +26,8 @@ namespace Elwig.Windows {
|
|||||||
ViewModel.Title = $"Flächenbindungen - {ViewModel.FilterMember.AdministrativeName} - Elwig";
|
ViewModel.Title = $"Flächenbindungen - {ViewModel.FilterMember.AdministrativeName} - Elwig";
|
||||||
ExemptInputs = [
|
ExemptInputs = [
|
||||||
MgNrInput, AreaCommitmentList, NewAreaCommitmentButton,
|
MgNrInput, AreaCommitmentList, NewAreaCommitmentButton,
|
||||||
EditAreaCommitmentButton, DeleteAreaCommitmentButton, AreaCommitmentSaveButton,
|
EditAreaCommitmentButton, DeleteAreaCommitmentButton, SaveButton,
|
||||||
AreaCommitmentResetButton, AreaCommitmentCancelButton, SearchInput, ActiveAreaCommitmentInput
|
ResetButton, CancelButton, SearchInput, ActiveAreaCommitmentInput
|
||||||
];
|
];
|
||||||
RequiredInputs = [
|
RequiredInputs = [
|
||||||
FbNrInput, YearFromInput, KgInput, RdInput,
|
FbNrInput, YearFromInput, KgInput, RdInput,
|
||||||
@@ -163,8 +164,8 @@ namespace Elwig.Windows {
|
|||||||
IsCreating = true;
|
IsCreating = true;
|
||||||
AreaCommitmentList.IsEnabled = false;
|
AreaCommitmentList.IsEnabled = false;
|
||||||
AreaCommitmentList.SelectedItem = null;
|
AreaCommitmentList.SelectedItem = null;
|
||||||
HideAreaCommitmentNewEditDeleteButtons();
|
HideNewEditDeleteButtons();
|
||||||
ShowAreaCommitmentSaveResetCancelButtons();
|
ShowSaveResetCancelButtons();
|
||||||
UnlockInputs();
|
UnlockInputs();
|
||||||
await InitInputs();
|
await InitInputs();
|
||||||
LockSearchInputs();
|
LockSearchInputs();
|
||||||
@@ -184,8 +185,8 @@ namespace Elwig.Windows {
|
|||||||
IsEditing = true;
|
IsEditing = true;
|
||||||
AreaCommitmentList.IsEnabled = false;
|
AreaCommitmentList.IsEnabled = false;
|
||||||
|
|
||||||
HideAreaCommitmentNewEditDeleteButtons();
|
HideNewEditDeleteButtons();
|
||||||
ShowAreaCommitmentSaveResetCancelButtons();
|
ShowSaveResetCancelButtons();
|
||||||
UnlockInputs();
|
UnlockInputs();
|
||||||
LockSearchInputs();
|
LockSearchInputs();
|
||||||
}
|
}
|
||||||
@@ -199,40 +200,81 @@ namespace Elwig.Windows {
|
|||||||
private async void DeleteAreaCommitmentButton_Click(object? sender, RoutedEventArgs? evt) {
|
private async void DeleteAreaCommitmentButton_Click(object? sender, RoutedEventArgs? evt) {
|
||||||
if (AreaCommitmentList.SelectedItem is not AreaCom a)
|
if (AreaCommitmentList.SelectedItem is not AreaCom a)
|
||||||
return;
|
return;
|
||||||
var r = MessageBox.Show(
|
|
||||||
$"Soll die Flächenbindung {a.GstNr} ({a.Area} m²) wirklich unwiderruflich gelöscht werden?",
|
var d = new AreaComModifyDialog(a.YearFrom, a.YearTo, a.Area, true);
|
||||||
"Flächenbindung löschen", MessageBoxButton.OKCancel, MessageBoxImage.Warning, MessageBoxResult.Cancel);
|
if (d.ShowDialog() != true)
|
||||||
if (r == MessageBoxResult.OK) {
|
return;
|
||||||
Mouse.OverrideCursor = Cursors.Wait;
|
|
||||||
try {
|
Mouse.OverrideCursor = Cursors.Wait;
|
||||||
|
try {
|
||||||
|
if (d.YearTo is int yearTo) {
|
||||||
|
ViewModel.YearTo = yearTo;
|
||||||
|
await ViewModel.UpdateAreaCommitment((AreaCommitmentList.SelectedItem as AreaCom)?.FbNr);
|
||||||
|
} else {
|
||||||
await AreaComService.DeleteAreaCom(a.FbNr);
|
await AreaComService.DeleteAreaCom(a.FbNr);
|
||||||
} 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, "Flächenbindung löschen", MessageBoxButton.OK, MessageBoxImage.Error);
|
|
||||||
}
|
}
|
||||||
Mouse.OverrideCursor = null;
|
App.HintContextChange();
|
||||||
|
} 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, "Flächenbindung löschen", MessageBoxButton.OK, MessageBoxImage.Error);
|
||||||
}
|
}
|
||||||
|
Mouse.OverrideCursor = null;
|
||||||
}
|
}
|
||||||
|
|
||||||
protected override void ShortcutSave() {
|
protected override void ShortcutSave() {
|
||||||
if (!AreaCommitmentSaveButton.IsEnabled || AreaCommitmentSaveButton.Visibility != Visibility.Visible)
|
if (!SaveButton.IsEnabled || SaveButton.Visibility != Visibility.Visible)
|
||||||
return;
|
return;
|
||||||
AreaCommitmentSaveButton_Click(null, null);
|
SaveButton_Click(null, null);
|
||||||
}
|
}
|
||||||
|
|
||||||
private async void AreaCommitmentSaveButton_Click(object? sender, RoutedEventArgs? evt) {
|
private async void SaveButton_Click(object? sender, RoutedEventArgs? evt) {
|
||||||
AreaCommitmentSaveButton.IsEnabled = false;
|
SaveButton.IsEnabled = false;
|
||||||
Mouse.OverrideCursor = Cursors.Wait;
|
|
||||||
|
int? yearTo = null;
|
||||||
|
if (InputHasChanged(AreaInput) || InputHasChanged(AreaComTypeInput)) {
|
||||||
|
var a = (AreaCommitmentList.SelectedItem as AreaCom)!;
|
||||||
|
var d = new AreaComModifyDialog(a.YearFrom, a.YearTo, a.Area, false);
|
||||||
|
if (d.ShowDialog() != true)
|
||||||
|
return;
|
||||||
|
yearTo = d.YearTo;
|
||||||
|
}
|
||||||
|
|
||||||
int fbnr;
|
int fbnr;
|
||||||
|
Mouse.OverrideCursor = Cursors.Wait;
|
||||||
try {
|
try {
|
||||||
|
AreaCom? temp = null;
|
||||||
|
if (yearTo != null && (!ViewModel.YearTo.HasValue || yearTo < ViewModel.YearTo)) {
|
||||||
|
temp = new AreaCom {
|
||||||
|
FbNr = ViewModel.FbNr!.Value,
|
||||||
|
MgNr = ViewModel.MgNr!.Value,
|
||||||
|
YearFrom = ViewModel.YearFrom,
|
||||||
|
YearTo = ViewModel.YearTo,
|
||||||
|
VtrgId = ViewModel.AreaComType!.VtrgId,
|
||||||
|
CultId = ViewModel.WineCult?.CultId,
|
||||||
|
Comment = ViewModel.Comment,
|
||||||
|
KgNr = ViewModel.Kg!.KgNr,
|
||||||
|
RdNr = ViewModel.Rd?.RdNr,
|
||||||
|
GstNr = ViewModel.GstNr?.Trim() ?? "-",
|
||||||
|
Area = ViewModel.Area!.Value,
|
||||||
|
};
|
||||||
|
RefreshInputs();
|
||||||
|
ViewModel.YearTo = yearTo;
|
||||||
|
}
|
||||||
fbnr = await ViewModel.UpdateAreaCommitment((AreaCommitmentList.SelectedItem as AreaCom)?.FbNr);
|
fbnr = await ViewModel.UpdateAreaCommitment((AreaCommitmentList.SelectedItem as AreaCom)?.FbNr);
|
||||||
|
if (temp is AreaCom t) {
|
||||||
|
await ViewModel.InitInputs();
|
||||||
|
t.FbNr = ViewModel.FbNr!.Value;
|
||||||
|
t.YearFrom = yearTo + 1;
|
||||||
|
ViewModel.FillInputs(t);
|
||||||
|
fbnr = await ViewModel.UpdateAreaCommitment(null);
|
||||||
|
}
|
||||||
|
App.HintContextChange();
|
||||||
} catch (Exception exc) {
|
} catch (Exception exc) {
|
||||||
var str = "Der Eintrag konnte nicht in der Datenbank aktualisiert werden!\n\n" + exc.Message;
|
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;
|
if (exc.InnerException != null) str += "\n\n" + exc.InnerException.Message;
|
||||||
MessageBox.Show(str, "Flächenbindung aktualisieren", MessageBoxButton.OK, MessageBoxImage.Error);
|
MessageBox.Show(str, "Flächenbindung aktualisieren", MessageBoxButton.OK, MessageBoxImage.Error);
|
||||||
AreaCommitmentSaveButton.IsEnabled = true;
|
SaveButton.IsEnabled = true;
|
||||||
Mouse.OverrideCursor = null;
|
Mouse.OverrideCursor = null;
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
@@ -240,8 +282,8 @@ namespace Elwig.Windows {
|
|||||||
IsEditing = false;
|
IsEditing = false;
|
||||||
IsCreating = false;
|
IsCreating = false;
|
||||||
AreaCommitmentList.IsEnabled = true;
|
AreaCommitmentList.IsEnabled = true;
|
||||||
HideAreaCommitmentSaveResetCancelButtons();
|
HideSaveResetCancelButtons();
|
||||||
ShowAreaCommitmentNewEditDeleteButtons();
|
ShowNewEditDeleteButtons();
|
||||||
LockInputs();
|
LockInputs();
|
||||||
UnlockSearchInputs();
|
UnlockSearchInputs();
|
||||||
FinishInputFilling();
|
FinishInputFilling();
|
||||||
@@ -253,12 +295,12 @@ namespace Elwig.Windows {
|
|||||||
}
|
}
|
||||||
|
|
||||||
protected override void ShortcutReset() {
|
protected override void ShortcutReset() {
|
||||||
if (!AreaCommitmentResetButton.IsEnabled || AreaCommitmentResetButton.Visibility != Visibility.Visible)
|
if (!ResetButton.IsEnabled || ResetButton.Visibility != Visibility.Visible)
|
||||||
return;
|
return;
|
||||||
AreaCommitmentResetButton_Click(null, null);
|
ResetButton_Click(null, null);
|
||||||
}
|
}
|
||||||
|
|
||||||
private async void AreaCommitmentResetButton_Click(object? sender, RoutedEventArgs? evt) {
|
private async void ResetButton_Click(object? sender, RoutedEventArgs? evt) {
|
||||||
if (IsEditing) {
|
if (IsEditing) {
|
||||||
RefreshInputs();
|
RefreshInputs();
|
||||||
} else if (IsCreating) {
|
} else if (IsCreating) {
|
||||||
@@ -267,12 +309,12 @@ namespace Elwig.Windows {
|
|||||||
UpdateButtons();
|
UpdateButtons();
|
||||||
}
|
}
|
||||||
|
|
||||||
private void AreaCommitmentCancelButton_Click(object sender, RoutedEventArgs evt) {
|
private void CancelButton_Click(object sender, RoutedEventArgs evt) {
|
||||||
IsEditing = false;
|
IsEditing = false;
|
||||||
IsCreating = false;
|
IsCreating = false;
|
||||||
AreaCommitmentList.IsEnabled = true;
|
AreaCommitmentList.IsEnabled = true;
|
||||||
HideAreaCommitmentSaveResetCancelButtons();
|
HideSaveResetCancelButtons();
|
||||||
ShowAreaCommitmentNewEditDeleteButtons();
|
ShowNewEditDeleteButtons();
|
||||||
RefreshInputs();
|
RefreshInputs();
|
||||||
ClearInputStates();
|
ClearInputStates();
|
||||||
LockInputs();
|
LockInputs();
|
||||||
@@ -282,49 +324,49 @@ namespace Elwig.Windows {
|
|||||||
override protected void UpdateButtons() {
|
override protected void UpdateButtons() {
|
||||||
if (!IsEditing && !IsCreating) return;
|
if (!IsEditing && !IsCreating) return;
|
||||||
bool ch = HasChanged, v = IsValid;
|
bool ch = HasChanged, v = IsValid;
|
||||||
AreaCommitmentResetButton.IsEnabled = (ch);
|
ResetButton.IsEnabled = (ch);
|
||||||
AreaCommitmentSaveButton.IsEnabled = (ch && v);
|
SaveButton.IsEnabled = (ch && v);
|
||||||
}
|
}
|
||||||
|
|
||||||
private void DisableAreaCommitmentNewEditDeleteButtons() {
|
private void DisableNewEditDeleteButtons() {
|
||||||
NewAreaCommitmentButton.IsEnabled = false;
|
NewAreaCommitmentButton.IsEnabled = false;
|
||||||
EditAreaCommitmentButton.IsEnabled = false;
|
EditAreaCommitmentButton.IsEnabled = false;
|
||||||
DeleteAreaCommitmentButton.IsEnabled = false;
|
DeleteAreaCommitmentButton.IsEnabled = false;
|
||||||
}
|
}
|
||||||
|
|
||||||
private void EnableAreaCommitmentNewEditDeleteButtons() {
|
private void EnableNewEditDeleteButtons() {
|
||||||
NewAreaCommitmentButton.IsEnabled = true;
|
NewAreaCommitmentButton.IsEnabled = true;
|
||||||
EditAreaCommitmentButton.IsEnabled = AreaCommitmentList.SelectedItem != null;
|
EditAreaCommitmentButton.IsEnabled = AreaCommitmentList.SelectedItem != null;
|
||||||
DeleteAreaCommitmentButton.IsEnabled = AreaCommitmentList.SelectedItem != null;
|
DeleteAreaCommitmentButton.IsEnabled = AreaCommitmentList.SelectedItem != null;
|
||||||
}
|
}
|
||||||
|
|
||||||
private void ShowAreaCommitmentSaveResetCancelButtons() {
|
private void ShowSaveResetCancelButtons() {
|
||||||
AreaCommitmentSaveButton.IsEnabled = false;
|
SaveButton.IsEnabled = false;
|
||||||
AreaCommitmentResetButton.IsEnabled = false;
|
ResetButton.IsEnabled = false;
|
||||||
AreaCommitmentCancelButton.IsEnabled = true;
|
CancelButton.IsEnabled = true;
|
||||||
AreaCommitmentSaveButton.Visibility = Visibility.Visible;
|
SaveButton.Visibility = Visibility.Visible;
|
||||||
AreaCommitmentResetButton.Visibility = Visibility.Visible;
|
ResetButton.Visibility = Visibility.Visible;
|
||||||
AreaCommitmentCancelButton.Visibility = Visibility.Visible;
|
CancelButton.Visibility = Visibility.Visible;
|
||||||
}
|
}
|
||||||
|
|
||||||
private void HideAreaCommitmentSaveResetCancelButtons() {
|
private void HideSaveResetCancelButtons() {
|
||||||
AreaCommitmentSaveButton.IsEnabled = false;
|
SaveButton.IsEnabled = false;
|
||||||
AreaCommitmentResetButton.IsEnabled = false;
|
ResetButton.IsEnabled = false;
|
||||||
AreaCommitmentCancelButton.IsEnabled = false;
|
CancelButton.IsEnabled = false;
|
||||||
AreaCommitmentSaveButton.Visibility = Visibility.Hidden;
|
SaveButton.Visibility = Visibility.Hidden;
|
||||||
AreaCommitmentResetButton.Visibility = Visibility.Hidden;
|
ResetButton.Visibility = Visibility.Hidden;
|
||||||
AreaCommitmentCancelButton.Visibility = Visibility.Hidden;
|
CancelButton.Visibility = Visibility.Hidden;
|
||||||
}
|
}
|
||||||
|
|
||||||
private void ShowAreaCommitmentNewEditDeleteButtons() {
|
private void ShowNewEditDeleteButtons() {
|
||||||
EnableAreaCommitmentNewEditDeleteButtons();
|
EnableNewEditDeleteButtons();
|
||||||
NewAreaCommitmentButton.Visibility = Visibility.Visible;
|
NewAreaCommitmentButton.Visibility = Visibility.Visible;
|
||||||
EditAreaCommitmentButton.Visibility = Visibility.Visible;
|
EditAreaCommitmentButton.Visibility = Visibility.Visible;
|
||||||
DeleteAreaCommitmentButton.Visibility = Visibility.Visible;
|
DeleteAreaCommitmentButton.Visibility = Visibility.Visible;
|
||||||
}
|
}
|
||||||
|
|
||||||
private void HideAreaCommitmentNewEditDeleteButtons() {
|
private void HideNewEditDeleteButtons() {
|
||||||
DisableAreaCommitmentNewEditDeleteButtons();
|
DisableNewEditDeleteButtons();
|
||||||
NewAreaCommitmentButton.Visibility = Visibility.Hidden;
|
NewAreaCommitmentButton.Visibility = Visibility.Hidden;
|
||||||
EditAreaCommitmentButton.Visibility = Visibility.Hidden;
|
EditAreaCommitmentButton.Visibility = Visibility.Hidden;
|
||||||
DeleteAreaCommitmentButton.Visibility = Visibility.Hidden;
|
DeleteAreaCommitmentButton.Visibility = Visibility.Hidden;
|
||||||
@@ -341,6 +383,8 @@ namespace Elwig.Windows {
|
|||||||
}
|
}
|
||||||
|
|
||||||
private void AreaCommitmentList_SelectionChanged(object sender, SelectionChangedEventArgs evt) {
|
private void AreaCommitmentList_SelectionChanged(object sender, SelectionChangedEventArgs evt) {
|
||||||
|
if (AreaCommitmentList.SelectedItem != null)
|
||||||
|
AreaCommitmentList.ScrollIntoView(AreaCommitmentList.SelectedItem);
|
||||||
RefreshInputs();
|
RefreshInputs();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@@ -122,6 +122,12 @@
|
|||||||
VerticalAlignment="Top" HorizontalAlignment="Left" Grid.Column="3" Margin="0,130,10,10" Width="64"
|
VerticalAlignment="Top" HorizontalAlignment="Left" Grid.Column="3" Margin="0,130,10,10" Width="64"
|
||||||
TextChanged="LfbisNrInput_TextChanged" LostFocus="LfbisNrInput_LostFocus"/>
|
TextChanged="LfbisNrInput_TextChanged" LostFocus="LfbisNrInput_LostFocus"/>
|
||||||
|
|
||||||
|
<Label Content="Bio-Kontrollstelle:"
|
||||||
|
VerticalAlignment="Top" HorizontalAlignment="Right" Grid.Column="3" Margin="10,130,110,10"/>
|
||||||
|
<TextBox x:Name="ClientOrganicAuthorityInput"
|
||||||
|
VerticalAlignment="Top" HorizontalAlignment="Right" Grid.Column="3" Margin="10,130,10,10" Width="90"
|
||||||
|
TextChanged="OrganicAuthorityCodeInput_TextChanged" LostFocus="OrganicAuthorityCodeInput_LostFocus"/>
|
||||||
|
|
||||||
<Label Content="Telefon-Nr.:"
|
<Label Content="Telefon-Nr.:"
|
||||||
VerticalAlignment="Top" HorizontalAlignment="Left" Grid.Column="2" Margin="10,160,0,10"/>
|
VerticalAlignment="Top" HorizontalAlignment="Left" Grid.Column="2" Margin="10,160,0,10"/>
|
||||||
<TextBox x:Name="ClientPhoneNrInput" Margin="0,160,10,10" Grid.Column="3"
|
<TextBox x:Name="ClientPhoneNrInput" Margin="0,160,10,10" Grid.Column="3"
|
||||||
@@ -330,7 +336,7 @@
|
|||||||
<ListBox.ItemTemplate>
|
<ListBox.ItemTemplate>
|
||||||
<DataTemplate>
|
<DataTemplate>
|
||||||
<StackPanel Orientation="Horizontal">
|
<StackPanel Orientation="Horizontal">
|
||||||
<TextBlock Text="{Binding SortId}" Width="30"/>
|
<TextBlock Text="{Binding SortId}" Width="30" Foreground="{Binding WineVar.Color}"/>
|
||||||
<TextBlock Text="{Binding WineAttr.Name}" Width="70"/>
|
<TextBlock Text="{Binding WineAttr.Name}" Width="70"/>
|
||||||
<TextBlock Text="{Binding Discriminator}"/>
|
<TextBlock Text="{Binding Discriminator}"/>
|
||||||
</StackPanel>
|
</StackPanel>
|
||||||
|
@@ -366,6 +366,7 @@ namespace Elwig.Windows {
|
|||||||
ClientBicInput.Text = p.Bic;
|
ClientBicInput.Text = p.Bic;
|
||||||
ClientUstIdNrInput.Text = p.UstIdNr;
|
ClientUstIdNrInput.Text = p.UstIdNr;
|
||||||
ClientLfbisNrInput.Text = p.LfbisNr;
|
ClientLfbisNrInput.Text = p.LfbisNr;
|
||||||
|
ClientOrganicAuthorityInput.Text = p.OrganicAuthority;
|
||||||
ClientPhoneNrInput.Text = p.PhoneNr;
|
ClientPhoneNrInput.Text = p.PhoneNr;
|
||||||
ClientFaxNrInput.Text = p.FaxNr;
|
ClientFaxNrInput.Text = p.FaxNr;
|
||||||
ClientEmailAddressInput.Text = p.EmailAddress;
|
ClientEmailAddressInput.Text = p.EmailAddress;
|
||||||
@@ -392,26 +393,27 @@ namespace Elwig.Windows {
|
|||||||
|
|
||||||
private async Task UpdateClientParameters(ClientParameters p) {
|
private async Task UpdateClientParameters(ClientParameters p) {
|
||||||
p.Name = ClientNameInput.Text;
|
p.Name = ClientNameInput.Text;
|
||||||
p.NameSuffix = ClientNameSuffixInput.Text.Length > 0 ? ClientNameSuffixInput.Text : null;
|
p.NameSuffix = string.IsNullOrEmpty(ClientNameSuffixInput.Text) ? null : ClientNameSuffixInput.Text;
|
||||||
p.NameType = ClientNameTypeInput.Text;
|
p.NameType = ClientNameTypeInput.Text;
|
||||||
p.NameToken = ClientNameTokenInput.Text;
|
p.NameToken = ClientNameTokenInput.Text;
|
||||||
p.NameShort = ClientNameShortInput.Text;
|
p.NameShort = ClientNameShortInput.Text;
|
||||||
p.Address = ClientAddressInput.Text;
|
p.Address = ClientAddressInput.Text;
|
||||||
p.Plz = int.Parse(ClientPlzInput.Text);
|
p.Plz = int.Parse(ClientPlzInput.Text);
|
||||||
p.Ort = ClientOrtInput.Text;
|
p.Ort = ClientOrtInput.Text;
|
||||||
p.Iban = ClientIbanInput.Text.Length > 0 ? ClientIbanInput.Text : null;
|
p.Iban = string.IsNullOrEmpty(ClientIbanInput.Text) ? null : ClientIbanInput.Text;
|
||||||
p.Bic = ClientBicInput.Text.Length > 0 ? ClientBicInput.Text : null;
|
p.Bic = string.IsNullOrEmpty(ClientBicInput.Text) ? null : ClientBicInput.Text;
|
||||||
p.UstIdNr = ClientUstIdNrInput.Text.Length > 0 ? ClientUstIdNrInput.Text : null;
|
p.UstIdNr = string.IsNullOrEmpty(ClientUstIdNrInput.Text) ? null : ClientUstIdNrInput.Text;
|
||||||
p.LfbisNr = ClientLfbisNrInput.Text.Length > 0 ? ClientLfbisNrInput.Text : null;
|
p.LfbisNr = string.IsNullOrEmpty(ClientLfbisNrInput.Text) ? null : ClientLfbisNrInput.Text;
|
||||||
p.PhoneNr = ClientPhoneNrInput.Text.Length > 0 ? ClientPhoneNrInput.Text : null;
|
p.OrganicAuthority = string.IsNullOrEmpty(ClientOrganicAuthorityInput.Text) ? null : ClientOrganicAuthorityInput.Text;
|
||||||
p.FaxNr = ClientFaxNrInput.Text.Length > 0 ? ClientFaxNrInput.Text : null;
|
p.PhoneNr = string.IsNullOrEmpty(ClientPhoneNrInput.Text) ? null : ClientPhoneNrInput.Text;
|
||||||
p.EmailAddress = ClientEmailAddressInput.Text.Length > 0 ? ClientEmailAddressInput.Text : null;
|
p.FaxNr = string.IsNullOrEmpty(ClientFaxNrInput.Text) ? null : ClientFaxNrInput.Text;
|
||||||
p.Website = ClientWebsiteInput.Text.Length > 0 ? ClientWebsiteInput.Text : null;
|
p.EmailAddress = string.IsNullOrEmpty(ClientEmailAddressInput.Text) ? null : ClientEmailAddressInput.Text;
|
||||||
|
p.Website = string.IsNullOrEmpty(ClientWebsiteInput.Text) ? null : ClientWebsiteInput.Text;
|
||||||
|
|
||||||
p.TextDeliveryNote = TextElementDeliveryNote.Text.Length > 0 ? TextElementDeliveryNote.Text : null;
|
p.TextDeliveryNote = string.IsNullOrEmpty(TextElementDeliveryNote.Text) ? null : TextElementDeliveryNote.Text;
|
||||||
p.ModeDeliveryNoteStats = (ModeDeliveryNoteNone.IsChecked == true) ? 0 : (ModeDeliveryNoteGaOnly.IsChecked == true) ? 1 : (ModeDeliveryNoteShort.IsChecked == true) ? 2 : (ModeDeliveryNoteFull.IsChecked == true) ? 3 : 2;
|
p.ModeDeliveryNoteStats = (ModeDeliveryNoteNone.IsChecked == true) ? 0 : (ModeDeliveryNoteGaOnly.IsChecked == true) ? 1 : (ModeDeliveryNoteShort.IsChecked == true) ? 2 : (ModeDeliveryNoteFull.IsChecked == true) ? 3 : 2;
|
||||||
p.TextDeliveryConfirmation = TextElementDeliveryConfirmation.Text.Length > 0 ? TextElementDeliveryConfirmation.Text : null;
|
p.TextDeliveryConfirmation = string.IsNullOrEmpty(TextElementDeliveryConfirmation.Text) ? null : TextElementDeliveryConfirmation.Text;
|
||||||
p.TextCreditNote = TextElementCreditNote.Text.Length > 0 ? TextElementCreditNote.Text : null;
|
p.TextCreditNote = string.IsNullOrEmpty(TextElementCreditNote.Text) ? null : TextElementCreditNote.Text;
|
||||||
|
|
||||||
p.ExportEbicsVersion = ParameterExportEbicsVersion.SelectedIndex + 3;
|
p.ExportEbicsVersion = ParameterExportEbicsVersion.SelectedIndex + 3;
|
||||||
p.ExportEbicsAddress = ParameterExportEbicsAddress.SelectedIndex;
|
p.ExportEbicsAddress = ParameterExportEbicsAddress.SelectedIndex;
|
||||||
|
@@ -75,8 +75,8 @@
|
|||||||
<ctrl:CheckComboBox.ItemTemplate>
|
<ctrl:CheckComboBox.ItemTemplate>
|
||||||
<DataTemplate>
|
<DataTemplate>
|
||||||
<StackPanel Orientation="Horizontal">
|
<StackPanel Orientation="Horizontal">
|
||||||
<TextBlock Text="{Binding Variety.Name}" Width="150"/>
|
<TextBlock Text="{Binding Variety.Name}" Foreground="{Binding Variety.Color}" Width="150"/>
|
||||||
<TextBlock Text="{Binding Variety.Type}" Width="30"/>
|
<TextBlock Text="{Binding Variety.Type}" Foreground="{Binding Variety.Color}" Width="30"/>
|
||||||
<TextBlock Text="{Binding Attribute.Name}" Width="80"/>
|
<TextBlock Text="{Binding Attribute.Name}" Width="80"/>
|
||||||
<TextBlock Text="{Binding Cultivation.Name}" Width="80"/>
|
<TextBlock Text="{Binding Cultivation.Name}" Width="80"/>
|
||||||
<TextBlock Text="{Binding AssignedGraphId}" Width="30"/>
|
<TextBlock Text="{Binding AssignedGraphId}" Width="30"/>
|
||||||
@@ -94,8 +94,8 @@
|
|||||||
<ListBox.ItemTemplate>
|
<ListBox.ItemTemplate>
|
||||||
<DataTemplate>
|
<DataTemplate>
|
||||||
<StackPanel Orientation="Horizontal">
|
<StackPanel Orientation="Horizontal">
|
||||||
<TextBlock Text="{Binding Id}" Width="30"/>
|
<TextBlock Text="{Binding Id}" Foreground="{Binding Color}" Width="30"/>
|
||||||
<TextBlock Text="{Binding VaributeStringSimple}" ToolTip="{Binding VaributeString}"/>
|
<TextBlock Text="{Binding VaributeStringSimple}" Foreground="{Binding Color}" ToolTip="{Binding VaributeString}"/>
|
||||||
</StackPanel>
|
</StackPanel>
|
||||||
</DataTemplate>
|
</DataTemplate>
|
||||||
</ListBox.ItemTemplate>
|
</ListBox.ItemTemplate>
|
||||||
|
@@ -639,10 +639,11 @@ namespace Elwig.Windows {
|
|||||||
|
|
||||||
private async void SaveButton_Click(object sender, RoutedEventArgs e) {
|
private async void SaveButton_Click(object sender, RoutedEventArgs e) {
|
||||||
SaveButton.IsEnabled = false;
|
SaveButton.IsEnabled = false;
|
||||||
Mouse.OverrideCursor = Cursors.AppStarting;
|
Mouse.OverrideCursor = Cursors.Wait;
|
||||||
|
|
||||||
try {
|
try {
|
||||||
using (var ctx = new AppDbContext()) {
|
await Task.Run(async () => {
|
||||||
|
using var ctx = new AppDbContext();
|
||||||
var origData = BillingData.FromJson(PaymentVar.Data);
|
var origData = BillingData.FromJson(PaymentVar.Data);
|
||||||
var data = BillingData.FromGraphEntries(GraphEntries, origData, Utils.GetVaributes(ctx, Year),
|
var data = BillingData.FromGraphEntries(GraphEntries, origData, Utils.GetVaributes(ctx, Year),
|
||||||
AllVaributesAssigned, AllVaributesAssignedAbgew);
|
AllVaributesAssigned, AllVaributesAssignedAbgew);
|
||||||
@@ -650,27 +651,31 @@ namespace Elwig.Windows {
|
|||||||
PaymentVar.Data = data.ToJsonString();
|
PaymentVar.Data = data.ToJsonString();
|
||||||
ctx.Update(PaymentVar);
|
ctx.Update(PaymentVar);
|
||||||
await ctx.SaveChangesAsync();
|
await ctx.SaveChangesAsync();
|
||||||
}
|
});
|
||||||
try {
|
|
||||||
var b = new BillingVariant(PaymentVar.Year, PaymentVar.AvNr);
|
|
||||||
await b.Calculate();
|
|
||||||
} catch (Exception exc) {
|
|
||||||
MessageBox.Show(exc.Message, "Berechnungsfehler", MessageBoxButton.OK, MessageBoxImage.Error);
|
|
||||||
}
|
|
||||||
LockContext = false;
|
|
||||||
App.HintContextChange();
|
|
||||||
} catch (Exception exc) {
|
} catch (Exception exc) {
|
||||||
|
Mouse.OverrideCursor = null;
|
||||||
var str = "Der Eintrag konnte nicht in der Datenbank gespeichert werden!\n\n" + exc.Message;
|
var str = "Der Eintrag konnte nicht in der Datenbank gespeichert werden!\n\n" + exc.Message;
|
||||||
if (exc.InnerException != null) str += "\n\n" + exc.InnerException.Message;
|
if (exc.InnerException != null) str += "\n\n" + exc.InnerException.Message;
|
||||||
MessageBox.Show(str, "Auszahlungsvariante speichern", MessageBoxButton.OK, MessageBoxImage.Error);
|
MessageBox.Show(str, "Auszahlungsvariante speichern", MessageBoxButton.OK, MessageBoxImage.Error);
|
||||||
SaveButton.IsEnabled = true;
|
SaveButton.IsEnabled = true;
|
||||||
return;
|
return;
|
||||||
} finally {
|
|
||||||
Mouse.OverrideCursor = null;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
try {
|
||||||
|
await Task.Run(async () => {
|
||||||
|
var b = new BillingVariant(PaymentVar.Year, PaymentVar.AvNr);
|
||||||
|
await b.Calculate();
|
||||||
|
});
|
||||||
|
} catch (Exception exc) {
|
||||||
|
MessageBox.Show(exc.Message, "Berechnungsfehler", MessageBoxButton.OK, MessageBoxImage.Error);
|
||||||
|
}
|
||||||
|
|
||||||
|
LockContext = false;
|
||||||
|
App.HintContextChange();
|
||||||
LockContext = true;
|
LockContext = true;
|
||||||
SetHasChanged(false);
|
SetHasChanged(false);
|
||||||
|
|
||||||
|
Mouse.OverrideCursor = null;
|
||||||
}
|
}
|
||||||
|
|
||||||
private void EnableTextBox(TextBox u) {
|
private void EnableTextBox(TextBox u) {
|
||||||
|
@@ -268,6 +268,7 @@
|
|||||||
<DataGridTextColumn Header="Sorte" Binding="{Binding FilteredSortIdString}" Width="50">
|
<DataGridTextColumn Header="Sorte" Binding="{Binding FilteredSortIdString}" Width="50">
|
||||||
<DataGridTextColumn.CellStyle>
|
<DataGridTextColumn.CellStyle>
|
||||||
<Style>
|
<Style>
|
||||||
|
<Setter Property="TextBlock.Foreground" Value="{Binding FilteredColor}"/>
|
||||||
<Setter Property="TextBlock.TextAlignment" Value="Center"/>
|
<Setter Property="TextBlock.TextAlignment" Value="Center"/>
|
||||||
</Style>
|
</Style>
|
||||||
</DataGridTextColumn.CellStyle>
|
</DataGridTextColumn.CellStyle>
|
||||||
@@ -438,7 +439,7 @@
|
|||||||
<DataTemplate>
|
<DataTemplate>
|
||||||
<StackPanel Orientation="Horizontal">
|
<StackPanel Orientation="Horizontal">
|
||||||
<TextBlock Text="{Binding DPNr}" Width="13" TextAlignment="Right" Margin="0,0,7,0"/>
|
<TextBlock Text="{Binding DPNr}" Width="13" TextAlignment="Right" Margin="0,0,7,0"/>
|
||||||
<TextBlock Text="{Binding SortId}" Width="30"/>
|
<TextBlock Text="{Binding SortId}" Foreground="{Binding Variety.Color}" TextAlignment="Center" Width="30"/>
|
||||||
<TextBlock Text="{Binding Kmw, StringFormat='{}{0:N1}°'}" Width="40" TextAlignment="Right" Padding="0,0,10,0"/>
|
<TextBlock Text="{Binding Kmw, StringFormat='{}{0:N1}°'}" Width="40" TextAlignment="Right" Padding="0,0,10,0"/>
|
||||||
<TextBlock Text="{Binding QualId}" Width="30"/>
|
<TextBlock Text="{Binding QualId}" Width="30"/>
|
||||||
<TextBlock Text="{Binding Weight, StringFormat='{}{0:N0} kg'}" Width="60" TextAlignment="Right" Padding="0,0,10,0"/>
|
<TextBlock Text="{Binding Weight, StringFormat='{}{0:N0} kg'}" Width="60" TextAlignment="Right" Padding="0,0,10,0"/>
|
||||||
@@ -460,7 +461,7 @@
|
|||||||
</Grid.ColumnDefinitions>
|
</Grid.ColumnDefinitions>
|
||||||
|
|
||||||
<Label Content="Sorte:" Margin="10,10,0,0" Grid.Column="0"/>
|
<Label Content="Sorte:" Margin="10,10,0,0" Grid.Column="0"/>
|
||||||
<TextBox x:Name="SortIdInput" Text="{Binding SortId, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"
|
<TextBox x:Name="SortIdInput" Text="{Binding SortId, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}" Foreground="{Binding WineVar.Color}"
|
||||||
Width="36" Grid.Row="1" Grid.Column="1" Margin="0,10,0,0" HorizontalAlignment="Left"
|
Width="36" Grid.Row="1" Grid.Column="1" Margin="0,10,0,0" HorizontalAlignment="Left"
|
||||||
TextChanged="SortIdInput_TextChanged" LostFocus="SortIdInput_LostFocus" KeyUp="Input_KeyUp"/>
|
TextChanged="SortIdInput_TextChanged" LostFocus="SortIdInput_LostFocus" KeyUp="Input_KeyUp"/>
|
||||||
<ComboBox x:Name="WineVarietyInput" SelectedItem="{Binding WineVar, Mode=TwoWay}" ItemsSource="{Binding WineVarSource, Mode=TwoWay}"
|
<ComboBox x:Name="WineVarietyInput" SelectedItem="{Binding WineVar, Mode=TwoWay}" ItemsSource="{Binding WineVarSource, Mode=TwoWay}"
|
||||||
|
@@ -732,6 +732,7 @@ namespace Elwig.Windows {
|
|||||||
InputHasChanged(TimeInput),
|
InputHasChanged(TimeInput),
|
||||||
!InputIsNotDefault(TimeInput)
|
!InputIsNotDefault(TimeInput)
|
||||||
);
|
);
|
||||||
|
App.HintContextChange();
|
||||||
} catch (Exception exc) {
|
} catch (Exception exc) {
|
||||||
var str = "Der Eintrag konnte nicht in der Datenbank aktualisiert werden!\n\n" + exc.Message;
|
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;
|
if (exc.InnerException != null) str += "\n\n" + exc.InnerException.Message;
|
||||||
@@ -770,6 +771,7 @@ namespace Elwig.Windows {
|
|||||||
InputHasChanged(TimeInput),
|
InputHasChanged(TimeInput),
|
||||||
!InputIsNotDefault(TimeInput)
|
!InputIsNotDefault(TimeInput)
|
||||||
);
|
);
|
||||||
|
App.HintContextChange();
|
||||||
} catch (Exception exc) {
|
} catch (Exception exc) {
|
||||||
var str = "Der Eintrag konnte nicht in der Datenbank aktualisiert werden!\n\n" + exc.Message;
|
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;
|
if (exc.InnerException != null) str += "\n\n" + exc.InnerException.Message;
|
||||||
@@ -905,6 +907,7 @@ namespace Elwig.Windows {
|
|||||||
var n = await DeliveryService.SplitDeliveryToLsNr(d.Year, d.DId, weights, id);
|
var n = await DeliveryService.SplitDeliveryToLsNr(d.Year, d.DId, weights, id);
|
||||||
ControlUtils.SelectItemWithPk(DeliveryList, n.Year, n.DId);
|
ControlUtils.SelectItemWithPk(DeliveryList, n.Year, n.DId);
|
||||||
}
|
}
|
||||||
|
App.HintContextChange();
|
||||||
} catch (Exception exc) {
|
} catch (Exception exc) {
|
||||||
var str = "Der Eintrag konnte nicht in der Datenbank aktualisiert werden!\n\n" + exc.Message;
|
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;
|
if (exc.InnerException != null) str += "\n\n" + exc.InnerException.Message;
|
||||||
@@ -962,6 +965,7 @@ namespace Elwig.Windows {
|
|||||||
Mouse.OverrideCursor = Cursors.Wait;
|
Mouse.OverrideCursor = Cursors.Wait;
|
||||||
try {
|
try {
|
||||||
await DeliveryService.DeleteDelivery(d.LsNr);
|
await DeliveryService.DeleteDelivery(d.LsNr);
|
||||||
|
App.HintContextChange();
|
||||||
} catch (Exception exc) {
|
} catch (Exception exc) {
|
||||||
var str = "Der Eintrag konnte nicht in der Datenbank aktualisiert werden!\n\n" + exc.Message;
|
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;
|
if (exc.InnerException != null) str += "\n\n" + exc.InnerException.Message;
|
||||||
@@ -991,6 +995,7 @@ namespace Elwig.Windows {
|
|||||||
InputHasChanged(TimeInput),
|
InputHasChanged(TimeInput),
|
||||||
!InputIsNotDefault(TimeInput)
|
!InputIsNotDefault(TimeInput)
|
||||||
);
|
);
|
||||||
|
App.HintContextChange();
|
||||||
} catch (Exception exc) {
|
} catch (Exception exc) {
|
||||||
var str = "Der Eintrag konnte nicht in der Datenbank aktualisiert werden!\n\n" + exc.Message;
|
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;
|
if (exc.InnerException != null) str += "\n\n" + exc.InnerException.Message;
|
||||||
|
@@ -187,6 +187,7 @@
|
|||||||
<DataGridTextColumn Header="Sorte" Binding="{Binding SortId}" Width="50">
|
<DataGridTextColumn Header="Sorte" Binding="{Binding SortId}" Width="50">
|
||||||
<DataGridTextColumn.CellStyle>
|
<DataGridTextColumn.CellStyle>
|
||||||
<Style>
|
<Style>
|
||||||
|
<Setter Property="TextBlock.Foreground" Value="{Binding Variety.Color}"/>
|
||||||
<Setter Property="TextBlock.TextAlignment" Value="Center"/>
|
<Setter Property="TextBlock.TextAlignment" Value="Center"/>
|
||||||
</Style>
|
</Style>
|
||||||
</DataGridTextColumn.CellStyle>
|
</DataGridTextColumn.CellStyle>
|
||||||
@@ -198,7 +199,7 @@
|
|||||||
</Style>
|
</Style>
|
||||||
</DataGridTextColumn.CellStyle>
|
</DataGridTextColumn.CellStyle>
|
||||||
</DataGridTextColumn>
|
</DataGridTextColumn>
|
||||||
<DataGridTextColumn Header="Angemeldet" Binding="{Binding CreatedTimestamp, StringFormat='{}{0:HH:mm, dd.MM.}'}" Width="100">
|
<DataGridTextColumn Header="Angemeldet" Binding="{Binding CreatedAt, StringFormat='{}{0:HH:mm, dd.MM.}'}" Width="100">
|
||||||
<DataGridTextColumn.CellStyle>
|
<DataGridTextColumn.CellStyle>
|
||||||
<Style>
|
<Style>
|
||||||
<Setter Property="TextBlock.TextAlignment" Value="Center"/>
|
<Setter Property="TextBlock.TextAlignment" Value="Center"/>
|
||||||
@@ -316,7 +317,7 @@
|
|||||||
</ComboBox>
|
</ComboBox>
|
||||||
|
|
||||||
<Label Content="Sorte:" Margin="10,40,0,0" Grid.Column="0"/>
|
<Label Content="Sorte:" Margin="10,40,0,0" Grid.Column="0"/>
|
||||||
<TextBox x:Name="SortIdInput" Text="{Binding SortId, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"
|
<TextBox x:Name="SortIdInput" Text="{Binding SortId, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}" Foreground="{Binding WineVariety.Color}"
|
||||||
Width="36" Grid.Row="1" Grid.Column="1" Margin="0,40,0,0" HorizontalAlignment="Left"
|
Width="36" Grid.Row="1" Grid.Column="1" Margin="0,40,0,0" HorizontalAlignment="Left"
|
||||||
TextChanged="SortIdInput_TextChanged" LostFocus="SortIdInput_LostFocus" KeyUp="Input_KeyUp"/>
|
TextChanged="SortIdInput_TextChanged" LostFocus="SortIdInput_LostFocus" KeyUp="Input_KeyUp"/>
|
||||||
<ComboBox x:Name="WineVarietyInput" SelectedItem="{Binding WineVariety, Mode=TwoWay}" ItemsSource="{Binding WineVarietySource, Mode=TwoWay}"
|
<ComboBox x:Name="WineVarietyInput" SelectedItem="{Binding WineVariety, Mode=TwoWay}" ItemsSource="{Binding WineVarietySource, Mode=TwoWay}"
|
||||||
|
@@ -103,6 +103,7 @@ namespace Elwig.Windows {
|
|||||||
var deliveryAncmts = await deliveryAncmtQuery
|
var deliveryAncmts = await deliveryAncmtQuery
|
||||||
.Include(a => a.Member.BillingAddress)
|
.Include(a => a.Member.BillingAddress)
|
||||||
.Include(a => a.Schedule)
|
.Include(a => a.Schedule)
|
||||||
|
.Include(a => a.Variety)
|
||||||
.AsSplitQuery()
|
.AsSplitQuery()
|
||||||
.ToListAsync();
|
.ToListAsync();
|
||||||
|
|
||||||
@@ -317,12 +318,13 @@ namespace Elwig.Windows {
|
|||||||
$"Soll die Anmeldung wirklich unwiderruflich gelöscht werden?",
|
$"Soll die Anmeldung wirklich unwiderruflich gelöscht werden?",
|
||||||
"Anmeldung löschen", MessageBoxButton.OKCancel, MessageBoxImage.Warning, MessageBoxResult.Cancel);
|
"Anmeldung löschen", MessageBoxButton.OKCancel, MessageBoxImage.Warning, MessageBoxResult.Cancel);
|
||||||
if (r == MessageBoxResult.OK) {
|
if (r == MessageBoxResult.OK) {
|
||||||
Mouse.OverrideCursor = Cursors.AppStarting;
|
Mouse.OverrideCursor = Cursors.Wait;
|
||||||
try {
|
try {
|
||||||
using (var ctx = new AppDbContext()) {
|
await Task.Run(async () => {
|
||||||
|
using var ctx = new AppDbContext();
|
||||||
ctx.Remove(a);
|
ctx.Remove(a);
|
||||||
await ctx.SaveChangesAsync();
|
await ctx.SaveChangesAsync();
|
||||||
}
|
});
|
||||||
App.HintContextChange();
|
App.HintContextChange();
|
||||||
} catch (Exception exc) {
|
} catch (Exception exc) {
|
||||||
var str = "Der Eintrag konnte nicht in der Datenbank aktualisiert werden!\n\n" + exc.Message;
|
var str = "Der Eintrag konnte nicht in der Datenbank aktualisiert werden!\n\n" + exc.Message;
|
||||||
@@ -340,7 +342,7 @@ namespace Elwig.Windows {
|
|||||||
}
|
}
|
||||||
|
|
||||||
private async void SaveButton_Click(object? sender, RoutedEventArgs? evt) {
|
private async void SaveButton_Click(object? sender, RoutedEventArgs? evt) {
|
||||||
Mouse.OverrideCursor = Cursors.AppStarting;
|
Mouse.OverrideCursor = Cursors.Wait;
|
||||||
SaveButton.IsEnabled = false;
|
SaveButton.IsEnabled = false;
|
||||||
|
|
||||||
int year = -1, dsnr = -1, mgnr = -1;
|
int year = -1, dsnr = -1, mgnr = -1;
|
||||||
@@ -348,6 +350,7 @@ namespace Elwig.Windows {
|
|||||||
try {
|
try {
|
||||||
var s = ViewModel.SelectedDeliveryAncmt;
|
var s = ViewModel.SelectedDeliveryAncmt;
|
||||||
(year, dsnr, mgnr, sortid) = await ViewModel.UpdateDeliveryAncmt(s?.Year, s?.DsNr, s?.MgNr, s?.SortId, s?.Type);
|
(year, dsnr, mgnr, sortid) = await ViewModel.UpdateDeliveryAncmt(s?.Year, s?.DsNr, s?.MgNr, s?.SortId, s?.Type);
|
||||||
|
App.HintContextChange();
|
||||||
} catch (Exception exc) {
|
} catch (Exception exc) {
|
||||||
var str = "Der Eintrag konnte nicht in der Datenbank aktualisiert werden!\n\n" + exc.Message;
|
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;
|
if (exc.InnerException != null) str += "\n\n" + exc.InnerException.Message;
|
||||||
|
@@ -177,12 +177,13 @@ namespace Elwig.Windows {
|
|||||||
$"Soll der Leseplan \"{s.Description}\" vom {s.Date:dd.MM.yyyy} wirklich unwiderruflich gelöscht werden?",
|
$"Soll der Leseplan \"{s.Description}\" vom {s.Date:dd.MM.yyyy} wirklich unwiderruflich gelöscht werden?",
|
||||||
"Leseplan löschen", MessageBoxButton.OKCancel, MessageBoxImage.Warning, MessageBoxResult.Cancel);
|
"Leseplan löschen", MessageBoxButton.OKCancel, MessageBoxImage.Warning, MessageBoxResult.Cancel);
|
||||||
if (r == MessageBoxResult.OK) {
|
if (r == MessageBoxResult.OK) {
|
||||||
Mouse.OverrideCursor = Cursors.AppStarting;
|
Mouse.OverrideCursor = Cursors.Wait;
|
||||||
try {
|
try {
|
||||||
using (var ctx = new AppDbContext()) {
|
await Task.Run(async () => {
|
||||||
|
using var ctx = new AppDbContext();
|
||||||
ctx.Remove(s);
|
ctx.Remove(s);
|
||||||
await ctx.SaveChangesAsync();
|
await ctx.SaveChangesAsync();
|
||||||
}
|
});
|
||||||
App.HintContextChange();
|
App.HintContextChange();
|
||||||
} catch (Exception exc) {
|
} catch (Exception exc) {
|
||||||
var str = "Der Eintrag konnte nicht in der Datenbank aktualisiert werden!\n\n" + exc.Message;
|
var str = "Der Eintrag konnte nicht in der Datenbank aktualisiert werden!\n\n" + exc.Message;
|
||||||
@@ -200,11 +201,12 @@ namespace Elwig.Windows {
|
|||||||
}
|
}
|
||||||
|
|
||||||
private async void SaveButton_Click(object? sender, RoutedEventArgs? evt) {
|
private async void SaveButton_Click(object? sender, RoutedEventArgs? evt) {
|
||||||
Mouse.OverrideCursor = Cursors.AppStarting;
|
Mouse.OverrideCursor = Cursors.Wait;
|
||||||
SaveButton.IsEnabled = false;
|
SaveButton.IsEnabled = false;
|
||||||
|
|
||||||
try {
|
try {
|
||||||
await ViewModel.UpdateDeliverySchedule(ViewModel.SelectedDeliverySchedule?.Year, ViewModel.SelectedDeliverySchedule?.DsNr);
|
await ViewModel.UpdateDeliverySchedule(ViewModel.SelectedDeliverySchedule?.Year, ViewModel.SelectedDeliverySchedule?.DsNr);
|
||||||
|
App.HintContextChange();
|
||||||
} catch (Exception exc) {
|
} catch (Exception exc) {
|
||||||
var str = "Der Eintrag konnte nicht in der Datenbank aktualisiert werden!\n\n" + exc.Message;
|
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;
|
if (exc.InnerException != null) str += "\n\n" + exc.InnerException.Message;
|
||||||
|
@@ -602,7 +602,7 @@ namespace Elwig.Windows {
|
|||||||
PreviewButton.IsEnabled = false;
|
PreviewButton.IsEnabled = false;
|
||||||
PrintButton.IsEnabled = false;
|
PrintButton.IsEnabled = false;
|
||||||
EmailButton.IsEnabled = false;
|
EmailButton.IsEnabled = false;
|
||||||
Mouse.OverrideCursor = Cursors.AppStarting;
|
Mouse.OverrideCursor = Cursors.Wait;
|
||||||
GenerateButton.IsEnabled = false;
|
GenerateButton.IsEnabled = false;
|
||||||
|
|
||||||
DisposeDocs();
|
DisposeDocs();
|
||||||
@@ -828,25 +828,27 @@ namespace Elwig.Windows {
|
|||||||
EmailButton.IsEnabled = EmailDocuments != null && App.Config.Smtp != null;
|
EmailButton.IsEnabled = EmailDocuments != null && App.Config.Smtp != null;
|
||||||
}
|
}
|
||||||
|
|
||||||
private void PreviewButton_Click(object sender, RoutedEventArgs evt) {
|
private async void PreviewButton_Click(object sender, RoutedEventArgs evt) {
|
||||||
var d = new OpenFolderDialog() {
|
var d = new OpenFolderDialog() {
|
||||||
Title = "Ordner auswählen - Elwig",
|
Title = "Ordner auswählen - Elwig",
|
||||||
};
|
};
|
||||||
if (d.ShowDialog() == true) {
|
if (d.ShowDialog() == true) {
|
||||||
Mouse.OverrideCursor = Cursors.AppStarting;
|
Mouse.OverrideCursor = Cursors.Wait;
|
||||||
PrintDocument?.SaveTo($"{d.FolderName}/Print.pdf");
|
await Task.Run(() => {
|
||||||
if (EmailDocuments != null) {
|
PrintDocument?.SaveTo($"{d.FolderName}/Print.pdf");
|
||||||
foreach (var (m, docs) in EmailDocuments) {
|
if (EmailDocuments != null) {
|
||||||
var folder = $"{d.FolderName}/E-Mail/{m.AdministrativeName.Trim()}";
|
foreach (var (m, docs) in EmailDocuments) {
|
||||||
Directory.CreateDirectory(folder);
|
var folder = $"{d.FolderName}/E-Mail/{m.AdministrativeName.Trim()}";
|
||||||
foreach (var item in docs.Select((d, i) => new { Index = i, Doc = d })) {
|
Directory.CreateDirectory(folder);
|
||||||
var doc = item.Doc;
|
foreach (var item in docs.Select((d, i) => new { Index = i, Doc = d })) {
|
||||||
var name = Utils.NormalizeFileName(doc.Title);
|
var doc = item.Doc;
|
||||||
doc.SaveTo($"{folder}/{item.Index + 1:00}.{name}.pdf");
|
var name = Utils.NormalizeFileName(doc.Title);
|
||||||
}
|
doc.SaveTo($"{folder}/{item.Index + 1:00}.{name}.pdf");
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
});
|
||||||
Mouse.OverrideCursor = null;
|
Mouse.OverrideCursor = null;
|
||||||
Process.Start("explorer.exe", d.FolderName);
|
Process.Start("explorer.exe", d.FolderName);
|
||||||
}
|
}
|
||||||
@@ -862,20 +864,22 @@ namespace Elwig.Windows {
|
|||||||
var res = MessageBox.Show($"Sollen {PrintDocument.Pages} Blätter ({PrintDocument.TotalPages} Seiten) gedruckt werden?",
|
var res = MessageBox.Show($"Sollen {PrintDocument.Pages} Blätter ({PrintDocument.TotalPages} Seiten) gedruckt werden?",
|
||||||
"Rundschreiben drucken", MessageBoxButton.YesNo, MessageBoxImage.Question, MessageBoxResult.No);
|
"Rundschreiben drucken", MessageBoxButton.YesNo, MessageBoxImage.Question, MessageBoxResult.No);
|
||||||
if (res == MessageBoxResult.Yes) {
|
if (res == MessageBoxResult.Yes) {
|
||||||
Mouse.OverrideCursor = Cursors.AppStarting;
|
Mouse.OverrideCursor = Cursors.Wait;
|
||||||
if (App.Config.Debug) {
|
await Task.Run(async () => {
|
||||||
PrintDocument.Show();
|
if (App.Config.Debug) {
|
||||||
} else {
|
PrintDocument.Show();
|
||||||
await PrintDocument.Print();
|
} else {
|
||||||
await Utils.AddSentMails(
|
await PrintDocument.Print();
|
||||||
PrintMemberDocuments.Select(d => (
|
await Utils.AddSentMails(
|
||||||
"postal", d.Key.MgNr, d.Key.AdministrativeName,
|
PrintMemberDocuments.Select(d => (
|
||||||
new string[] { d.Value.Select(d => (d as BusinessDocument)?.Address).FirstOrDefault(a => a != null) ?? d.Key.FullAddress },
|
"postal", d.Key.MgNr, d.Key.AdministrativeName,
|
||||||
d.Value.Select(d => d.Title).FirstOrDefault("Briefkopf"),
|
new string[] { d.Value.Select(d => (d as BusinessDocument)?.Address).FirstOrDefault(a => a != null) ?? d.Key.FullAddress },
|
||||||
d.Value.Select(d => d.Title).ToArray()
|
d.Value.Select(d => d.Title).FirstOrDefault("Briefkopf"),
|
||||||
))
|
d.Value.Select(d => d.Title).ToArray()
|
||||||
);
|
))
|
||||||
}
|
);
|
||||||
|
}
|
||||||
|
});
|
||||||
Mouse.OverrideCursor = null;
|
Mouse.OverrideCursor = null;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -893,8 +897,8 @@ namespace Elwig.Windows {
|
|||||||
|
|
||||||
SmtpClient? client = null;
|
SmtpClient? client = null;
|
||||||
try {
|
try {
|
||||||
Mouse.OverrideCursor = Cursors.AppStarting;
|
Mouse.OverrideCursor = Cursors.Wait;
|
||||||
client = await Utils.GetSmtpClient();
|
client = await Task.Run(Utils.GetSmtpClient);
|
||||||
Mouse.OverrideCursor = null;
|
Mouse.OverrideCursor = null;
|
||||||
|
|
||||||
var res = MessageBox.Show($"Sollen {EmailDocuments.Count:N0} E-Mails verschickt werden?",
|
var res = MessageBox.Show($"Sollen {EmailDocuments.Count:N0} E-Mails verschickt werden?",
|
||||||
@@ -903,31 +907,33 @@ namespace Elwig.Windows {
|
|||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
Mouse.OverrideCursor = Cursors.AppStarting;
|
Mouse.OverrideCursor = Cursors.Wait;
|
||||||
var subject = EmailSubjectInput.Text;
|
var subject = EmailSubjectInput.Text;
|
||||||
var text = EmailBodyInput.Text;
|
var text = EmailBodyInput.Text;
|
||||||
await Utils.AddSentMailBody(subject, text, EmailDocuments.Count);
|
await Task.Run(async () => {
|
||||||
foreach (var (m, docs) in EmailDocuments) {
|
await Utils.AddSentMailBody(subject, text, EmailDocuments.Count);
|
||||||
using var msg = new MimeMessage();
|
foreach (var (m, docs) in EmailDocuments) {
|
||||||
msg.From.Add(new MailboxAddress(App.Client.NameFull, App.Config.Smtp.Value.From));
|
using var msg = new MimeMessage();
|
||||||
msg.To.AddRange(m.EmailAddresses.OrderBy(a => a.Nr).Select(a => new MailboxAddress(m.AdministrativeName, a.Address)));
|
msg.From.Add(new MailboxAddress(App.Client.NameFull, App.Config.Smtp.Value.From));
|
||||||
msg.Subject = subject;
|
msg.To.AddRange(m.EmailAddresses.OrderBy(a => a.Nr).Select(a => new MailboxAddress(m.AdministrativeName, a.Address)));
|
||||||
var body = new Multipart("mixed") {
|
msg.Subject = subject;
|
||||||
new TextPart("plain") { Text = text }
|
var body = new Multipart("mixed") {
|
||||||
};
|
new TextPart("plain") { Text = text }
|
||||||
foreach (var doc in docs) {
|
};
|
||||||
var name = Utils.NormalizeFileName(doc.Title);
|
foreach (var doc in docs) {
|
||||||
body.Add(doc.AsEmailAttachment($"{name}.pdf"));
|
var name = Utils.NormalizeFileName(doc.Title);
|
||||||
|
body.Add(doc.AsEmailAttachment($"{name}.pdf"));
|
||||||
|
}
|
||||||
|
msg.Body = body;
|
||||||
|
await client!.SendAsync(msg);
|
||||||
|
await Utils.AddSentMails([(
|
||||||
|
"email", m.MgNr, m.AdministrativeName,
|
||||||
|
m.EmailAddresses.OrderBy(a => a.Nr).Select(a => a.Address).ToArray(),
|
||||||
|
subject,
|
||||||
|
docs.Select(d => d.Title).ToArray()
|
||||||
|
)]);
|
||||||
}
|
}
|
||||||
msg.Body = body;
|
});
|
||||||
await client!.SendAsync(msg);
|
|
||||||
await Utils.AddSentMails([(
|
|
||||||
"email", m.MgNr, m.AdministrativeName,
|
|
||||||
m.EmailAddresses.OrderBy(a => a.Nr).Select(a => a.Address).ToArray(),
|
|
||||||
subject,
|
|
||||||
docs.Select(d => d.Title).ToArray()
|
|
||||||
)]);
|
|
||||||
}
|
|
||||||
|
|
||||||
MessageBox.Show("Erfolgreich alle E-Mails verschickt!", "Rundschreiben verschicken", MessageBoxButton.OK, MessageBoxImage.Information);
|
MessageBox.Show("Erfolgreich alle E-Mails verschickt!", "Rundschreiben verschicken", MessageBoxButton.OK, MessageBoxImage.Information);
|
||||||
} catch (Exception exc) {
|
} catch (Exception exc) {
|
||||||
|
@@ -41,6 +41,17 @@
|
|||||||
<TextBlock FontFamily="Segoe MDL2 Assets" FontSize="16" Text=""/>
|
<TextBlock FontFamily="Segoe MDL2 Assets" FontSize="16" Text=""/>
|
||||||
</MenuItem.Icon>
|
</MenuItem.Icon>
|
||||||
</MenuItem>
|
</MenuItem>
|
||||||
|
<Separator/>
|
||||||
|
<MenuItem x:Name="Menu_Database_Upload" Header="Datenbank hochladen..." Click="Menu_Database_Upload_Click">
|
||||||
|
<MenuItem.Icon>
|
||||||
|
<TextBlock FontFamily="Segoe MDL2 Assets" FontSize="16" Text=""/>
|
||||||
|
</MenuItem.Icon>
|
||||||
|
</MenuItem>
|
||||||
|
<MenuItem x:Name="Menu_Database_Download" Header="Datenbank herunterladen..." Click="Menu_Database_Download_Click" IsEnabled="False">
|
||||||
|
<MenuItem.Icon>
|
||||||
|
<TextBlock FontFamily="Segoe MDL2 Assets" FontSize="16" Text=""/>
|
||||||
|
</MenuItem.Icon>
|
||||||
|
</MenuItem>
|
||||||
</MenuItem>
|
</MenuItem>
|
||||||
<MenuItem Header="Waage">
|
<MenuItem Header="Waage">
|
||||||
<MenuItem Header="Datum und Uhrzeit setzen" Click="Menu_Scale_SetDateTime_Click">
|
<MenuItem Header="Datum und Uhrzeit setzen" Click="Menu_Scale_SetDateTime_Click">
|
||||||
|
@@ -25,12 +25,14 @@ namespace Elwig.Windows {
|
|||||||
public MainWindow() {
|
public MainWindow() {
|
||||||
InitializeComponent();
|
InitializeComponent();
|
||||||
var v = Assembly.GetExecutingAssembly().GetName().Version;
|
var v = Assembly.GetExecutingAssembly().GetName().Version;
|
||||||
VersionField.Text = "Version: " + (v == null ? "?" : $"{v.Major}.{v.Minor}.{v.Build}") + $" – {App.BranchName}";
|
VersionField.Text = $"Version: {v?.ToString() ?? "?"} – {App.BranchName}";
|
||||||
if (App.Client.Client == null) VersionField.Text += " (Unbekannt)";
|
if (App.Client.Client == null) VersionField.Text += " (Unbekannt)";
|
||||||
Menu_Help_Update.IsEnabled = App.Config.UpdateUrl != null;
|
Menu_Help_Update.IsEnabled = App.Config.UpdateUrl != null;
|
||||||
Menu_Help_Smtp.IsEnabled = App.Config.Smtp != null;
|
Menu_Help_Smtp.IsEnabled = App.Config.Smtp != null;
|
||||||
DownloadButton.Visibility = App.Config.SyncUrl != null ? Visibility.Visible : Visibility.Hidden;
|
DownloadButton.Visibility = App.Config.SyncUrl != null ? Visibility.Visible : Visibility.Hidden;
|
||||||
UploadButton.Visibility = App.Config.SyncUrl != null ? Visibility.Visible : Visibility.Hidden;
|
UploadButton.Visibility = App.Config.SyncUrl != null ? Visibility.Visible : Visibility.Hidden;
|
||||||
|
Menu_Database_Upload.IsEnabled = App.Config.SyncUrl != null;
|
||||||
|
Menu_Database_Download.IsEnabled = App.Config.SyncUrl != null;
|
||||||
}
|
}
|
||||||
|
|
||||||
private void Window_Loaded(object sender, RoutedEventArgs evt) {
|
private void Window_Loaded(object sender, RoutedEventArgs evt) {
|
||||||
@@ -156,7 +158,7 @@ namespace Elwig.Windows {
|
|||||||
Name = f!["name"]!.AsValue().GetValue<string>(),
|
Name = f!["name"]!.AsValue().GetValue<string>(),
|
||||||
Timestamp = f!["timestamp"] != null && DateTime.TryParseExact(f!["timestamp"]!.AsValue().GetValue<string>(), "yyyy-MM-ddTHH:mm:ssK", CultureInfo.InvariantCulture, DateTimeStyles.None, out var dt) ? dt : (DateTime?)null,
|
Timestamp = f!["timestamp"] != null && DateTime.TryParseExact(f!["timestamp"]!.AsValue().GetValue<string>(), "yyyy-MM-ddTHH:mm:ssK", CultureInfo.InvariantCulture, DateTimeStyles.None, out var dt) ? dt : (DateTime?)null,
|
||||||
ZwstId = f!["meta"]?["zwstid"]?.AsValue().GetValue<string>() ?? f!["zwstid"]?.AsValue().GetValue<string>(),
|
ZwstId = f!["meta"]?["zwstid"]?.AsValue().GetValue<string>() ?? f!["zwstid"]?.AsValue().GetValue<string>(),
|
||||||
Device = f!["meta"]?["device"]!.AsValue().GetValue<string>(),
|
Device = f!["meta"]?["device"]?.AsValue().GetValue<string>(),
|
||||||
Url = f!["url"]!.AsValue().GetValue<string>(),
|
Url = f!["url"]!.AsValue().GetValue<string>(),
|
||||||
Size = f!["size"]!.AsValue().GetValue<long>(),
|
Size = f!["size"]!.AsValue().GetValue<long>(),
|
||||||
})
|
})
|
||||||
@@ -178,11 +180,11 @@ namespace Elwig.Windows {
|
|||||||
}
|
}
|
||||||
await ElwigData.Import(paths, ElwigData.ImportMode.FromBranches);
|
await ElwigData.Import(paths, ElwigData.ImportMode.FromBranches);
|
||||||
} catch (HttpRequestException exc) {
|
} catch (HttpRequestException exc) {
|
||||||
MessageBox.Show("Eventuell Internetverbindung prüfen!\n\n" + exc.Message, "Fehler", MessageBoxButton.OK, MessageBoxImage.Error);
|
MessageBox.Show("Eventuell Internetverbindung prüfen!\n\n" + exc.Message, "Daten herunterladen", MessageBoxButton.OK, MessageBoxImage.Error);
|
||||||
} catch (TaskCanceledException exc) {
|
} catch (TaskCanceledException exc) {
|
||||||
MessageBox.Show("Eventuell Internetverbindung prüfen!\n\n" + exc.Message, "Fehler", MessageBoxButton.OK, MessageBoxImage.Error);
|
MessageBox.Show("Eventuell Internetverbindung prüfen!\n\n" + exc.Message, "Daten herunterladen", MessageBoxButton.OK, MessageBoxImage.Error);
|
||||||
} catch (Exception exc) {
|
} catch (Exception exc) {
|
||||||
MessageBox.Show(exc.Message, "Fehler", MessageBoxButton.OK, MessageBoxImage.Error);
|
MessageBox.Show(exc.Message, "Daten herunterladen", MessageBoxButton.OK, MessageBoxImage.Error);
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
Mouse.OverrideCursor = null;
|
Mouse.OverrideCursor = null;
|
||||||
@@ -200,16 +202,25 @@ namespace Elwig.Windows {
|
|||||||
.Where(d => d.Year == Utils.CurrentLastSeason && d.ZwstId == App.ZwstId)
|
.Where(d => d.Year == Utils.CurrentLastSeason && d.ZwstId == App.ZwstId)
|
||||||
.Include(d => d.Parts)
|
.Include(d => d.Parts)
|
||||||
.ThenInclude(p => p.PartModifiers)
|
.ThenInclude(p => p.PartModifiers)
|
||||||
|
.Include(d => d.Parts)
|
||||||
|
.ThenInclude(p => p.Kg)
|
||||||
|
.ThenInclude(k => k!.Gl)
|
||||||
.OrderBy(d => d.DateString)
|
.OrderBy(d => d.DateString)
|
||||||
.ThenBy(d => d.TimeString)
|
.ThenBy(d => d.TimeString)
|
||||||
.ThenBy(d => d.LsNr)
|
.ThenBy(d => d.LsNr)
|
||||||
.AsSplitQuery()
|
.AsSplitQuery()
|
||||||
.ToListAsync();
|
.ToListAsync();
|
||||||
|
var wbKgs = deliveries
|
||||||
|
.SelectMany(d => d.Parts)
|
||||||
|
.Where(p => p.Kg != null)
|
||||||
|
.Select(p => p.Kg!)
|
||||||
|
.DistinctBy(k => k.KgNr)
|
||||||
|
.ToList();
|
||||||
if (deliveries.Count == 0) {
|
if (deliveries.Count == 0) {
|
||||||
MessageBox.Show("Es gibt keine Lieferungen, die hochgeladen werden können!", "Lieferungen hochladen",
|
MessageBox.Show("Es gibt keine Lieferungen, die hochgeladen werden können!", "Lieferungen hochladen",
|
||||||
MessageBoxButton.OK, MessageBoxImage.Error);
|
MessageBoxButton.OK, MessageBoxImage.Error);
|
||||||
} else {
|
} else {
|
||||||
await ElwigData.Export(path, deliveries, [$"{Utils.CurrentLastSeason}", $"Zweigstelle {App.BranchName}"]);
|
await ElwigData.Export(path, deliveries, wbKgs, [$"{Utils.CurrentLastSeason}", $"Zweigstelle {App.BranchName}"]);
|
||||||
await Utils.UploadExportData(path, App.Config.SyncUrl, App.Config.SyncUsername, App.Config.SyncPassword);
|
await Utils.UploadExportData(path, App.Config.SyncUrl, App.Config.SyncUsername, App.Config.SyncPassword);
|
||||||
MessageBox.Show($"Hochladen von {deliveries.Count:N0} Lieferungen erfolgreich!", "Lieferungen hochladen",
|
MessageBox.Show($"Hochladen von {deliveries.Count:N0} Lieferungen erfolgreich!", "Lieferungen hochladen",
|
||||||
MessageBoxButton.OK, MessageBoxImage.Information);
|
MessageBoxButton.OK, MessageBoxImage.Information);
|
||||||
@@ -225,6 +236,87 @@ namespace Elwig.Windows {
|
|||||||
Mouse.OverrideCursor = null;
|
Mouse.OverrideCursor = null;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private async void Menu_Database_Download_Click(object sender, RoutedEventArgs evt) {
|
||||||
|
if (App.Config.SyncUrl == null)
|
||||||
|
return;
|
||||||
|
Mouse.OverrideCursor = Cursors.Wait;
|
||||||
|
await Task.Run(async () => {
|
||||||
|
try {
|
||||||
|
var data = await Utils.GetExportMetaData(App.Config.SyncUrl, App.Config.SyncUsername, App.Config.SyncPassword);
|
||||||
|
var file = data
|
||||||
|
.Select(f => new {
|
||||||
|
Name = f!["name"]!.AsValue().GetValue<string>(),
|
||||||
|
Timestamp = f!["modified"] != null && DateTime.TryParseExact(f!["modified"]!.AsValue().GetValue<string>(), "yyyy-MM-ddTHH:mm:ssK", CultureInfo.InvariantCulture, DateTimeStyles.None, out var dt) ? dt : (DateTime?)null,
|
||||||
|
Url = f!["url"]!.AsValue().GetValue<string>(),
|
||||||
|
Size = f!["size"]!.AsValue().GetValue<long>(),
|
||||||
|
})
|
||||||
|
.Where(f => f.Name == "database.sqlite3.zip")
|
||||||
|
.FirstOrDefault();
|
||||||
|
|
||||||
|
if (file == null) {
|
||||||
|
MessageBox.Show("Die Datenbank wurde noch nicht vom Hauptgerät hochgeladen!", "Datenbank herunterladen",
|
||||||
|
MessageBoxButton.OK, MessageBoxImage.Error);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
var res = MessageBox.Show($"Es wurde eine komprimierte Datenbank (ca. {file.Size / 1024 / 1024} MB) vom {file.Timestamp:dd.MM.yyyy, HH:mm} gefunden.\n\nWollen Sie wirklich die aktuelle Datenbank unwiederruflich\nlöschen und durch die gefundene ersetzen?\n\nDas kann zu Datenverlust führen!", "Datenbank herunterladen",
|
||||||
|
MessageBoxButton.OKCancel, MessageBoxImage.Warning, MessageBoxResult.Cancel);
|
||||||
|
if (res != MessageBoxResult.OK)
|
||||||
|
return;
|
||||||
|
|
||||||
|
var filename = Path.Combine(App.TempPath, file.Name);
|
||||||
|
using (var client = Utils.GetHttpClient(App.Config.SyncUsername, App.Config.SyncPassword)) {
|
||||||
|
using var stream = new FileStream(filename, FileMode.Create);
|
||||||
|
await client.DownloadAsync(file.Url, stream);
|
||||||
|
}
|
||||||
|
|
||||||
|
res = MessageBox.Show("Die Datenbank wurde erfolgreich heruntergeladen!\n\nSoll die Datenbank wirklich unwiederruflich ersetzt werden?\n\nWenn Sie unsicher sind sprechen Sie sich mit dem Benutzer des Hauptgerätes ab!", "Datenbank herunterladen",
|
||||||
|
MessageBoxButton.OKCancel, MessageBoxImage.Warning, MessageBoxResult.Cancel);
|
||||||
|
if (res != MessageBoxResult.OK)
|
||||||
|
return;
|
||||||
|
|
||||||
|
await App.MainDispatcher.BeginInvoke(async () => {
|
||||||
|
await App.ReplaceDatabase(filename);
|
||||||
|
});
|
||||||
|
} catch (HttpRequestException exc) {
|
||||||
|
MessageBox.Show("Eventuell Internetverbindung prüfen!\n\n" + exc.Message, "Datenbank herunterladen", MessageBoxButton.OK, MessageBoxImage.Error);
|
||||||
|
} catch (TaskCanceledException exc) {
|
||||||
|
MessageBox.Show("Eventuell Internetverbindung prüfen!\n\n" + exc.Message, "Datenbank herunterladen", MessageBoxButton.OK, MessageBoxImage.Error);
|
||||||
|
} catch (Exception exc) {
|
||||||
|
MessageBox.Show(exc.Message, "Datenbank herunterladen", MessageBoxButton.OK, MessageBoxImage.Error);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
Mouse.OverrideCursor = null;
|
||||||
|
}
|
||||||
|
|
||||||
|
private async void Menu_Database_Upload_Click(object sender, RoutedEventArgs evt) {
|
||||||
|
if (App.Config.SyncUrl == null)
|
||||||
|
return;
|
||||||
|
|
||||||
|
var res = MessageBox.Show("Sind Sie wirklich sicher, dass Sie die Datenbank dieses\nGerätes hochladen möchten? Das sollte nur vom Hauptgerät aus passieren!", "Datenbank hochladen",
|
||||||
|
MessageBoxButton.OKCancel, MessageBoxImage.Warning, MessageBoxResult.Cancel);
|
||||||
|
if (res != MessageBoxResult.OK)
|
||||||
|
return;
|
||||||
|
|
||||||
|
Mouse.OverrideCursor = Cursors.Wait;
|
||||||
|
await Task.Run(async () => {
|
||||||
|
try {
|
||||||
|
var path = Path.Combine(App.TempPath, "database.sqlite3.zip");
|
||||||
|
ElwigData.ExportDatabase(path);
|
||||||
|
await Utils.UploadExportData(path, App.Config.SyncUrl, App.Config.SyncUsername, App.Config.SyncPassword);
|
||||||
|
MessageBox.Show($"Hochladen der gesamten Datenbank erfolgreich!", "Datenbank hochladen",
|
||||||
|
MessageBoxButton.OK, MessageBoxImage.Information);
|
||||||
|
} catch (HttpRequestException exc) {
|
||||||
|
MessageBox.Show("Eventuell Internetverbindung prüfen!\n\n" + exc.Message, "Datenbank hochladen", MessageBoxButton.OK, MessageBoxImage.Error);
|
||||||
|
} catch (TaskCanceledException exc) {
|
||||||
|
MessageBox.Show("Eventuell Internetverbindung prüfen!\n\n" + exc.Message, "Datenbank hochladen", MessageBoxButton.OK, MessageBoxImage.Error);
|
||||||
|
} catch (Exception exc) {
|
||||||
|
MessageBox.Show(exc.Message, "Datenbank hochladen", MessageBoxButton.OK, MessageBoxImage.Error);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
Mouse.OverrideCursor = null;
|
||||||
|
}
|
||||||
|
|
||||||
private void MemberAdminButton_Click(object sender, RoutedEventArgs evt) {
|
private void MemberAdminButton_Click(object sender, RoutedEventArgs evt) {
|
||||||
var w = new MemberAdminWindow();
|
var w = new MemberAdminWindow();
|
||||||
w.Show();
|
w.Show();
|
||||||
|
@@ -392,6 +392,7 @@ namespace Elwig.Windows {
|
|||||||
Mouse.OverrideCursor = Cursors.Wait;
|
Mouse.OverrideCursor = Cursors.Wait;
|
||||||
try {
|
try {
|
||||||
await MemberService.DeleteMember(m.MgNr, d.DeletePaymentData, d.DeleteDeliveries, d.DeleteAreaComs);
|
await MemberService.DeleteMember(m.MgNr, d.DeletePaymentData, d.DeleteDeliveries, d.DeleteAreaComs);
|
||||||
|
App.HintContextChange();
|
||||||
} catch (Exception exc) {
|
} catch (Exception exc) {
|
||||||
var str = "Der Eintrag konnte nicht in der Datenbank aktualisiert werden!\n\n" + exc.Message;
|
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;
|
if (exc.InnerException != null) str += "\n\n" + exc.InnerException.Message;
|
||||||
@@ -414,6 +415,7 @@ namespace Elwig.Windows {
|
|||||||
int mgnr;
|
int mgnr;
|
||||||
try {
|
try {
|
||||||
mgnr = await ViewModel.UpdateMember(ViewModel.SelectedMember?.MgNr);
|
mgnr = await ViewModel.UpdateMember(ViewModel.SelectedMember?.MgNr);
|
||||||
|
App.HintContextChange();
|
||||||
} catch (Exception exc) {
|
} catch (Exception exc) {
|
||||||
var str = "Der Eintrag konnte nicht in der Datenbank aktualisiert werden!\n\n" + exc.Message;
|
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;
|
if (exc.InnerException != null) str += "\n\n" + exc.InnerException.Message;
|
||||||
@@ -782,7 +784,7 @@ namespace Elwig.Windows {
|
|||||||
$"{ViewModel.Prefix}{(!string.IsNullOrEmpty(ViewModel.Prefix) ? " " : "")}" +
|
$"{ViewModel.Prefix}{(!string.IsNullOrEmpty(ViewModel.Prefix) ? " " : "")}" +
|
||||||
$"{ViewModel.GivenName}{(!string.IsNullOrEmpty(ViewModel.GivenName) ? " " : "")}" +
|
$"{ViewModel.GivenName}{(!string.IsNullOrEmpty(ViewModel.GivenName) ? " " : "")}" +
|
||||||
$"{ViewModel.Suffix}{(!string.IsNullOrEmpty(ViewModel.Suffix) ? " " : "")}";
|
$"{ViewModel.Suffix}{(!string.IsNullOrEmpty(ViewModel.Suffix) ? " " : "")}";
|
||||||
var d = new AreaComDialog(oldMember.AdministrativeName, newName, areaComs.Count, areaComs.Sum(c => c.Area));
|
var d = new AreaComTransferDialog(oldMember.AdministrativeName, newName, areaComs.Count, areaComs.Sum(c => c.Area));
|
||||||
if (d.ShowDialog() != true)
|
if (d.ShowDialog() != true)
|
||||||
return;
|
return;
|
||||||
ViewModel.TransferPredecessorAreaComs = d.SuccessorSeason;
|
ViewModel.TransferPredecessorAreaComs = d.SuccessorSeason;
|
||||||
@@ -845,7 +847,7 @@ namespace Elwig.Windows {
|
|||||||
.Where(c => c.MgNr == mgnr && (c.YearTo == null || c.YearTo >= Utils.FollowingSeason))
|
.Where(c => c.MgNr == mgnr && (c.YearTo == null || c.YearTo >= Utils.FollowingSeason))
|
||||||
.ToListAsync();
|
.ToListAsync();
|
||||||
if (areaComs.Count > 0) {
|
if (areaComs.Count > 0) {
|
||||||
var d = new AreaComDialog(m.AdministrativeName, areaComs.Count, areaComs.Sum(c => c.Area));
|
var d = new AreaComTransferDialog(m.AdministrativeName, areaComs.Count, areaComs.Sum(c => c.Area));
|
||||||
if (d.ShowDialog() == true) {
|
if (d.ShowDialog() == true) {
|
||||||
ViewModel.CancelAreaComs = d.CancelSeason;
|
ViewModel.CancelAreaComs = d.CancelSeason;
|
||||||
}
|
}
|
||||||
|
@@ -156,7 +156,7 @@ namespace Elwig.Windows {
|
|||||||
}
|
}
|
||||||
|
|
||||||
private async void AutoAdjustBsButton_Click(object sender, RoutedEventArgs evt) {
|
private async void AutoAdjustBsButton_Click(object sender, RoutedEventArgs evt) {
|
||||||
Mouse.OverrideCursor = Cursors.AppStarting;
|
Mouse.OverrideCursor = Cursors.Wait;
|
||||||
try {
|
try {
|
||||||
int? kg = AllowanceKgInput.Text == "" ? null : int.Parse(AllowanceKgInput.Text);
|
int? kg = AllowanceKgInput.Text == "" ? null : int.Parse(AllowanceKgInput.Text);
|
||||||
double? bs = AllowanceBsInput.Text == "" ? null : double.Parse(AllowanceBsInput.Text);
|
double? bs = AllowanceBsInput.Text == "" ? null : double.Parse(AllowanceBsInput.Text);
|
||||||
@@ -169,10 +169,12 @@ namespace Elwig.Windows {
|
|||||||
App.Client.AutoAdjustBs.AllowanceKgPerBs = kgPerBs;
|
App.Client.AutoAdjustBs.AllowanceKgPerBs = kgPerBs;
|
||||||
App.Client.AutoAdjustBs.AllowancePercent = percent;
|
App.Client.AutoAdjustBs.AllowancePercent = percent;
|
||||||
App.Client.AutoAdjustBs.MinBs = minBs;
|
App.Client.AutoAdjustBs.MinBs = minBs;
|
||||||
await App.Client.UpdateValues();
|
|
||||||
|
|
||||||
var b = new Billing(Year);
|
await Task.Run(async () => {
|
||||||
await b.AutoAdjustBusinessShares(new DateOnly(Year, 11, 30), kg ?? default, bs ?? default, kgPerBs ?? default, percent / 100.0 ?? default, minBs ?? default);
|
await App.Client.UpdateValues();
|
||||||
|
var b = new Billing(Year);
|
||||||
|
await b.AutoAdjustBusinessShares(new DateOnly(Year, 11, 30), kg ?? default, bs ?? default, kgPerBs ?? default, percent / 100.0 ?? default, minBs ?? default);
|
||||||
|
});
|
||||||
App.HintContextChange();
|
App.HintContextChange();
|
||||||
} catch (Exception exc) {
|
} catch (Exception exc) {
|
||||||
var str = "Der Eintrag konnte nicht in der Datenbank aktualisiert werden!\n\n" + exc.Message;
|
var str = "Der Eintrag konnte nicht in der Datenbank aktualisiert werden!\n\n" + exc.Message;
|
||||||
@@ -183,10 +185,12 @@ namespace Elwig.Windows {
|
|||||||
}
|
}
|
||||||
|
|
||||||
private async void UnAdjustBsButton_Click(object sender, RoutedEventArgs evt) {
|
private async void UnAdjustBsButton_Click(object sender, RoutedEventArgs evt) {
|
||||||
Mouse.OverrideCursor = Cursors.AppStarting;
|
Mouse.OverrideCursor = Cursors.Wait;
|
||||||
try {
|
try {
|
||||||
var b = new Billing(Year);
|
await Task.Run(async () => {
|
||||||
await b.UnAdjustBusinessShares();
|
var b = new Billing(Year);
|
||||||
|
await b.UnAdjustBusinessShares();
|
||||||
|
});
|
||||||
App.HintContextChange();
|
App.HintContextChange();
|
||||||
} catch (Exception exc) {
|
} catch (Exception exc) {
|
||||||
var str = "Der Eintrag konnte nicht in der Datenbank aktualisiert werden!\n\n" + exc.Message;
|
var str = "Der Eintrag konnte nicht in der Datenbank aktualisiert werden!\n\n" + exc.Message;
|
||||||
@@ -281,35 +285,37 @@ namespace Elwig.Windows {
|
|||||||
|
|
||||||
private async void CustomButton_Click(object sender, RoutedEventArgs evt) {
|
private async void CustomButton_Click(object sender, RoutedEventArgs evt) {
|
||||||
if (MemberInput.SelectedItem is not Member m) return;
|
if (MemberInput.SelectedItem is not Member m) return;
|
||||||
Mouse.OverrideCursor = Cursors.AppStarting;
|
Mouse.OverrideCursor = Cursors.Wait;
|
||||||
try {
|
try {
|
||||||
using var ctx = new AppDbContext();
|
var modAbs = decimal.TryParse(CustomModAbsInput.Text, out var n1) ? (decimal?)n1 : null;
|
||||||
if (CustomPayments?.TryGetValue(m.MgNr, out var p) == true) {
|
var modRel = decimal.TryParse(CustomModRelInput.Text, out var n2) ? (decimal?)n2 / 100 : null;
|
||||||
ctx.Remove(p);
|
var amount = decimal.TryParse(CustomAmountInput.Text, out var n3) ? (decimal?)n3 : null;
|
||||||
}
|
var modText = CustomModCommentInput.Text.Trim();
|
||||||
if (sender == SaveCustomButton) {
|
var text = CustomCommentInput.Text.Trim();
|
||||||
var modAbs = decimal.TryParse(CustomModAbsInput.Text, out var n1) ? (decimal?)n1 : null;
|
await Task.Run(async () => {
|
||||||
var modRel = decimal.TryParse(CustomModRelInput.Text, out var n2) ? (decimal?)n2 / 100 : null;
|
using var ctx = new AppDbContext();
|
||||||
var amount = decimal.TryParse(CustomAmountInput.Text, out var n3) ? (decimal?)n3 : null;
|
if (CustomPayments?.TryGetValue(m.MgNr, out var p) == true) {
|
||||||
var modText = CustomModCommentInput.Text.Trim();
|
ctx.Remove(p);
|
||||||
var text = CustomCommentInput.Text.Trim();
|
}
|
||||||
ctx.Add(new PaymentCustom {
|
if (sender == SaveCustomButton) {
|
||||||
MgNr = m.MgNr,
|
ctx.Add(new PaymentCustom {
|
||||||
Year = Year,
|
MgNr = m.MgNr,
|
||||||
ModAbs = modAbs,
|
Year = Year,
|
||||||
ModRel = modRel,
|
ModAbs = modAbs,
|
||||||
ModComment = modText == "" ? null : modText,
|
ModRel = modRel,
|
||||||
Amount = amount,
|
ModComment = modText == "" ? null : modText,
|
||||||
Comment = text == "" ? null : text,
|
Amount = amount,
|
||||||
});
|
Comment = text == "" ? null : text,
|
||||||
}
|
});
|
||||||
await ctx.SaveChangesAsync();
|
}
|
||||||
|
await ctx.SaveChangesAsync();
|
||||||
|
});
|
||||||
|
App.HintContextChange();
|
||||||
} catch (Exception exc) {
|
} catch (Exception exc) {
|
||||||
var str = "Der Eintrag konnte nicht in der Datenbank aktualisiert werden!\n\n" + exc.Message;
|
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;
|
if (exc.InnerException != null) str += "\n\n" + exc.InnerException.Message;
|
||||||
MessageBox.Show(str, "Benutzerdefinierten Zu-/Abschlag speichern", MessageBoxButton.OK, MessageBoxImage.Error);
|
MessageBox.Show(str, "Benutzerdefinierten Zu-/Abschlag speichern", MessageBoxButton.OK, MessageBoxImage.Error);
|
||||||
}
|
}
|
||||||
App.HintContextChange();
|
|
||||||
Mouse.OverrideCursor = null;
|
Mouse.OverrideCursor = null;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@@ -128,7 +128,8 @@
|
|||||||
VerticalAlignment="Center" HorizontalAlignment="Right" Width="25" Height="25" Margin="5,60,5,0" Grid.RowSpan="2"
|
VerticalAlignment="Center" HorizontalAlignment="Right" Width="25" Height="25" Margin="5,60,5,0" Grid.RowSpan="2"
|
||||||
Click="DeleteButton_Click"/>
|
Click="DeleteButton_Click"/>
|
||||||
|
|
||||||
<TextBox x:Name="DataInput" Margin="10,200,35,10" IsReadOnly="{Binding DataIsReadOnly}"
|
<TextBox x:Name="DataInput" Text="{Binding Data, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}" IsReadOnly="{Binding DataIsReadOnly}"
|
||||||
|
Margin="10,200,35,10"
|
||||||
HorizontalAlignment="Stretch" VerticalAlignment="Stretch" Height="auto"
|
HorizontalAlignment="Stretch" VerticalAlignment="Stretch" Height="auto"
|
||||||
AcceptsReturn="True" VerticalScrollBarVisibility="Visible" HorizontalScrollBarVisibility="Auto"
|
AcceptsReturn="True" VerticalScrollBarVisibility="Visible" HorizontalScrollBarVisibility="Auto"
|
||||||
FontFamily="Cascadia Code Light" FontSize="13"
|
FontFamily="Cascadia Code Light" FontSize="13"
|
||||||
|
@@ -87,14 +87,17 @@ namespace Elwig.Windows {
|
|||||||
}
|
}
|
||||||
|
|
||||||
private async void AddButton_Click(object sender, RoutedEventArgs evt) {
|
private async void AddButton_Click(object sender, RoutedEventArgs evt) {
|
||||||
|
Mouse.OverrideCursor = Cursors.Wait;
|
||||||
try {
|
try {
|
||||||
var v = await PaymentVariantService.CreatePaymentVariant(Year);
|
var v = await PaymentVariantService.CreatePaymentVariant(Year);
|
||||||
|
App.HintContextChange();
|
||||||
ControlUtils.SelectItem(PaymentVariantList, v);
|
ControlUtils.SelectItem(PaymentVariantList, v);
|
||||||
} catch (Exception exc) {
|
} catch (Exception exc) {
|
||||||
var str = "Der Eintrag konnte nicht in der Datenbank aktualisiert werden!\n\n" + exc.Message;
|
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;
|
if (exc.InnerException != null) str += "\n\n" + exc.InnerException.Message;
|
||||||
MessageBox.Show(str, "Auszahlungsvariante erstellen", MessageBoxButton.OK, MessageBoxImage.Error);
|
MessageBox.Show(str, "Auszahlungsvariante erstellen", MessageBoxButton.OK, MessageBoxImage.Error);
|
||||||
}
|
}
|
||||||
|
Mouse.OverrideCursor = null;
|
||||||
}
|
}
|
||||||
|
|
||||||
private async void CopyButton_Click(object sender, RoutedEventArgs evt) {
|
private async void CopyButton_Click(object sender, RoutedEventArgs evt) {
|
||||||
@@ -103,6 +106,7 @@ namespace Elwig.Windows {
|
|||||||
Mouse.OverrideCursor = Cursors.Wait;
|
Mouse.OverrideCursor = Cursors.Wait;
|
||||||
try {
|
try {
|
||||||
PaymentVar n = await orig.Duplicate();
|
PaymentVar n = await orig.Duplicate();
|
||||||
|
App.HintContextChange();
|
||||||
ControlUtils.SelectItem(PaymentVariantList, n);
|
ControlUtils.SelectItem(PaymentVariantList, n);
|
||||||
} catch (Exception exc) {
|
} catch (Exception exc) {
|
||||||
var str = "Der Eintrag konnte nicht in der Datenbank aktualisiert werden!\n\n" + exc.Message;
|
var str = "Der Eintrag konnte nicht in der Datenbank aktualisiert werden!\n\n" + exc.Message;
|
||||||
@@ -118,6 +122,7 @@ namespace Elwig.Windows {
|
|||||||
Mouse.OverrideCursor = Cursors.Wait;
|
Mouse.OverrideCursor = Cursors.Wait;
|
||||||
try {
|
try {
|
||||||
await PaymentVariantService.DeletePaymentVariant(v.Year, v.AvNr);
|
await PaymentVariantService.DeletePaymentVariant(v.Year, v.AvNr);
|
||||||
|
App.HintContextChange();
|
||||||
} catch (Exception exc) {
|
} catch (Exception exc) {
|
||||||
var str = "Der Eintrag konnte nicht in der Datenbank aktualisiert werden!\n\n" + exc.Message;
|
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;
|
if (exc.InnerException != null) str += "\n\n" + exc.InnerException.Message;
|
||||||
@@ -133,6 +138,7 @@ namespace Elwig.Windows {
|
|||||||
Mouse.OverrideCursor = Cursors.Wait;
|
Mouse.OverrideCursor = Cursors.Wait;
|
||||||
try {
|
try {
|
||||||
await PaymentVariantService.Calculate(v.Year, v.AvNr);
|
await PaymentVariantService.Calculate(v.Year, v.AvNr);
|
||||||
|
App.HintContextChange();
|
||||||
} catch (Exception exc) {
|
} catch (Exception exc) {
|
||||||
MessageBox.Show(exc.Message, "Berechnungsfehler", MessageBoxButton.OK, MessageBoxImage.Error);
|
MessageBox.Show(exc.Message, "Berechnungsfehler", MessageBoxButton.OK, MessageBoxImage.Error);
|
||||||
}
|
}
|
||||||
@@ -194,6 +200,7 @@ namespace Elwig.Windows {
|
|||||||
Mouse.OverrideCursor = Cursors.Wait;
|
Mouse.OverrideCursor = Cursors.Wait;
|
||||||
try {
|
try {
|
||||||
await PaymentVariantService.Commit(v.Year, v.AvNr);
|
await PaymentVariantService.Commit(v.Year, v.AvNr);
|
||||||
|
App.HintContextChange();
|
||||||
} catch (Exception exc) {
|
} catch (Exception exc) {
|
||||||
MessageBox.Show(exc.Message, "Fehler", MessageBoxButton.OK, MessageBoxImage.Error);
|
MessageBox.Show(exc.Message, "Fehler", MessageBoxButton.OK, MessageBoxImage.Error);
|
||||||
}
|
}
|
||||||
@@ -214,6 +221,7 @@ namespace Elwig.Windows {
|
|||||||
Mouse.OverrideCursor = Cursors.Wait;
|
Mouse.OverrideCursor = Cursors.Wait;
|
||||||
try {
|
try {
|
||||||
await PaymentVariantService.Revert(v.Year, v.AvNr);
|
await PaymentVariantService.Revert(v.Year, v.AvNr);
|
||||||
|
App.HintContextChange();
|
||||||
} catch (Exception exc) {
|
} catch (Exception exc) {
|
||||||
MessageBox.Show(exc.Message, "Fehler", MessageBoxButton.OK, MessageBoxImage.Error);
|
MessageBox.Show(exc.Message, "Fehler", MessageBoxButton.OK, MessageBoxImage.Error);
|
||||||
}
|
}
|
||||||
@@ -243,6 +251,7 @@ namespace Elwig.Windows {
|
|||||||
Mouse.OverrideCursor = Cursors.Wait;
|
Mouse.OverrideCursor = Cursors.Wait;
|
||||||
try {
|
try {
|
||||||
await ViewModel.UpdatePaymentVariant(v.Year, v.AvNr);
|
await ViewModel.UpdatePaymentVariant(v.Year, v.AvNr);
|
||||||
|
App.HintContextChange();
|
||||||
} catch (Exception exc) {
|
} catch (Exception exc) {
|
||||||
await HintContextChange();
|
await HintContextChange();
|
||||||
var str = "Der Eintrag konnte nicht in der Datenbank aktualisiert werden!\n\n" + exc.Message;
|
var str = "Der Eintrag konnte nicht in der Datenbank aktualisiert werden!\n\n" + exc.Message;
|
||||||
|
674
LICENSE
Normal file
674
LICENSE
Normal file
@@ -0,0 +1,674 @@
|
|||||||
|
GNU GENERAL PUBLIC LICENSE
|
||||||
|
Version 3, 29 June 2007
|
||||||
|
|
||||||
|
Copyright (C) 2007 Free Software Foundation, Inc. <https://fsf.org/>
|
||||||
|
Everyone is permitted to copy and distribute verbatim copies
|
||||||
|
of this license document, but changing it is not allowed.
|
||||||
|
|
||||||
|
Preamble
|
||||||
|
|
||||||
|
The GNU General Public License is a free, copyleft license for
|
||||||
|
software and other kinds of works.
|
||||||
|
|
||||||
|
The licenses for most software and other practical works are designed
|
||||||
|
to take away your freedom to share and change the works. By contrast,
|
||||||
|
the GNU General Public License is intended to guarantee your freedom to
|
||||||
|
share and change all versions of a program--to make sure it remains free
|
||||||
|
software for all its users. We, the Free Software Foundation, use the
|
||||||
|
GNU General Public License for most of our software; it applies also to
|
||||||
|
any other work released this way by its authors. You can apply it to
|
||||||
|
your programs, too.
|
||||||
|
|
||||||
|
When we speak of free software, we are referring to freedom, not
|
||||||
|
price. Our General Public Licenses are designed to make sure that you
|
||||||
|
have the freedom to distribute copies of free software (and charge for
|
||||||
|
them if you wish), that you receive source code or can get it if you
|
||||||
|
want it, that you can change the software or use pieces of it in new
|
||||||
|
free programs, and that you know you can do these things.
|
||||||
|
|
||||||
|
To protect your rights, we need to prevent others from denying you
|
||||||
|
these rights or asking you to surrender the rights. Therefore, you have
|
||||||
|
certain responsibilities if you distribute copies of the software, or if
|
||||||
|
you modify it: responsibilities to respect the freedom of others.
|
||||||
|
|
||||||
|
For example, if you distribute copies of such a program, whether
|
||||||
|
gratis or for a fee, you must pass on to the recipients the same
|
||||||
|
freedoms that you received. You must make sure that they, too, receive
|
||||||
|
or can get the source code. And you must show them these terms so they
|
||||||
|
know their rights.
|
||||||
|
|
||||||
|
Developers that use the GNU GPL protect your rights with two steps:
|
||||||
|
(1) assert copyright on the software, and (2) offer you this License
|
||||||
|
giving you legal permission to copy, distribute and/or modify it.
|
||||||
|
|
||||||
|
For the developers' and authors' protection, the GPL clearly explains
|
||||||
|
that there is no warranty for this free software. For both users' and
|
||||||
|
authors' sake, the GPL requires that modified versions be marked as
|
||||||
|
changed, so that their problems will not be attributed erroneously to
|
||||||
|
authors of previous versions.
|
||||||
|
|
||||||
|
Some devices are designed to deny users access to install or run
|
||||||
|
modified versions of the software inside them, although the manufacturer
|
||||||
|
can do so. This is fundamentally incompatible with the aim of
|
||||||
|
protecting users' freedom to change the software. The systematic
|
||||||
|
pattern of such abuse occurs in the area of products for individuals to
|
||||||
|
use, which is precisely where it is most unacceptable. Therefore, we
|
||||||
|
have designed this version of the GPL to prohibit the practice for those
|
||||||
|
products. If such problems arise substantially in other domains, we
|
||||||
|
stand ready to extend this provision to those domains in future versions
|
||||||
|
of the GPL, as needed to protect the freedom of users.
|
||||||
|
|
||||||
|
Finally, every program is threatened constantly by software patents.
|
||||||
|
States should not allow patents to restrict development and use of
|
||||||
|
software on general-purpose computers, but in those that do, we wish to
|
||||||
|
avoid the special danger that patents applied to a free program could
|
||||||
|
make it effectively proprietary. To prevent this, the GPL assures that
|
||||||
|
patents cannot be used to render the program non-free.
|
||||||
|
|
||||||
|
The precise terms and conditions for copying, distribution and
|
||||||
|
modification follow.
|
||||||
|
|
||||||
|
TERMS AND CONDITIONS
|
||||||
|
|
||||||
|
0. Definitions.
|
||||||
|
|
||||||
|
"This License" refers to version 3 of the GNU General Public License.
|
||||||
|
|
||||||
|
"Copyright" also means copyright-like laws that apply to other kinds of
|
||||||
|
works, such as semiconductor masks.
|
||||||
|
|
||||||
|
"The Program" refers to any copyrightable work licensed under this
|
||||||
|
License. Each licensee is addressed as "you". "Licensees" and
|
||||||
|
"recipients" may be individuals or organizations.
|
||||||
|
|
||||||
|
To "modify" a work means to copy from or adapt all or part of the work
|
||||||
|
in a fashion requiring copyright permission, other than the making of an
|
||||||
|
exact copy. The resulting work is called a "modified version" of the
|
||||||
|
earlier work or a work "based on" the earlier work.
|
||||||
|
|
||||||
|
A "covered work" means either the unmodified Program or a work based
|
||||||
|
on the Program.
|
||||||
|
|
||||||
|
To "propagate" a work means to do anything with it that, without
|
||||||
|
permission, would make you directly or secondarily liable for
|
||||||
|
infringement under applicable copyright law, except executing it on a
|
||||||
|
computer or modifying a private copy. Propagation includes copying,
|
||||||
|
distribution (with or without modification), making available to the
|
||||||
|
public, and in some countries other activities as well.
|
||||||
|
|
||||||
|
To "convey" a work means any kind of propagation that enables other
|
||||||
|
parties to make or receive copies. Mere interaction with a user through
|
||||||
|
a computer network, with no transfer of a copy, is not conveying.
|
||||||
|
|
||||||
|
An interactive user interface displays "Appropriate Legal Notices"
|
||||||
|
to the extent that it includes a convenient and prominently visible
|
||||||
|
feature that (1) displays an appropriate copyright notice, and (2)
|
||||||
|
tells the user that there is no warranty for the work (except to the
|
||||||
|
extent that warranties are provided), that licensees may convey the
|
||||||
|
work under this License, and how to view a copy of this License. If
|
||||||
|
the interface presents a list of user commands or options, such as a
|
||||||
|
menu, a prominent item in the list meets this criterion.
|
||||||
|
|
||||||
|
1. Source Code.
|
||||||
|
|
||||||
|
The "source code" for a work means the preferred form of the work
|
||||||
|
for making modifications to it. "Object code" means any non-source
|
||||||
|
form of a work.
|
||||||
|
|
||||||
|
A "Standard Interface" means an interface that either is an official
|
||||||
|
standard defined by a recognized standards body, or, in the case of
|
||||||
|
interfaces specified for a particular programming language, one that
|
||||||
|
is widely used among developers working in that language.
|
||||||
|
|
||||||
|
The "System Libraries" of an executable work include anything, other
|
||||||
|
than the work as a whole, that (a) is included in the normal form of
|
||||||
|
packaging a Major Component, but which is not part of that Major
|
||||||
|
Component, and (b) serves only to enable use of the work with that
|
||||||
|
Major Component, or to implement a Standard Interface for which an
|
||||||
|
implementation is available to the public in source code form. A
|
||||||
|
"Major Component", in this context, means a major essential component
|
||||||
|
(kernel, window system, and so on) of the specific operating system
|
||||||
|
(if any) on which the executable work runs, or a compiler used to
|
||||||
|
produce the work, or an object code interpreter used to run it.
|
||||||
|
|
||||||
|
The "Corresponding Source" for a work in object code form means all
|
||||||
|
the source code needed to generate, install, and (for an executable
|
||||||
|
work) run the object code and to modify the work, including scripts to
|
||||||
|
control those activities. However, it does not include the work's
|
||||||
|
System Libraries, or general-purpose tools or generally available free
|
||||||
|
programs which are used unmodified in performing those activities but
|
||||||
|
which are not part of the work. For example, Corresponding Source
|
||||||
|
includes interface definition files associated with source files for
|
||||||
|
the work, and the source code for shared libraries and dynamically
|
||||||
|
linked subprograms that the work is specifically designed to require,
|
||||||
|
such as by intimate data communication or control flow between those
|
||||||
|
subprograms and other parts of the work.
|
||||||
|
|
||||||
|
The Corresponding Source need not include anything that users
|
||||||
|
can regenerate automatically from other parts of the Corresponding
|
||||||
|
Source.
|
||||||
|
|
||||||
|
The Corresponding Source for a work in source code form is that
|
||||||
|
same work.
|
||||||
|
|
||||||
|
2. Basic Permissions.
|
||||||
|
|
||||||
|
All rights granted under this License are granted for the term of
|
||||||
|
copyright on the Program, and are irrevocable provided the stated
|
||||||
|
conditions are met. This License explicitly affirms your unlimited
|
||||||
|
permission to run the unmodified Program. The output from running a
|
||||||
|
covered work is covered by this License only if the output, given its
|
||||||
|
content, constitutes a covered work. This License acknowledges your
|
||||||
|
rights of fair use or other equivalent, as provided by copyright law.
|
||||||
|
|
||||||
|
You may make, run and propagate covered works that you do not
|
||||||
|
convey, without conditions so long as your license otherwise remains
|
||||||
|
in force. You may convey covered works to others for the sole purpose
|
||||||
|
of having them make modifications exclusively for you, or provide you
|
||||||
|
with facilities for running those works, provided that you comply with
|
||||||
|
the terms of this License in conveying all material for which you do
|
||||||
|
not control copyright. Those thus making or running the covered works
|
||||||
|
for you must do so exclusively on your behalf, under your direction
|
||||||
|
and control, on terms that prohibit them from making any copies of
|
||||||
|
your copyrighted material outside their relationship with you.
|
||||||
|
|
||||||
|
Conveying under any other circumstances is permitted solely under
|
||||||
|
the conditions stated below. Sublicensing is not allowed; section 10
|
||||||
|
makes it unnecessary.
|
||||||
|
|
||||||
|
3. Protecting Users' Legal Rights From Anti-Circumvention Law.
|
||||||
|
|
||||||
|
No covered work shall be deemed part of an effective technological
|
||||||
|
measure under any applicable law fulfilling obligations under article
|
||||||
|
11 of the WIPO copyright treaty adopted on 20 December 1996, or
|
||||||
|
similar laws prohibiting or restricting circumvention of such
|
||||||
|
measures.
|
||||||
|
|
||||||
|
When you convey a covered work, you waive any legal power to forbid
|
||||||
|
circumvention of technological measures to the extent such circumvention
|
||||||
|
is effected by exercising rights under this License with respect to
|
||||||
|
the covered work, and you disclaim any intention to limit operation or
|
||||||
|
modification of the work as a means of enforcing, against the work's
|
||||||
|
users, your or third parties' legal rights to forbid circumvention of
|
||||||
|
technological measures.
|
||||||
|
|
||||||
|
4. Conveying Verbatim Copies.
|
||||||
|
|
||||||
|
You may convey verbatim copies of the Program's source code as you
|
||||||
|
receive it, in any medium, provided that you conspicuously and
|
||||||
|
appropriately publish on each copy an appropriate copyright notice;
|
||||||
|
keep intact all notices stating that this License and any
|
||||||
|
non-permissive terms added in accord with section 7 apply to the code;
|
||||||
|
keep intact all notices of the absence of any warranty; and give all
|
||||||
|
recipients a copy of this License along with the Program.
|
||||||
|
|
||||||
|
You may charge any price or no price for each copy that you convey,
|
||||||
|
and you may offer support or warranty protection for a fee.
|
||||||
|
|
||||||
|
5. Conveying Modified Source Versions.
|
||||||
|
|
||||||
|
You may convey a work based on the Program, or the modifications to
|
||||||
|
produce it from the Program, in the form of source code under the
|
||||||
|
terms of section 4, provided that you also meet all of these conditions:
|
||||||
|
|
||||||
|
a) The work must carry prominent notices stating that you modified
|
||||||
|
it, and giving a relevant date.
|
||||||
|
|
||||||
|
b) The work must carry prominent notices stating that it is
|
||||||
|
released under this License and any conditions added under section
|
||||||
|
7. This requirement modifies the requirement in section 4 to
|
||||||
|
"keep intact all notices".
|
||||||
|
|
||||||
|
c) You must license the entire work, as a whole, under this
|
||||||
|
License to anyone who comes into possession of a copy. This
|
||||||
|
License will therefore apply, along with any applicable section 7
|
||||||
|
additional terms, to the whole of the work, and all its parts,
|
||||||
|
regardless of how they are packaged. This License gives no
|
||||||
|
permission to license the work in any other way, but it does not
|
||||||
|
invalidate such permission if you have separately received it.
|
||||||
|
|
||||||
|
d) If the work has interactive user interfaces, each must display
|
||||||
|
Appropriate Legal Notices; however, if the Program has interactive
|
||||||
|
interfaces that do not display Appropriate Legal Notices, your
|
||||||
|
work need not make them do so.
|
||||||
|
|
||||||
|
A compilation of a covered work with other separate and independent
|
||||||
|
works, which are not by their nature extensions of the covered work,
|
||||||
|
and which are not combined with it such as to form a larger program,
|
||||||
|
in or on a volume of a storage or distribution medium, is called an
|
||||||
|
"aggregate" if the compilation and its resulting copyright are not
|
||||||
|
used to limit the access or legal rights of the compilation's users
|
||||||
|
beyond what the individual works permit. Inclusion of a covered work
|
||||||
|
in an aggregate does not cause this License to apply to the other
|
||||||
|
parts of the aggregate.
|
||||||
|
|
||||||
|
6. Conveying Non-Source Forms.
|
||||||
|
|
||||||
|
You may convey a covered work in object code form under the terms
|
||||||
|
of sections 4 and 5, provided that you also convey the
|
||||||
|
machine-readable Corresponding Source under the terms of this License,
|
||||||
|
in one of these ways:
|
||||||
|
|
||||||
|
a) Convey the object code in, or embodied in, a physical product
|
||||||
|
(including a physical distribution medium), accompanied by the
|
||||||
|
Corresponding Source fixed on a durable physical medium
|
||||||
|
customarily used for software interchange.
|
||||||
|
|
||||||
|
b) Convey the object code in, or embodied in, a physical product
|
||||||
|
(including a physical distribution medium), accompanied by a
|
||||||
|
written offer, valid for at least three years and valid for as
|
||||||
|
long as you offer spare parts or customer support for that product
|
||||||
|
model, to give anyone who possesses the object code either (1) a
|
||||||
|
copy of the Corresponding Source for all the software in the
|
||||||
|
product that is covered by this License, on a durable physical
|
||||||
|
medium customarily used for software interchange, for a price no
|
||||||
|
more than your reasonable cost of physically performing this
|
||||||
|
conveying of source, or (2) access to copy the
|
||||||
|
Corresponding Source from a network server at no charge.
|
||||||
|
|
||||||
|
c) Convey individual copies of the object code with a copy of the
|
||||||
|
written offer to provide the Corresponding Source. This
|
||||||
|
alternative is allowed only occasionally and noncommercially, and
|
||||||
|
only if you received the object code with such an offer, in accord
|
||||||
|
with subsection 6b.
|
||||||
|
|
||||||
|
d) Convey the object code by offering access from a designated
|
||||||
|
place (gratis or for a charge), and offer equivalent access to the
|
||||||
|
Corresponding Source in the same way through the same place at no
|
||||||
|
further charge. You need not require recipients to copy the
|
||||||
|
Corresponding Source along with the object code. If the place to
|
||||||
|
copy the object code is a network server, the Corresponding Source
|
||||||
|
may be on a different server (operated by you or a third party)
|
||||||
|
that supports equivalent copying facilities, provided you maintain
|
||||||
|
clear directions next to the object code saying where to find the
|
||||||
|
Corresponding Source. Regardless of what server hosts the
|
||||||
|
Corresponding Source, you remain obligated to ensure that it is
|
||||||
|
available for as long as needed to satisfy these requirements.
|
||||||
|
|
||||||
|
e) Convey the object code using peer-to-peer transmission, provided
|
||||||
|
you inform other peers where the object code and Corresponding
|
||||||
|
Source of the work are being offered to the general public at no
|
||||||
|
charge under subsection 6d.
|
||||||
|
|
||||||
|
A separable portion of the object code, whose source code is excluded
|
||||||
|
from the Corresponding Source as a System Library, need not be
|
||||||
|
included in conveying the object code work.
|
||||||
|
|
||||||
|
A "User Product" is either (1) a "consumer product", which means any
|
||||||
|
tangible personal property which is normally used for personal, family,
|
||||||
|
or household purposes, or (2) anything designed or sold for incorporation
|
||||||
|
into a dwelling. In determining whether a product is a consumer product,
|
||||||
|
doubtful cases shall be resolved in favor of coverage. For a particular
|
||||||
|
product received by a particular user, "normally used" refers to a
|
||||||
|
typical or common use of that class of product, regardless of the status
|
||||||
|
of the particular user or of the way in which the particular user
|
||||||
|
actually uses, or expects or is expected to use, the product. A product
|
||||||
|
is a consumer product regardless of whether the product has substantial
|
||||||
|
commercial, industrial or non-consumer uses, unless such uses represent
|
||||||
|
the only significant mode of use of the product.
|
||||||
|
|
||||||
|
"Installation Information" for a User Product means any methods,
|
||||||
|
procedures, authorization keys, or other information required to install
|
||||||
|
and execute modified versions of a covered work in that User Product from
|
||||||
|
a modified version of its Corresponding Source. The information must
|
||||||
|
suffice to ensure that the continued functioning of the modified object
|
||||||
|
code is in no case prevented or interfered with solely because
|
||||||
|
modification has been made.
|
||||||
|
|
||||||
|
If you convey an object code work under this section in, or with, or
|
||||||
|
specifically for use in, a User Product, and the conveying occurs as
|
||||||
|
part of a transaction in which the right of possession and use of the
|
||||||
|
User Product is transferred to the recipient in perpetuity or for a
|
||||||
|
fixed term (regardless of how the transaction is characterized), the
|
||||||
|
Corresponding Source conveyed under this section must be accompanied
|
||||||
|
by the Installation Information. But this requirement does not apply
|
||||||
|
if neither you nor any third party retains the ability to install
|
||||||
|
modified object code on the User Product (for example, the work has
|
||||||
|
been installed in ROM).
|
||||||
|
|
||||||
|
The requirement to provide Installation Information does not include a
|
||||||
|
requirement to continue to provide support service, warranty, or updates
|
||||||
|
for a work that has been modified or installed by the recipient, or for
|
||||||
|
the User Product in which it has been modified or installed. Access to a
|
||||||
|
network may be denied when the modification itself materially and
|
||||||
|
adversely affects the operation of the network or violates the rules and
|
||||||
|
protocols for communication across the network.
|
||||||
|
|
||||||
|
Corresponding Source conveyed, and Installation Information provided,
|
||||||
|
in accord with this section must be in a format that is publicly
|
||||||
|
documented (and with an implementation available to the public in
|
||||||
|
source code form), and must require no special password or key for
|
||||||
|
unpacking, reading or copying.
|
||||||
|
|
||||||
|
7. Additional Terms.
|
||||||
|
|
||||||
|
"Additional permissions" are terms that supplement the terms of this
|
||||||
|
License by making exceptions from one or more of its conditions.
|
||||||
|
Additional permissions that are applicable to the entire Program shall
|
||||||
|
be treated as though they were included in this License, to the extent
|
||||||
|
that they are valid under applicable law. If additional permissions
|
||||||
|
apply only to part of the Program, that part may be used separately
|
||||||
|
under those permissions, but the entire Program remains governed by
|
||||||
|
this License without regard to the additional permissions.
|
||||||
|
|
||||||
|
When you convey a copy of a covered work, you may at your option
|
||||||
|
remove any additional permissions from that copy, or from any part of
|
||||||
|
it. (Additional permissions may be written to require their own
|
||||||
|
removal in certain cases when you modify the work.) You may place
|
||||||
|
additional permissions on material, added by you to a covered work,
|
||||||
|
for which you have or can give appropriate copyright permission.
|
||||||
|
|
||||||
|
Notwithstanding any other provision of this License, for material you
|
||||||
|
add to a covered work, you may (if authorized by the copyright holders of
|
||||||
|
that material) supplement the terms of this License with terms:
|
||||||
|
|
||||||
|
a) Disclaiming warranty or limiting liability differently from the
|
||||||
|
terms of sections 15 and 16 of this License; or
|
||||||
|
|
||||||
|
b) Requiring preservation of specified reasonable legal notices or
|
||||||
|
author attributions in that material or in the Appropriate Legal
|
||||||
|
Notices displayed by works containing it; or
|
||||||
|
|
||||||
|
c) Prohibiting misrepresentation of the origin of that material, or
|
||||||
|
requiring that modified versions of such material be marked in
|
||||||
|
reasonable ways as different from the original version; or
|
||||||
|
|
||||||
|
d) Limiting the use for publicity purposes of names of licensors or
|
||||||
|
authors of the material; or
|
||||||
|
|
||||||
|
e) Declining to grant rights under trademark law for use of some
|
||||||
|
trade names, trademarks, or service marks; or
|
||||||
|
|
||||||
|
f) Requiring indemnification of licensors and authors of that
|
||||||
|
material by anyone who conveys the material (or modified versions of
|
||||||
|
it) with contractual assumptions of liability to the recipient, for
|
||||||
|
any liability that these contractual assumptions directly impose on
|
||||||
|
those licensors and authors.
|
||||||
|
|
||||||
|
All other non-permissive additional terms are considered "further
|
||||||
|
restrictions" within the meaning of section 10. If the Program as you
|
||||||
|
received it, or any part of it, contains a notice stating that it is
|
||||||
|
governed by this License along with a term that is a further
|
||||||
|
restriction, you may remove that term. If a license document contains
|
||||||
|
a further restriction but permits relicensing or conveying under this
|
||||||
|
License, you may add to a covered work material governed by the terms
|
||||||
|
of that license document, provided that the further restriction does
|
||||||
|
not survive such relicensing or conveying.
|
||||||
|
|
||||||
|
If you add terms to a covered work in accord with this section, you
|
||||||
|
must place, in the relevant source files, a statement of the
|
||||||
|
additional terms that apply to those files, or a notice indicating
|
||||||
|
where to find the applicable terms.
|
||||||
|
|
||||||
|
Additional terms, permissive or non-permissive, may be stated in the
|
||||||
|
form of a separately written license, or stated as exceptions;
|
||||||
|
the above requirements apply either way.
|
||||||
|
|
||||||
|
8. Termination.
|
||||||
|
|
||||||
|
You may not propagate or modify a covered work except as expressly
|
||||||
|
provided under this License. Any attempt otherwise to propagate or
|
||||||
|
modify it is void, and will automatically terminate your rights under
|
||||||
|
this License (including any patent licenses granted under the third
|
||||||
|
paragraph of section 11).
|
||||||
|
|
||||||
|
However, if you cease all violation of this License, then your
|
||||||
|
license from a particular copyright holder is reinstated (a)
|
||||||
|
provisionally, unless and until the copyright holder explicitly and
|
||||||
|
finally terminates your license, and (b) permanently, if the copyright
|
||||||
|
holder fails to notify you of the violation by some reasonable means
|
||||||
|
prior to 60 days after the cessation.
|
||||||
|
|
||||||
|
Moreover, your license from a particular copyright holder is
|
||||||
|
reinstated permanently if the copyright holder notifies you of the
|
||||||
|
violation by some reasonable means, this is the first time you have
|
||||||
|
received notice of violation of this License (for any work) from that
|
||||||
|
copyright holder, and you cure the violation prior to 30 days after
|
||||||
|
your receipt of the notice.
|
||||||
|
|
||||||
|
Termination of your rights under this section does not terminate the
|
||||||
|
licenses of parties who have received copies or rights from you under
|
||||||
|
this License. If your rights have been terminated and not permanently
|
||||||
|
reinstated, you do not qualify to receive new licenses for the same
|
||||||
|
material under section 10.
|
||||||
|
|
||||||
|
9. Acceptance Not Required for Having Copies.
|
||||||
|
|
||||||
|
You are not required to accept this License in order to receive or
|
||||||
|
run a copy of the Program. Ancillary propagation of a covered work
|
||||||
|
occurring solely as a consequence of using peer-to-peer transmission
|
||||||
|
to receive a copy likewise does not require acceptance. However,
|
||||||
|
nothing other than this License grants you permission to propagate or
|
||||||
|
modify any covered work. These actions infringe copyright if you do
|
||||||
|
not accept this License. Therefore, by modifying or propagating a
|
||||||
|
covered work, you indicate your acceptance of this License to do so.
|
||||||
|
|
||||||
|
10. Automatic Licensing of Downstream Recipients.
|
||||||
|
|
||||||
|
Each time you convey a covered work, the recipient automatically
|
||||||
|
receives a license from the original licensors, to run, modify and
|
||||||
|
propagate that work, subject to this License. You are not responsible
|
||||||
|
for enforcing compliance by third parties with this License.
|
||||||
|
|
||||||
|
An "entity transaction" is a transaction transferring control of an
|
||||||
|
organization, or substantially all assets of one, or subdividing an
|
||||||
|
organization, or merging organizations. If propagation of a covered
|
||||||
|
work results from an entity transaction, each party to that
|
||||||
|
transaction who receives a copy of the work also receives whatever
|
||||||
|
licenses to the work the party's predecessor in interest had or could
|
||||||
|
give under the previous paragraph, plus a right to possession of the
|
||||||
|
Corresponding Source of the work from the predecessor in interest, if
|
||||||
|
the predecessor has it or can get it with reasonable efforts.
|
||||||
|
|
||||||
|
You may not impose any further restrictions on the exercise of the
|
||||||
|
rights granted or affirmed under this License. For example, you may
|
||||||
|
not impose a license fee, royalty, or other charge for exercise of
|
||||||
|
rights granted under this License, and you may not initiate litigation
|
||||||
|
(including a cross-claim or counterclaim in a lawsuit) alleging that
|
||||||
|
any patent claim is infringed by making, using, selling, offering for
|
||||||
|
sale, or importing the Program or any portion of it.
|
||||||
|
|
||||||
|
11. Patents.
|
||||||
|
|
||||||
|
A "contributor" is a copyright holder who authorizes use under this
|
||||||
|
License of the Program or a work on which the Program is based. The
|
||||||
|
work thus licensed is called the contributor's "contributor version".
|
||||||
|
|
||||||
|
A contributor's "essential patent claims" are all patent claims
|
||||||
|
owned or controlled by the contributor, whether already acquired or
|
||||||
|
hereafter acquired, that would be infringed by some manner, permitted
|
||||||
|
by this License, of making, using, or selling its contributor version,
|
||||||
|
but do not include claims that would be infringed only as a
|
||||||
|
consequence of further modification of the contributor version. For
|
||||||
|
purposes of this definition, "control" includes the right to grant
|
||||||
|
patent sublicenses in a manner consistent with the requirements of
|
||||||
|
this License.
|
||||||
|
|
||||||
|
Each contributor grants you a non-exclusive, worldwide, royalty-free
|
||||||
|
patent license under the contributor's essential patent claims, to
|
||||||
|
make, use, sell, offer for sale, import and otherwise run, modify and
|
||||||
|
propagate the contents of its contributor version.
|
||||||
|
|
||||||
|
In the following three paragraphs, a "patent license" is any express
|
||||||
|
agreement or commitment, however denominated, not to enforce a patent
|
||||||
|
(such as an express permission to practice a patent or covenant not to
|
||||||
|
sue for patent infringement). To "grant" such a patent license to a
|
||||||
|
party means to make such an agreement or commitment not to enforce a
|
||||||
|
patent against the party.
|
||||||
|
|
||||||
|
If you convey a covered work, knowingly relying on a patent license,
|
||||||
|
and the Corresponding Source of the work is not available for anyone
|
||||||
|
to copy, free of charge and under the terms of this License, through a
|
||||||
|
publicly available network server or other readily accessible means,
|
||||||
|
then you must either (1) cause the Corresponding Source to be so
|
||||||
|
available, or (2) arrange to deprive yourself of the benefit of the
|
||||||
|
patent license for this particular work, or (3) arrange, in a manner
|
||||||
|
consistent with the requirements of this License, to extend the patent
|
||||||
|
license to downstream recipients. "Knowingly relying" means you have
|
||||||
|
actual knowledge that, but for the patent license, your conveying the
|
||||||
|
covered work in a country, or your recipient's use of the covered work
|
||||||
|
in a country, would infringe one or more identifiable patents in that
|
||||||
|
country that you have reason to believe are valid.
|
||||||
|
|
||||||
|
If, pursuant to or in connection with a single transaction or
|
||||||
|
arrangement, you convey, or propagate by procuring conveyance of, a
|
||||||
|
covered work, and grant a patent license to some of the parties
|
||||||
|
receiving the covered work authorizing them to use, propagate, modify
|
||||||
|
or convey a specific copy of the covered work, then the patent license
|
||||||
|
you grant is automatically extended to all recipients of the covered
|
||||||
|
work and works based on it.
|
||||||
|
|
||||||
|
A patent license is "discriminatory" if it does not include within
|
||||||
|
the scope of its coverage, prohibits the exercise of, or is
|
||||||
|
conditioned on the non-exercise of one or more of the rights that are
|
||||||
|
specifically granted under this License. You may not convey a covered
|
||||||
|
work if you are a party to an arrangement with a third party that is
|
||||||
|
in the business of distributing software, under which you make payment
|
||||||
|
to the third party based on the extent of your activity of conveying
|
||||||
|
the work, and under which the third party grants, to any of the
|
||||||
|
parties who would receive the covered work from you, a discriminatory
|
||||||
|
patent license (a) in connection with copies of the covered work
|
||||||
|
conveyed by you (or copies made from those copies), or (b) primarily
|
||||||
|
for and in connection with specific products or compilations that
|
||||||
|
contain the covered work, unless you entered into that arrangement,
|
||||||
|
or that patent license was granted, prior to 28 March 2007.
|
||||||
|
|
||||||
|
Nothing in this License shall be construed as excluding or limiting
|
||||||
|
any implied license or other defenses to infringement that may
|
||||||
|
otherwise be available to you under applicable patent law.
|
||||||
|
|
||||||
|
12. No Surrender of Others' Freedom.
|
||||||
|
|
||||||
|
If conditions are imposed on you (whether by court order, agreement or
|
||||||
|
otherwise) that contradict the conditions of this License, they do not
|
||||||
|
excuse you from the conditions of this License. If you cannot convey a
|
||||||
|
covered work so as to satisfy simultaneously your obligations under this
|
||||||
|
License and any other pertinent obligations, then as a consequence you may
|
||||||
|
not convey it at all. For example, if you agree to terms that obligate you
|
||||||
|
to collect a royalty for further conveying from those to whom you convey
|
||||||
|
the Program, the only way you could satisfy both those terms and this
|
||||||
|
License would be to refrain entirely from conveying the Program.
|
||||||
|
|
||||||
|
13. Use with the GNU Affero General Public License.
|
||||||
|
|
||||||
|
Notwithstanding any other provision of this License, you have
|
||||||
|
permission to link or combine any covered work with a work licensed
|
||||||
|
under version 3 of the GNU Affero General Public License into a single
|
||||||
|
combined work, and to convey the resulting work. The terms of this
|
||||||
|
License will continue to apply to the part which is the covered work,
|
||||||
|
but the special requirements of the GNU Affero General Public License,
|
||||||
|
section 13, concerning interaction through a network will apply to the
|
||||||
|
combination as such.
|
||||||
|
|
||||||
|
14. Revised Versions of this License.
|
||||||
|
|
||||||
|
The Free Software Foundation may publish revised and/or new versions of
|
||||||
|
the GNU General Public License from time to time. Such new versions will
|
||||||
|
be similar in spirit to the present version, but may differ in detail to
|
||||||
|
address new problems or concerns.
|
||||||
|
|
||||||
|
Each version is given a distinguishing version number. If the
|
||||||
|
Program specifies that a certain numbered version of the GNU General
|
||||||
|
Public License "or any later version" applies to it, you have the
|
||||||
|
option of following the terms and conditions either of that numbered
|
||||||
|
version or of any later version published by the Free Software
|
||||||
|
Foundation. If the Program does not specify a version number of the
|
||||||
|
GNU General Public License, you may choose any version ever published
|
||||||
|
by the Free Software Foundation.
|
||||||
|
|
||||||
|
If the Program specifies that a proxy can decide which future
|
||||||
|
versions of the GNU General Public License can be used, that proxy's
|
||||||
|
public statement of acceptance of a version permanently authorizes you
|
||||||
|
to choose that version for the Program.
|
||||||
|
|
||||||
|
Later license versions may give you additional or different
|
||||||
|
permissions. However, no additional obligations are imposed on any
|
||||||
|
author or copyright holder as a result of your choosing to follow a
|
||||||
|
later version.
|
||||||
|
|
||||||
|
15. Disclaimer of Warranty.
|
||||||
|
|
||||||
|
THERE IS NO WARRANTY FOR THE PROGRAM, TO THE EXTENT PERMITTED BY
|
||||||
|
APPLICABLE LAW. EXCEPT WHEN OTHERWISE STATED IN WRITING THE COPYRIGHT
|
||||||
|
HOLDERS AND/OR OTHER PARTIES PROVIDE THE PROGRAM "AS IS" WITHOUT WARRANTY
|
||||||
|
OF ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING, BUT NOT LIMITED TO,
|
||||||
|
THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
|
||||||
|
PURPOSE. THE ENTIRE RISK AS TO THE QUALITY AND PERFORMANCE OF THE PROGRAM
|
||||||
|
IS WITH YOU. SHOULD THE PROGRAM PROVE DEFECTIVE, YOU ASSUME THE COST OF
|
||||||
|
ALL NECESSARY SERVICING, REPAIR OR CORRECTION.
|
||||||
|
|
||||||
|
16. Limitation of Liability.
|
||||||
|
|
||||||
|
IN NO EVENT UNLESS REQUIRED BY APPLICABLE LAW OR AGREED TO IN WRITING
|
||||||
|
WILL ANY COPYRIGHT HOLDER, OR ANY OTHER PARTY WHO MODIFIES AND/OR CONVEYS
|
||||||
|
THE PROGRAM AS PERMITTED ABOVE, BE LIABLE TO YOU FOR DAMAGES, INCLUDING ANY
|
||||||
|
GENERAL, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES ARISING OUT OF THE
|
||||||
|
USE OR INABILITY TO USE THE PROGRAM (INCLUDING BUT NOT LIMITED TO LOSS OF
|
||||||
|
DATA OR DATA BEING RENDERED INACCURATE OR LOSSES SUSTAINED BY YOU OR THIRD
|
||||||
|
PARTIES OR A FAILURE OF THE PROGRAM TO OPERATE WITH ANY OTHER PROGRAMS),
|
||||||
|
EVEN IF SUCH HOLDER OR OTHER PARTY HAS BEEN ADVISED OF THE POSSIBILITY OF
|
||||||
|
SUCH DAMAGES.
|
||||||
|
|
||||||
|
17. Interpretation of Sections 15 and 16.
|
||||||
|
|
||||||
|
If the disclaimer of warranty and limitation of liability provided
|
||||||
|
above cannot be given local legal effect according to their terms,
|
||||||
|
reviewing courts shall apply local law that most closely approximates
|
||||||
|
an absolute waiver of all civil liability in connection with the
|
||||||
|
Program, unless a warranty or assumption of liability accompanies a
|
||||||
|
copy of the Program in return for a fee.
|
||||||
|
|
||||||
|
END OF TERMS AND CONDITIONS
|
||||||
|
|
||||||
|
How to Apply These Terms to Your New Programs
|
||||||
|
|
||||||
|
If you develop a new program, and you want it to be of the greatest
|
||||||
|
possible use to the public, the best way to achieve this is to make it
|
||||||
|
free software which everyone can redistribute and change under these terms.
|
||||||
|
|
||||||
|
To do so, attach the following notices to the program. It is safest
|
||||||
|
to attach them to the start of each source file to most effectively
|
||||||
|
state the exclusion of warranty; and each file should have at least
|
||||||
|
the "copyright" line and a pointer to where the full notice is found.
|
||||||
|
|
||||||
|
<one line to give the program's name and a brief idea of what it does.>
|
||||||
|
Copyright (C) <year> <name of author>
|
||||||
|
|
||||||
|
This program is free software: you can redistribute it and/or modify
|
||||||
|
it under the terms of the GNU General Public License as published by
|
||||||
|
the Free Software Foundation, either version 3 of the License, or
|
||||||
|
(at your option) any later version.
|
||||||
|
|
||||||
|
This program is distributed in the hope that it will be useful,
|
||||||
|
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
|
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||||
|
GNU General Public License for more details.
|
||||||
|
|
||||||
|
You should have received a copy of the GNU General Public License
|
||||||
|
along with this program. If not, see <https://www.gnu.org/licenses/>.
|
||||||
|
|
||||||
|
Also add information on how to contact you by electronic and paper mail.
|
||||||
|
|
||||||
|
If the program does terminal interaction, make it output a short
|
||||||
|
notice like this when it starts in an interactive mode:
|
||||||
|
|
||||||
|
<program> Copyright (C) <year> <name of author>
|
||||||
|
This program comes with ABSOLUTELY NO WARRANTY; for details type `show w'.
|
||||||
|
This is free software, and you are welcome to redistribute it
|
||||||
|
under certain conditions; type `show c' for details.
|
||||||
|
|
||||||
|
The hypothetical commands `show w' and `show c' should show the appropriate
|
||||||
|
parts of the General Public License. Of course, your program's commands
|
||||||
|
might be different; for a GUI interface, you would use an "about box".
|
||||||
|
|
||||||
|
You should also get your employer (if you work as a programmer) or school,
|
||||||
|
if any, to sign a "copyright disclaimer" for the program, if necessary.
|
||||||
|
For more information on this, and how to apply and follow the GNU GPL, see
|
||||||
|
<https://www.gnu.org/licenses/>.
|
||||||
|
|
||||||
|
The GNU General Public License does not permit incorporating your program
|
||||||
|
into proprietary programs. If your program is a subroutine library, you
|
||||||
|
may consider it more useful to permit linking proprietary applications with
|
||||||
|
the library. If this is what you want to do, use the GNU Lesser General
|
||||||
|
Public License instead of this License. But first, please read
|
||||||
|
<https://www.gnu.org/licenses/why-not-lgpl.html>.
|
@@ -13,7 +13,7 @@
|
|||||||
</Target>
|
</Target>
|
||||||
<ItemGroup>
|
<ItemGroup>
|
||||||
<ProjectReference Include="..\Installer\Installer.wixproj" />
|
<ProjectReference Include="..\Installer\Installer.wixproj" />
|
||||||
<PackageReference Include="WixToolset.Bal.wixext" Version="6.0.0" />
|
<PackageReference Include="WixToolset.Bal.wixext" Version="6.0.1" />
|
||||||
<PackageReference Include="WixToolset.Util.wixext" Version="6.0.0" />
|
<PackageReference Include="WixToolset.Util.wixext" Version="6.0.1" />
|
||||||
</ItemGroup>
|
</ItemGroup>
|
||||||
</Project>
|
</Project>
|
||||||
|
@@ -19,12 +19,12 @@
|
|||||||
</Target>
|
</Target>
|
||||||
|
|
||||||
<ItemGroup>
|
<ItemGroup>
|
||||||
<PackageReference Include="Microsoft.NET.Test.Sdk" Version="17.13.0" />
|
<PackageReference Include="Microsoft.NET.Test.Sdk" Version="17.14.1" />
|
||||||
<PackageReference Include="Appium.WebDriver" Version="4.4.5" />
|
<PackageReference Include="Appium.WebDriver" Version="4.4.5" />
|
||||||
<PackageReference Include="NReco.PdfRenderer" Version="1.6.0" />
|
<PackageReference Include="NReco.PdfRenderer" Version="1.6.0" />
|
||||||
<PackageReference Include="NUnit" Version="4.3.2" />
|
<PackageReference Include="NUnit" Version="4.4.0" />
|
||||||
<PackageReference Include="NUnit3TestAdapter" Version="5.0.0" />
|
<PackageReference Include="NUnit3TestAdapter" Version="5.1.0" />
|
||||||
<PackageReference Include="NUnit.Analyzers" Version="4.7.0">
|
<PackageReference Include="NUnit.Analyzers" Version="4.10.0">
|
||||||
<PrivateAssets>all</PrivateAssets>
|
<PrivateAssets>all</PrivateAssets>
|
||||||
<IncludeAssets>runtime; build; native; contentfiles; analyzers; buildtransitive</IncludeAssets>
|
<IncludeAssets>runtime; build; native; contentfiles; analyzers; buildtransitive</IncludeAssets>
|
||||||
</PackageReference>
|
</PackageReference>
|
||||||
|
Reference in New Issue
Block a user