Compare commits
51 Commits
Author | SHA1 | Date | |
---|---|---|---|
7749f6ab45 | |||
cf05a0c658 | |||
5567d9f25a | |||
4403754ada | |||
8db6007264 | |||
944270744a | |||
10ee1d6548 | |||
db4de5b5fe | |||
f69d2809f3 | |||
1c2e0baa68 | |||
39f93da0ba | |||
91717f8efb | |||
7786fb421a | |||
12d2aeecaf | |||
1bc0d67d26 | |||
38315cd928 | |||
53d3affefe | |||
4c3f0c40fa | |||
662862090e | |||
a5164e286f | |||
ae1e985656 | |||
36c1bd35a7 | |||
4aa3362029 | |||
cc97004b30 | |||
935b31f6e3 | |||
f09753ccc2 | |||
53c7cb2ec0 | |||
80c3ec1b9c | |||
b49c9c65b1 | |||
b6afb94246 | |||
8e9f2f4e90 | |||
d741ba92dc | |||
84f772a32f | |||
fd0ed97305 | |||
1141331608 | |||
f235d5b380 | |||
30116f7848 | |||
abe7699a5b | |||
bb77a4e79a | |||
46ea0f29ff | |||
4229fbbef6 | |||
8dde1cb3f4 | |||
c314321039 | |||
cf1e975d8e | |||
60359935a4 | |||
49e988f71a | |||
2a8de18772 | |||
af80e827b7 | |||
9a2fa3ee3d | |||
ba9e1d7201 | |||
49f03c0a3c |
@ -2,7 +2,7 @@ name: Test
|
|||||||
on:
|
on:
|
||||||
push:
|
push:
|
||||||
branches: ["**"]
|
branches: ["**"]
|
||||||
paths: ["Elwig/**", "Tests/**", "Installer/Files/*.exe"]
|
paths: ["Elwig/**", "Tests/**", "Installer/Files/*.exe", ".gitea/workflows/test.yaml"]
|
||||||
jobs:
|
jobs:
|
||||||
test:
|
test:
|
||||||
name: Run tests
|
name: Run tests
|
||||||
@ -10,6 +10,19 @@ jobs:
|
|||||||
steps:
|
steps:
|
||||||
- name: Checkout repository
|
- name: Checkout repository
|
||||||
uses: actions/checkout@v4
|
uses: actions/checkout@v4
|
||||||
|
- name: Check for Byte order marks
|
||||||
|
shell: powershell
|
||||||
|
run: |
|
||||||
|
$pattern = [char]::ConvertFromUtf32(0xFEFF)
|
||||||
|
$files = git grep -IEl "^$pattern"
|
||||||
|
if ( $lastexitcode -ne 1 ) {
|
||||||
|
echo "Files with BOM found:"
|
||||||
|
echo $files
|
||||||
|
exit 1
|
||||||
|
} else {
|
||||||
|
echo "No files with BOM found"
|
||||||
|
exit 0
|
||||||
|
}
|
||||||
- name: Setup MSBuild
|
- name: Setup MSBuild
|
||||||
uses: microsoft/setup-msbuild@v1.1
|
uses: microsoft/setup-msbuild@v1.1
|
||||||
- name: Setup NuGet
|
- name: Setup NuGet
|
||||||
|
107
CHANGELOG.md
107
CHANGELOG.md
@ -3,6 +3,113 @@ Changelog
|
|||||||
=========
|
=========
|
||||||
|
|
||||||
|
|
||||||
|
[v0.9.3][v0.9.3] (2024-08-02) {#v0.9.3}
|
||||||
|
---------------------------------------
|
||||||
|
|
||||||
|
### Sonstiges {#v0.9.3-misc}
|
||||||
|
|
||||||
|
* Das Lieferjournal als Excel-Liste beinhaltet nun auch Liefer-Zweigstelle und Stamm-Zweigstelle des Liefernaten. (cf05a0c658)
|
||||||
|
|
||||||
|
[v0.9.3]: https://git.necronda.net/winzer/elwig/releases/tag/v0.9.3
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
[v0.9.2][v0.9.2] (2024-08-01) {#v0.9.2}
|
||||||
|
---------------------------------------
|
||||||
|
|
||||||
|
### Behobene Fehler {#v0.9.2-bugfixes}
|
||||||
|
|
||||||
|
* Verhalten beim Schließen des Haupt-Fensters (`MainWindow`) nicht immer richtig. (8db6007264)
|
||||||
|
* Im Mitglieder-Fenster (`MemberAdminWindow`) führt beim Erstellen eines Mitglied das Eingeben einer Tel.-Nr. zu einem Fehler. (4403754ada)
|
||||||
|
|
||||||
|
[v0.9.2]: https://git.necronda.net/winzer/elwig/releases/tag/v0.9.2
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
[v0.9.1][v0.9.1] (2024-08-01) {#v0.9.1}
|
||||||
|
---------------------------------------
|
||||||
|
|
||||||
|
### Neue Funktionen {#v0.9.1-features}
|
||||||
|
|
||||||
|
* Im Rundschreiben-Fenster (`MailWindow`) können E-Mails ohne Anhänge verschickt werden. (f69d2809f3)
|
||||||
|
* Im Mitglieder-Fenster (`MemberAdminWindow`) und Lieferungen-Fenster (`DeliveryAdminWindow`) kann das/die momentan ausgewählte Mitglied/Lieferung alleine exportiert werden. (db4de5b5fe)
|
||||||
|
* Exporte für Mitglieder enthalten nun auch deren Flächenbindungen. (10ee1d6548)
|
||||||
|
|
||||||
|
### Behobene Fehler {#v0.9.1-bugfixes}
|
||||||
|
|
||||||
|
* Sortierung der Wiegen-Knöpfe im Übernahme-Fenster (`DeliveryAdminWindow`). (7786fb421a)
|
||||||
|
|
||||||
|
### Sonstiges {#v0.9.1-misc}
|
||||||
|
|
||||||
|
* Deutsche Fehlermeldung beim Hochladen/Herunterladen im Haupt-Fenster (`MainWindow`). (91717f8efb)
|
||||||
|
* Waagen-Fehler _Brutto negativ_ implementiert. (39f93da0ba)
|
||||||
|
|
||||||
|
[v0.9.1]: https://git.necronda.net/winzer/elwig/releases/tag/v0.9.1
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
[v0.9.0][v0.9.0] (2024-07-28) {#v0.9.0}
|
||||||
|
---------------------------------------
|
||||||
|
|
||||||
|
### Neue Funktionen {#v0.9.0-features}
|
||||||
|
|
||||||
|
* Flächenbindungen werden als Tabelle in der Status-Leiste im Mitglieder-Fenster (`MemberAdminWindow`) angezeigt. ([#26][i26])
|
||||||
|
* Filter für E-Mail-Adressen, Tel.-Nr. und Kontaktarten im Mitglieder-Fenster (`MemberAdminWindow`). (1141331608)
|
||||||
|
* Auf Lieferscheinen (`DeliveryNote`) werden nun _Brutto, Tara, Netto_ werte abgedruckt. (fd0ed97305, 4aa3362029, 53d3affefe)
|
||||||
|
* Beim Exportieren der Mitgliederliste werden auch Tel.-Nr. und E-Mail-Adressen exportiert. (b6afb94246)
|
||||||
|
* Benutzerfreundliches Synchronisieren zwischen Standorten. ([#3][i3])
|
||||||
|
* Übernehmer _müssen_ explizit entscheiden, ob _gerebelt gewogen_ oder nicht. (935b31f6e3)
|
||||||
|
|
||||||
|
### Behobene Fehler {#v0.9.0-bugfixes}
|
||||||
|
|
||||||
|
* Zu-/Abschläge im Lieferungen-Fenster (`DeliveryAdminWindow`). (f235d5b380)
|
||||||
|
* Falls keine Saison existierte führte das zu einem Absturz im Rundschreiben-Fenster (`MailWindow`). (84f772a32f)
|
||||||
|
* Beim Drucken _sollte_ kein Kommandozeilen-Fenster mehr sichtbar sein. (d741ba92dc)
|
||||||
|
* Wenn bei einem Mitglied keine Stamm-KG hinterlegt war, kam es zu inkonsistentem Verhalten im Übernahme-Fenster (`DeliveryAdminWinodw`). (4c3f0c40fa)
|
||||||
|
|
||||||
|
### Sonstiges {#v0.9.0-misc}
|
||||||
|
|
||||||
|
* Model-View-ViewModel (MVVM) implementiert! ([#10][i10])
|
||||||
|
* Die nächste Saison "beginnt" bereits im Juli (statt erst im August) (`CurrentLastSeason`). (c314321039)
|
||||||
|
* Automatisierte Tests für Waagen (Sitzendorf, Haugsdorf). (8e9f2f4e90)
|
||||||
|
* Überprüfung auf Byte-Order-Marks in allen Quellcode-Dateien. (53c7cb2ec0, f09753ccc2)
|
||||||
|
|
||||||
|
[v0.9.0]: https://git.necronda.net/winzer/elwig/releases/tag/v0.9.0
|
||||||
|
[i3]: https://git.necronda.net/winzer/elwig/issues/3
|
||||||
|
[i10]: https://git.necronda.net/winzer/elwig/issues/10
|
||||||
|
[i26]: https://git.necronda.net/winzer/elwig/issues/26
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
[v0.8.9][v0.8.9] (2024-07-23) {#v0.8.9}
|
||||||
|
---------------------------------------
|
||||||
|
|
||||||
|
### Behobene Fehler {#v0.8.9-bugfixes}
|
||||||
|
|
||||||
|
* Absturz im Rundschreiben-Fenster (`MailWindow`). Fehler bei `CheckComboBox`. (49f03c0a3c)
|
||||||
|
* Excel-Exporte können nun auch Sonderzeichen (wie `&`) enthalten. (ba9e1d7201)
|
||||||
|
|
||||||
|
[v0.8.9]: https://git.necronda.net/winzer/elwig/releases/tag/v0.8.9
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
[v0.8.8][v0.8.8] (2024-07-22) {#v0.8.8}
|
||||||
|
---------------------------------------
|
||||||
|
|
||||||
|
### Behobene Fehler {#v0.8.8-bugfixes}
|
||||||
|
|
||||||
|
* Schnittstelle für Gassner-Waagen nicht funktionsfähig. (4c75dbe4aa)
|
||||||
|
|
||||||
|
[v0.8.8]: https://git.necronda.net/winzer/elwig/releases/tag/v0.8.8
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
[v0.8.7][v0.8.7] (2024-07-22) {#v0.8.7}
|
[v0.8.7][v0.8.7] (2024-07-22) {#v0.8.7}
|
||||||
---------------------------------------
|
---------------------------------------
|
||||||
|
|
||||||
|
@ -29,10 +29,11 @@ namespace Elwig {
|
|||||||
private readonly DispatcherTimer _autoUpdateTimer = new() { Interval = TimeSpan.FromHours(1) };
|
private readonly DispatcherTimer _autoUpdateTimer = new() { Interval = TimeSpan.FromHours(1) };
|
||||||
|
|
||||||
public static readonly string DataPath = @"C:\ProgramData\Elwig\";
|
public static readonly string DataPath = @"C:\ProgramData\Elwig\";
|
||||||
|
public static readonly string ConfigPath = Path.Combine(DataPath, "config.ini");
|
||||||
public static readonly string ExePath = @"C:\Program Files\Elwig\";
|
public static readonly string ExePath = @"C:\Program Files\Elwig\";
|
||||||
public static readonly string TempPath = Path.Combine(Path.GetTempPath(), "Elwig");
|
public static readonly string TempPath = Path.Combine(Path.GetTempPath(), "Elwig");
|
||||||
|
|
||||||
public static Config Config { get; private set; } = new(Path.Combine(DataPath, "config.ini"));
|
public static Config Config { get; private set; } = new(ConfigPath);
|
||||||
public static int VersionMajor { get; private set; }
|
public static int VersionMajor { get; private set; }
|
||||||
public static int VersionMinor { get; private set; }
|
public static int VersionMinor { get; private set; }
|
||||||
public static int VersionPatch { get; private set; }
|
public static int VersionPatch { get; private set; }
|
||||||
@ -264,15 +265,15 @@ namespace Elwig {
|
|||||||
}
|
}
|
||||||
|
|
||||||
public static DeliveryAdminWindow FocusReceipt() {
|
public static DeliveryAdminWindow FocusReceipt() {
|
||||||
return FocusWindow<DeliveryAdminWindow>(() => new(true), w => w.IsReceipt);
|
return FocusWindow<DeliveryAdminWindow>(() => new(true), w => w.ViewModel.IsReceipt);
|
||||||
}
|
}
|
||||||
|
|
||||||
public static DeliveryAdminWindow FocusMemberDeliveries(int mgnr) {
|
public static DeliveryAdminWindow FocusMemberDeliveries(int mgnr) {
|
||||||
return FocusWindow<DeliveryAdminWindow>(() => new(mgnr), w => w.MgNr == mgnr);
|
return FocusWindow<DeliveryAdminWindow>(() => new(mgnr), w => w.ViewModel.FilterMember?.MgNr == mgnr);
|
||||||
}
|
}
|
||||||
|
|
||||||
public static AreaComAdminWindow FocusMemberAreaComs(int mgnr) {
|
public static AreaComAdminWindow FocusMemberAreaComs(int mgnr) {
|
||||||
return FocusWindow<AreaComAdminWindow>(() => new(mgnr), w => w.MgNr == mgnr);
|
return FocusWindow<AreaComAdminWindow>(() => new(mgnr), w => w.ViewModel.FilterMember.MgNr == mgnr);
|
||||||
}
|
}
|
||||||
|
|
||||||
public static BaseDataWindow FocusBaseData() {
|
public static BaseDataWindow FocusBaseData() {
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
using System.Collections;
|
using System.Collections;
|
||||||
using System.Collections.ObjectModel;
|
using System.Collections.ObjectModel;
|
||||||
using System.Collections.Specialized;
|
using System.Collections.Specialized;
|
||||||
using System.Linq;
|
using System.Linq;
|
||||||
@ -8,7 +8,7 @@ using System.Windows.Controls;
|
|||||||
namespace Elwig.Controls {
|
namespace Elwig.Controls {
|
||||||
public class CheckComboBox : ListBox {
|
public class CheckComboBox : ListBox {
|
||||||
|
|
||||||
public new static readonly DependencyProperty SelectedItemsProperty = DependencyProperty.Register(nameof(SelectedItems), typeof(IList), typeof(CheckComboBox), new FrameworkPropertyMetadata(new ObservableCollection<object>(), FrameworkPropertyMetadataOptions.BindsTwoWayByDefault, OnSelectedItemsChangedCallback));
|
public new static readonly DependencyProperty SelectedItemsProperty = DependencyProperty.Register(nameof(SelectedItems), typeof(IList), typeof(CheckComboBox), new FrameworkPropertyMetadata(null, FrameworkPropertyMetadataOptions.BindsTwoWayByDefault, OnSelectedItemsChangedCallback));
|
||||||
public new IList SelectedItems {
|
public new IList SelectedItems {
|
||||||
get => (IList)GetValue(SelectedItemsProperty);
|
get => (IList)GetValue(SelectedItemsProperty);
|
||||||
set => SetValue(SelectedItemsProperty, value);
|
set => SetValue(SelectedItemsProperty, value);
|
||||||
@ -72,6 +72,7 @@ namespace Elwig.Controls {
|
|||||||
|
|
||||||
public CheckComboBox() {
|
public CheckComboBox() {
|
||||||
SelectionMode = SelectionMode.Multiple;
|
SelectionMode = SelectionMode.Multiple;
|
||||||
|
SelectedItems = new ObservableCollection<object>();
|
||||||
}
|
}
|
||||||
|
|
||||||
public override void OnApplyTemplate() {
|
public override void OnApplyTemplate() {
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
using System;
|
using System;
|
||||||
using System.Linq;
|
using System.Linq;
|
||||||
using System.Windows;
|
using System.Windows;
|
||||||
using System.Windows.Controls;
|
using System.Windows.Controls;
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
using System;
|
using System;
|
||||||
using System.Globalization;
|
using System.Globalization;
|
||||||
using System.Windows;
|
using System.Windows;
|
||||||
using System.Windows.Data;
|
using System.Windows.Data;
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
using System.Windows;
|
using System.Windows;
|
||||||
using System.Windows.Controls;
|
using System.Windows.Controls;
|
||||||
|
|
||||||
namespace Elwig.Controls {
|
namespace Elwig.Controls {
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
<ResourceDictionary xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
|
<ResourceDictionary 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:ctrl="clr-namespace:Elwig.Controls">
|
xmlns:ctrl="clr-namespace:Elwig.Controls">
|
||||||
<Style TargetType="ctrl:UnitTextBox" BasedOn="{StaticResource {x:Type TextBox}}">
|
<Style TargetType="ctrl:UnitTextBox" BasedOn="{StaticResource {x:Type TextBox}}">
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
using System;
|
using System;
|
||||||
using System.Windows;
|
using System.Windows;
|
||||||
using System.Windows.Data;
|
using System.Windows.Data;
|
||||||
using System.Globalization;
|
using System.Globalization;
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
using System;
|
using System;
|
||||||
using System.Windows;
|
using System.Windows;
|
||||||
using System.Windows.Data;
|
using System.Windows.Data;
|
||||||
using System.Globalization;
|
using System.Globalization;
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
using System.Windows.Controls;
|
using System.Windows.Controls;
|
||||||
using System.Windows;
|
using System.Windows;
|
||||||
|
|
||||||
namespace Elwig.Controls {
|
namespace Elwig.Controls {
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
using System.Windows.Controls;
|
using System.Windows.Controls;
|
||||||
using System.Windows;
|
using System.Windows;
|
||||||
|
|
||||||
namespace Elwig.Controls {
|
namespace Elwig.Controls {
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
using System.Windows.Controls;
|
using System.Windows.Controls;
|
||||||
using System.Windows;
|
using System.Windows;
|
||||||
|
|
||||||
namespace Elwig.Controls {
|
namespace Elwig.Controls {
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
<Window x:Class="Elwig.Dialogs.AreaComDialog"
|
<Window x:Class="Elwig.Dialogs.AreaComDialog"
|
||||||
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"
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
using Elwig.Helpers;
|
using Elwig.Helpers;
|
||||||
using System.Windows;
|
using System.Windows;
|
||||||
using System.Windows.Controls;
|
using System.Windows.Controls;
|
||||||
|
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
<Window x:Class="Elwig.Dialogs.DeleteMemberDialog"
|
<Window x:Class="Elwig.Dialogs.DeleteMemberDialog"
|
||||||
AutomationProperties.AutomationId="DeleteMemberDialog"
|
AutomationProperties.AutomationId="DeleteMemberDialog"
|
||||||
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"
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
using Elwig.Helpers;
|
using Elwig.Helpers;
|
||||||
using System.Linq;
|
using System.Linq;
|
||||||
using System.Windows;
|
using System.Windows;
|
||||||
using System.Windows.Controls;
|
using System.Windows.Controls;
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
<Window x:Class="Elwig.Dialogs.NewSeasonDialog"
|
<Window x:Class="Elwig.Dialogs.NewSeasonDialog"
|
||||||
AutomationProperties.AutomationId="NewSeasonDialog"
|
AutomationProperties.AutomationId="NewSeasonDialog"
|
||||||
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"
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
using Elwig.Helpers;
|
using Elwig.Helpers;
|
||||||
using Elwig.Models.Entities;
|
using Elwig.Models.Entities;
|
||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
using System.Windows;
|
using System.Windows;
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
<Window x:Class="Elwig.Dialogs.UpdateDialog"
|
<Window x:Class="Elwig.Dialogs.UpdateDialog"
|
||||||
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"
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
using Elwig.Helpers;
|
using Elwig.Helpers;
|
||||||
using System;
|
using System;
|
||||||
using System.Diagnostics;
|
using System.Diagnostics;
|
||||||
using System.IO;
|
using System.IO;
|
||||||
|
@ -33,9 +33,9 @@
|
|||||||
<th>Gewicht</th>
|
<th>Gewicht</th>
|
||||||
<th rowspan="3" style="padding: 0;">
|
<th rowspan="3" style="padding: 0;">
|
||||||
<svg width="10" height="40" xmlns="http://www.w3.org/2000/svg">
|
<svg width="10" height="40" xmlns="http://www.w3.org/2000/svg">
|
||||||
<text x="-40" y="5" transform="rotate(270)" font-size="8pt" font-style="italic" font-family="Times New Roman"
|
<text x="-40" y="4" transform="rotate(270)" font-size="8pt" font-style="italic" font-family="Times New Roman"
|
||||||
style="text-anchor: start; alignment-baseline: middle;">
|
style="text-anchor: start; alignment-baseline: middle;">
|
||||||
bto./nto.
|
gerebelt
|
||||||
</text>
|
</text>
|
||||||
</svg>
|
</svg>
|
||||||
</th>
|
</th>
|
||||||
@ -81,7 +81,7 @@
|
|||||||
}
|
}
|
||||||
@if (i == p.Buckets.Length - 1) {
|
@if (i == p.Buckets.Length - 1) {
|
||||||
<td class="number">@($"{p.Weight:N0}")</td>
|
<td class="number">@($"{p.Weight:N0}")</td>
|
||||||
<td class="small">@(p.IsNetWeight ? "n" : "b")</td>
|
<td style="font-size: 7pt;">@(p.IsNetWeight ? "\u2611" : "\u2610")</td>
|
||||||
} else {
|
} else {
|
||||||
<td></td>
|
<td></td>
|
||||||
<td></td>
|
<td></td>
|
||||||
|
@ -60,8 +60,18 @@
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
<tr><td></td><td colspan="5">
|
<tr><td></td><td colspan="5">
|
||||||
@Raw(part.IsManualWeighing ? "<i>Handwiegung</i>" : $"<i>Waage:</i> {part.ScaleId ?? "?"}, <i>ID:</i> {part.WeighingId ?? "?"}")
|
@if (part.IsManualWeighing) {
|
||||||
(@(part.IsNetWeight ? "netto/gerebelt gewogen" : "brutto/nicht gerebelt gewogen"))@Raw(part.WeighingReason != null ? $", <i>Begründung:</i>" : "") @part.WeighingReason
|
<i>Handwiegung @(part.IsNetWeight ? " (gerebelt gewogen)" : " (nicht gerebelt gewogen)")</i>@Raw(part.WeighingReason != null ? ", <i>Begründung:</i> " : "") @part.WeighingReason
|
||||||
|
} else {
|
||||||
|
var info = part.WeighingInfo;
|
||||||
|
<i>Waage:</i> @(part.ScaleId ?? "?")@(", ") <i>ID:</i> @(info.Id ?? "?")
|
||||||
|
@(info.Date != null || info.Time != null ? " – " : "")@(info.Time != null ? $"{info.Time:HH:mm}" : "")@(info.Date != null ? $", {info.Date:dd.MM.yyyy}" : "")
|
||||||
|
@if (info.Gross != null && info.Tare != null && info.Net != null) {
|
||||||
|
<br/><i>Brutto:</i> @($"{info.Gross:N0} kg")@(" – ") <i>Tara:</i> @($"{info.Tare:N0} kg")@(" – ") <i>Netto:</i> @($"{info.Net:N0} kg")@(" – ")@Raw(part.IsNetWeight ? "<i>gerebelt gewogen</i>" : "<i>nicht gerebelt gewogen</i>")
|
||||||
|
} else {
|
||||||
|
@Raw($" <i>({(part.IsNetWeight ? "gerebelt gewogen" : "nicht gerebelt gewogen")})</i>")
|
||||||
|
}
|
||||||
|
}
|
||||||
</td></tr>
|
</td></tr>
|
||||||
@if (part.Comment != null) {
|
@if (part.Comment != null) {
|
||||||
<tr><td></td><td colspan="5"><i>Anmerkung:</i> @part.Comment</td></tr>
|
<tr><td></td><td colspan="5"><i>Anmerkung:</i> @part.Comment</td></tr>
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
using Elwig.Helpers;
|
using Elwig.Helpers;
|
||||||
using Elwig.Models.Entities;
|
using Elwig.Models.Entities;
|
||||||
using System;
|
using System;
|
||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
@using RazorLight
|
@using RazorLight
|
||||||
@using Elwig.Helpers
|
@using Elwig.Helpers
|
||||||
@inherits TemplatePage<Elwig.Documents.MemberDataSheet>
|
@inherits TemplatePage<Elwig.Documents.MemberDataSheet>
|
||||||
@model Elwig.Documents.MemberDataSheet
|
@model Elwig.Documents.MemberDataSheet
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
|
|
||||||
h2 {
|
h2 {
|
||||||
margin-bottom: 0.5em !important;
|
margin-bottom: 0.5em !important;
|
||||||
}
|
}
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
using Elwig.Models.Dtos;
|
using Elwig.Models.Dtos;
|
||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
|
|
||||||
namespace Elwig.Documents {
|
namespace Elwig.Documents {
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
using Elwig.Helpers;
|
using Elwig.Helpers;
|
||||||
using Elwig.Helpers.Billing;
|
using Elwig.Helpers.Billing;
|
||||||
using Elwig.Models.Dtos;
|
using Elwig.Models.Dtos;
|
||||||
using Elwig.Models.Entities;
|
using Elwig.Models.Entities;
|
||||||
|
@ -49,7 +49,7 @@
|
|||||||
<td class="center">@(Model.BillingData.ConsiderContractPenalties ? "Ja" : "Nein")</td>
|
<td class="center">@(Model.BillingData.ConsiderContractPenalties ? "Ja" : "Nein")</td>
|
||||||
</tr>
|
</tr>
|
||||||
<tr>
|
<tr>
|
||||||
<th style="overflow: visible;">Nto./bto.-Zuschl:</th>
|
<th style="overflow: visible;">Rebel-Zuschl.:</th>
|
||||||
<td colspan="3" class="center">
|
<td colspan="3" class="center">
|
||||||
@($"{Utils.GetSign(Model.BillingData.NetWeightModifier)}{Math.Abs(Model.BillingData.NetWeightModifier) * 100:N2}") % /
|
@($"{Utils.GetSign(Model.BillingData.NetWeightModifier)}{Math.Abs(Model.BillingData.NetWeightModifier) * 100:N2}") % /
|
||||||
@($"{Utils.GetSign(Model.BillingData.GrossWeightModifier)}{Math.Abs(Model.BillingData.GrossWeightModifier) * 100:N2}") %
|
@($"{Utils.GetSign(Model.BillingData.GrossWeightModifier)}{Math.Abs(Model.BillingData.GrossWeightModifier) * 100:N2}") %
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
using Elwig.Models.Dtos;
|
using Elwig.Models.Dtos;
|
||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
|
|
||||||
namespace Elwig.Documents {
|
namespace Elwig.Documents {
|
||||||
|
@ -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.8.8</Version>
|
<Version>0.9.3</Version>
|
||||||
<SatelliteResourceLanguages>de-AT</SatelliteResourceLanguages>
|
<SatelliteResourceLanguages>de-AT</SatelliteResourceLanguages>
|
||||||
<AllowUnsafeBlocks>true</AllowUnsafeBlocks>
|
<AllowUnsafeBlocks>true</AllowUnsafeBlocks>
|
||||||
<ApplicationManifest>app.manifest</ApplicationManifest>
|
<ApplicationManifest>app.manifest</ApplicationManifest>
|
||||||
@ -25,6 +25,7 @@
|
|||||||
</Target>
|
</Target>
|
||||||
|
|
||||||
<ItemGroup>
|
<ItemGroup>
|
||||||
|
<PackageReference Include="CommunityToolkit.Mvvm" Version="8.2.2" />
|
||||||
<PackageReference Include="LinqKit" Version="1.3.0" />
|
<PackageReference Include="LinqKit" Version="1.3.0" />
|
||||||
<PackageReference Include="MailKit" Version="4.7.1.1" />
|
<PackageReference Include="MailKit" Version="4.7.1.1" />
|
||||||
<PackageReference Include="Microsoft.AspNetCore.Razor.Language" Version="6.0.32" />
|
<PackageReference Include="Microsoft.AspNetCore.Razor.Language" Version="6.0.32" />
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
using System;
|
using System;
|
||||||
using System.Windows.Input;
|
using System.Windows.Input;
|
||||||
|
|
||||||
namespace Elwig.Helpers {
|
namespace Elwig.Helpers {
|
||||||
|
@ -9,7 +9,7 @@ namespace Elwig.Helpers {
|
|||||||
public static class AppDbUpdater {
|
public static class AppDbUpdater {
|
||||||
|
|
||||||
// Don't forget to update value in Tests/fetch-resources.bat!
|
// Don't forget to update value in Tests/fetch-resources.bat!
|
||||||
public static readonly int RequiredSchemaVersion = 24;
|
public static readonly int RequiredSchemaVersion = 25;
|
||||||
|
|
||||||
private static int VersionOffset = 0;
|
private static int VersionOffset = 0;
|
||||||
|
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
using Newtonsoft.Json;
|
using Newtonsoft.Json;
|
||||||
using NJsonSchema;
|
using NJsonSchema;
|
||||||
using System;
|
using System;
|
||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
using Elwig.Models.Entities;
|
using Elwig.Models.Entities;
|
||||||
using System;
|
using System;
|
||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
using System.Linq;
|
using System.Linq;
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
using System;
|
using System;
|
||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
using System.Linq;
|
using System.Linq;
|
||||||
|
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
using System;
|
using System;
|
||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
using System.Linq;
|
using System.Linq;
|
||||||
using System.Text.Json.Nodes;
|
using System.Text.Json.Nodes;
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
using Elwig.Models.Entities;
|
using Elwig.Models.Entities;
|
||||||
using Microsoft.EntityFrameworkCore;
|
using Microsoft.EntityFrameworkCore;
|
||||||
using System;
|
using System;
|
||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
|
@ -87,7 +87,7 @@ namespace Elwig.Helpers {
|
|||||||
SmtpPassword = config["smtp:password"];
|
SmtpPassword = config["smtp:password"];
|
||||||
SmtpFrom = config["smtp:from"];
|
SmtpFrom = config["smtp:from"];
|
||||||
|
|
||||||
var scales = config.AsEnumerable().Where(i => i.Key.StartsWith("scale.")).GroupBy(i => i.Key.Split(':')[0][6..]).Select(i => i.Key);
|
var scales = config.AsEnumerable().Where(i => i.Key.StartsWith("scale.")).GroupBy(i => i.Key.Split(':')[0][6..]).Select(i => i.Key).Order();
|
||||||
ScaleList.Clear();
|
ScaleList.Clear();
|
||||||
Scales = ScaleList;
|
Scales = ScaleList;
|
||||||
foreach (var s in scales) {
|
foreach (var s in scales) {
|
||||||
|
@ -11,11 +11,7 @@ using Brushes = System.Windows.Media.Brushes;
|
|||||||
namespace Elwig.Helpers {
|
namespace Elwig.Helpers {
|
||||||
public class ControlUtils {
|
public class ControlUtils {
|
||||||
|
|
||||||
public enum RenewSourceDefault {
|
public enum RenewSourceDefault { None, IfOnly, First }
|
||||||
None,
|
|
||||||
IfOnly,
|
|
||||||
First
|
|
||||||
}
|
|
||||||
|
|
||||||
private static void SetControlBorderBrush(Control input, Brush brush) {
|
private static void SetControlBorderBrush(Control input, Brush brush) {
|
||||||
if (input is ComboBox cb) {
|
if (input is ComboBox cb) {
|
||||||
@ -171,15 +167,19 @@ namespace Elwig.Helpers {
|
|||||||
return item;
|
return item;
|
||||||
}
|
}
|
||||||
|
|
||||||
public static object? GetItemFromSource(IEnumerable source, object? item) {
|
public static T? GetItemFromSource<T>(IEnumerable source, T? item) {
|
||||||
return GetItemFromSource(source, Utils.GetEntityIdentifier(item));
|
return (T?)GetItemFromSource(source, Utils.GetEntityIdentifier(item));
|
||||||
|
}
|
||||||
|
|
||||||
|
public static object? GetItemFromSourceWithPk(IEnumerable source, params object?[] primaryKey) {
|
||||||
|
return GetItemFromSource(source, (int?)Utils.GetEntityIdetifierForPk(primaryKey));
|
||||||
}
|
}
|
||||||
|
|
||||||
public static void SelectItemWithHash(Selector input, int? hash) {
|
public static void SelectItemWithHash(Selector input, int? hash) {
|
||||||
if (hash == null) {
|
if (hash == null) {
|
||||||
input.SelectedItem = null;
|
input.SelectedItem = null;
|
||||||
} else {
|
} else {
|
||||||
input.SelectedItem = GetItemFromSource(input.ItemsSource, (int)hash);
|
input.SelectedItem = GetItemFromSource(input.ItemsSource, hash);
|
||||||
}
|
}
|
||||||
if (input is ListBox lb && lb.SelectedItem is object lbItem) {
|
if (input is ListBox lb && lb.SelectedItem is object lbItem) {
|
||||||
lb.ScrollIntoView(lbItem);
|
lb.ScrollIntoView(lbItem);
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
using System.IO.Compression;
|
using System.IO.Compression;
|
||||||
using System.IO;
|
using System.IO;
|
||||||
using System.Threading.Tasks;
|
using System.Threading.Tasks;
|
||||||
using Elwig.Models.Entities;
|
using Elwig.Models.Entities;
|
||||||
@ -8,12 +8,17 @@ using System.Text.Json.Nodes;
|
|||||||
using System.Linq;
|
using System.Linq;
|
||||||
using System.Windows;
|
using System.Windows;
|
||||||
using Microsoft.EntityFrameworkCore;
|
using Microsoft.EntityFrameworkCore;
|
||||||
|
using System.Text.Json;
|
||||||
|
|
||||||
namespace Elwig.Helpers.Export {
|
namespace Elwig.Helpers.Export {
|
||||||
public static class ElwigData {
|
public static class ElwigData {
|
||||||
|
|
||||||
|
public enum ImportMode { Auto, Interactively, FromBranches }
|
||||||
|
|
||||||
public static readonly string ImportedTxt = Path.Combine(App.DataPath, "imported.txt");
|
public static readonly string ImportedTxt = Path.Combine(App.DataPath, "imported.txt");
|
||||||
|
|
||||||
|
private static readonly JsonSerializerOptions JsonOpts = new() { Encoder = System.Text.Encodings.Web.JavaScriptEncoder.UnsafeRelaxedJsonEscaping };
|
||||||
|
|
||||||
public static async Task<string[]> GetImportedFiles() {
|
public static async Task<string[]> GetImportedFiles() {
|
||||||
try {
|
try {
|
||||||
return await File.ReadAllLinesAsync(ImportedTxt, Utils.UTF8);
|
return await File.ReadAllLinesAsync(ImportedTxt, Utils.UTF8);
|
||||||
@ -22,40 +27,73 @@ namespace Elwig.Helpers.Export {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public static async Task AddImportedFiles(IEnumerable<string> filenames) {
|
public static async Task AddImportedFiles(params string[] filenames) {
|
||||||
await File.AppendAllLinesAsync(ImportedTxt, filenames, Utils.UTF8);
|
await File.AppendAllLinesAsync(ImportedTxt, filenames, Utils.UTF8);
|
||||||
}
|
}
|
||||||
|
|
||||||
public static Task Import(string filename, bool interactive) => Import([filename], interactive);
|
public static Task Import(string filename, ImportMode mode) => Import([filename], mode);
|
||||||
|
|
||||||
public static async Task Import(IEnumerable<string> filenames, bool interactive) {
|
public static async Task Import(IEnumerable<string> filenames, ImportMode mode) {
|
||||||
try {
|
try {
|
||||||
using var ctx = new AppDbContext();
|
Dictionary<string, Branch> branches;
|
||||||
var currentDids = await ctx.Deliveries
|
Dictionary<int, int> currentDids;
|
||||||
.GroupBy(d => d.Year)
|
Dictionary<string, int> currentLsNrs;
|
||||||
.ToDictionaryAsync(g => g.Key, g => g.Max(d => d.DId));
|
Dictionary<int, List<WbRd>> currentWbRde;
|
||||||
|
|
||||||
var deliveries = new List<Delivery>();
|
using (var ctx = new AppDbContext()) {
|
||||||
var deliveryParts = new List<DeliveryPart>();
|
branches = await ctx.Branches.ToDictionaryAsync(b => b.ZwstId);
|
||||||
var modifiers = new List<DeliveryPartModifier>();
|
currentDids = await ctx.Deliveries
|
||||||
|
.GroupBy(d => d.Year)
|
||||||
|
.ToDictionaryAsync(g => g.Key, g => g.Max(d => d.DId));
|
||||||
|
currentLsNrs = await ctx.Deliveries
|
||||||
|
.ToDictionaryAsync(d => d.LsNr, d => d.DId);
|
||||||
|
currentWbRde = await ctx.WbRde
|
||||||
|
.GroupBy(r => r.KgNr)
|
||||||
|
.ToDictionaryAsync(g => g.Key, g => g.ToList());
|
||||||
|
}
|
||||||
|
|
||||||
var metaData = new List<(string Name, int DeliveryNum, string Filters)>();
|
var data = new List<(
|
||||||
|
List<Member> Members,
|
||||||
|
List<BillingAddr> BillingAddresses,
|
||||||
|
List<MemberTelNr> TelephoneNumbers,
|
||||||
|
List<MemberEmailAddr> EmailAddresses,
|
||||||
|
List<AreaCom> AreaCommitments,
|
||||||
|
List<WbRd> Riede,
|
||||||
|
List<Delivery> Deliveries,
|
||||||
|
List<DeliveryPart> DeliveryParts,
|
||||||
|
List<DeliveryPartModifier> Modifiers)>();
|
||||||
|
|
||||||
|
var metaData = new List<(string FileName, string ZwstId, string Device,
|
||||||
|
int? MemberNum, string? MemberFilters,
|
||||||
|
int? AreaComNum, string? AreaComFilters,
|
||||||
|
int? DeliveryNum, string? DeliveryFilters)>();
|
||||||
|
|
||||||
foreach (var filename in filenames) {
|
foreach (var filename in filenames) {
|
||||||
|
// TODO read encrypted files
|
||||||
using var zip = ZipFile.Open(filename, ZipArchiveMode.Read);
|
using var zip = ZipFile.Open(filename, ZipArchiveMode.Read);
|
||||||
|
|
||||||
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)) {
|
||||||
if (await reader.ReadToEndAsync() != "elwig:1")
|
if (await reader.ReadToEndAsync() != "elwig:1")
|
||||||
throw new FileFormatException("Ungültige Export-Datei");
|
throw new FileFormatException($"Ungültige Export-Datei ({filename})");
|
||||||
}
|
}
|
||||||
|
|
||||||
var metaJson = zip.GetEntry("meta.json");
|
var metaJson = zip.GetEntry("meta.json");
|
||||||
var meta = await JsonNode.ParseAsync(metaJson!.Open());
|
var meta = await JsonNode.ParseAsync(metaJson!.Open());
|
||||||
var deliveryCount = meta!["deliveries"]?["count"]!.AsValue().GetValue<int>();
|
var memberCount = meta!["members"]?["count"]?.AsValue().GetValue<int>();
|
||||||
var deliveryFilters = meta!["deliveries"]?["filters"]!.AsArray().Select(f => f!.AsValue().GetValue<string>()).ToArray();
|
var memberFilters = meta!["members"]?["filters"]?.AsArray().Select(f => f!.AsValue().GetValue<string>()).ToArray();
|
||||||
if (deliveryCount != null && deliveryFilters != null)
|
var areaComCount = meta!["area_commitments"]?["count"]?.AsValue().GetValue<int>();
|
||||||
metaData.Add((Path.GetFileName(filename), (int)deliveryCount, string.Join(" / ", deliveryFilters)));
|
var areaComFilters = meta!["area_commitments"]?["filters"]?.AsArray().Select(f => f!.AsValue().GetValue<string>()).ToArray();
|
||||||
|
var deliveryCount = meta!["deliveries"]?["count"]?.AsValue().GetValue<int>();
|
||||||
|
var deliveryFilters = meta!["deliveries"]?["filters"]?.AsArray().Select(f => f!.AsValue().GetValue<string>()).ToArray();
|
||||||
|
metaData.Add((Path.GetFileName(filename),
|
||||||
|
meta["zwstid"]!.AsValue().GetValue<string>(), meta["device"]!.AsValue().GetValue<string>(),
|
||||||
|
memberCount, memberFilters != null ? string.Join(" / ", memberFilters) : null,
|
||||||
|
areaComCount, areaComFilters != null ? string.Join(" / ", areaComFilters) : null,
|
||||||
|
deliveryCount, deliveryFilters != null ? string.Join(" / ", deliveryFilters) : null));
|
||||||
|
|
||||||
|
data.Add(new([], [], [], [], [], [], [], new([], [])));
|
||||||
|
var r = data[^1];
|
||||||
|
|
||||||
var membersJson = zip.GetEntry("members.json");
|
var membersJson = zip.GetEntry("members.json");
|
||||||
if (membersJson != null) {
|
if (membersJson != null) {
|
||||||
@ -63,7 +101,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();
|
||||||
// TODO import members.json
|
var (m, b, telNrs, emailAddrs) = obj.ToMember();
|
||||||
|
r.Members.Add(m);
|
||||||
|
if (b != null) data[^1].BillingAddresses.Add(b);
|
||||||
|
r.TelephoneNumbers.AddRange(telNrs);
|
||||||
|
r.EmailAddresses.AddRange(emailAddrs);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -73,7 +115,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();
|
||||||
// TODO import area_commitments.json
|
var (areaCom, wbrd) = obj.ToAreaCom(currentWbRde);
|
||||||
|
r.AreaCommitments.Add(areaCom);
|
||||||
|
if (wbrd != null) r.Riede.Add(wbrd);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -83,85 +127,437 @@ 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) = JsonToDelivery(obj, currentDids);
|
var (d, parts, mods) = obj.ToDelivery(currentLsNrs, currentDids);
|
||||||
deliveries.Add(d);
|
r.Deliveries.Add(d);
|
||||||
deliveryParts.AddRange(parts);
|
r.DeliveryParts.AddRange(parts);
|
||||||
modifiers.AddRange(mods);
|
r.Modifiers.AddRange(mods);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
var lsnrs = deliveries.Select(d => d.LsNr).ToList();
|
var importedMembers = new List<(string FileName, string ZwstId, string Device, int New, int Overwritten, int NotImported, string Filters)>();
|
||||||
var duplicateLsNrs = await ctx.Deliveries
|
var importedAreaComs = new List<(string FileName, string ZwstId, string Device, int Imported, int NotImported, string Filters)>();
|
||||||
.Where(d => lsnrs.Contains(d.LsNr))
|
var importedDeliveries = new List<(string FileName, string ZwstId, string Device, int New, int Overwritten, int NotImported, string Filters)>();
|
||||||
.Select(d => d.LsNr)
|
|
||||||
.ToListAsync();
|
foreach (var ((members, billingAddresses, telephoneNumbers, emailAddresses, areaCommitments, riede, deliveries, deliveryParts, modifiers), meta) in data.Zip(metaData)) {
|
||||||
var duplicateDIds = deliveries
|
var branch = branches[meta.ZwstId];
|
||||||
.Where(d => duplicateLsNrs.Contains(d.LsNr))
|
var device = meta.Device;
|
||||||
.Select(d => (d.Year, d.DId))
|
|
||||||
.ToList();
|
using var ctx = new AppDbContext();
|
||||||
bool overwriteDelivieries = false;
|
|
||||||
if (duplicateLsNrs.Count > 0) {
|
var mgnrs = members.Select(m => m.MgNr).ToList();
|
||||||
var res = MessageBox.Show($"Sollen {duplicateLsNrs.Count} Lieferungen überschreiben werden?", "Lieferungen überschreiben",
|
var duplicateMgNrs = await ctx.Members
|
||||||
MessageBoxButton.YesNo, MessageBoxImage.Warning, MessageBoxResult.No);
|
.Where(m => mgnrs.Contains(m.MgNr))
|
||||||
overwriteDelivieries = res == MessageBoxResult.Yes;
|
.Select(m => m.MgNr)
|
||||||
|
.ToListAsync();
|
||||||
|
bool importNewMembers = false, importDuplicateMembers = false;
|
||||||
|
if (mode == ImportMode.Interactively) {
|
||||||
|
if (mgnrs.Count - duplicateMgNrs.Count > 0)
|
||||||
|
importNewMembers = ImportQuestion(branch.Name, device, "Mitglieder", false, mgnrs.Count - duplicateMgNrs.Count);
|
||||||
|
} else {
|
||||||
|
importNewMembers = true;
|
||||||
|
}
|
||||||
|
if (duplicateMgNrs.Count > 0)
|
||||||
|
importDuplicateMembers = ImportQuestion(branch.Name, device, "Mitglieder", true, duplicateMgNrs.Count);
|
||||||
|
|
||||||
|
var fbnrs = areaCommitments.Select(c => c.FbNr).ToList();
|
||||||
|
var duplicateFbNrs = await ctx.AreaCommitments
|
||||||
|
.Where(c => fbnrs.Contains(c.FbNr))
|
||||||
|
.Select(c => c.FbNr)
|
||||||
|
.ToListAsync();
|
||||||
|
|
||||||
|
var lsnrs = deliveries.Select(d => d.LsNr).ToList();
|
||||||
|
var duplicateLsNrs = await ctx.Deliveries
|
||||||
|
.Where(d => lsnrs.Contains(d.LsNr))
|
||||||
|
.Select(d => d.LsNr)
|
||||||
|
.ToListAsync();
|
||||||
|
var duplicateDIds = deliveries
|
||||||
|
.Where(d => duplicateLsNrs.Contains(d.LsNr))
|
||||||
|
.Select(d => (d.Year, d.DId))
|
||||||
|
.ToList();
|
||||||
|
var allowedDuplicateLsNrs = new List<string>();
|
||||||
|
bool importNewDeliveries = false, importDuplicateDeliveries = false;
|
||||||
|
if (mode == ImportMode.Interactively) {
|
||||||
|
if (lsnrs.Count - duplicateLsNrs.Count > 0)
|
||||||
|
importNewDeliveries = ImportQuestion(branch.Name, device, "Lieferungen", false, lsnrs.Count - duplicateLsNrs.Count);
|
||||||
|
if (duplicateLsNrs.Count > 0)
|
||||||
|
importDuplicateDeliveries = ImportQuestion(branch.Name, device, "Lieferungen", true, duplicateLsNrs.Count);
|
||||||
|
} else if (mode == ImportMode.FromBranches) {
|
||||||
|
importNewDeliveries = true;
|
||||||
|
if (duplicateLsNrs.Count > 0) {
|
||||||
|
allowedDuplicateLsNrs = await ctx.Deliveries
|
||||||
|
.Where(d => lsnrs.Contains(d.LsNr) && d.ZwstId == branch.ZwstId)
|
||||||
|
.Select(d => d.LsNr)
|
||||||
|
.ToListAsync();
|
||||||
|
if (duplicateLsNrs.Count - allowedDuplicateLsNrs.Count > 0)
|
||||||
|
importDuplicateDeliveries = ImportQuestion(branch.Name, device, "Lieferungen", true, duplicateLsNrs.Count - allowedDuplicateLsNrs.Count);
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
importNewDeliveries = true;
|
||||||
|
if (duplicateLsNrs.Count > 0)
|
||||||
|
importDuplicateDeliveries = ImportQuestion(branch.Name, device, "Lieferungen", true, duplicateLsNrs.Count);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (importDuplicateMembers) {
|
||||||
|
ctx.RemoveRange(ctx.BillingAddresses.Where(a => duplicateMgNrs.Contains(a.MgNr)));
|
||||||
|
ctx.RemoveRange(ctx.MemberTelephoneNrs.Where(n => duplicateMgNrs.Contains(n.MgNr)));
|
||||||
|
ctx.RemoveRange(ctx.MemberEmailAddrs.Where(a => duplicateMgNrs.Contains(a.MgNr)));
|
||||||
|
ctx.UpdateRange(members.Where(m => duplicateMgNrs.Contains(m.MgNr)));
|
||||||
|
ctx.AddRange(billingAddresses.Where(a => duplicateMgNrs.Contains(a.MgNr)));
|
||||||
|
ctx.AddRange(telephoneNumbers.Where(n => duplicateMgNrs.Contains(n.MgNr)));
|
||||||
|
ctx.AddRange(emailAddresses.Where(a => duplicateMgNrs.Contains(a.MgNr)));
|
||||||
|
ctx.UpdateRange(areaCommitments.Where(c => duplicateMgNrs.Contains(c.MgNr) && duplicateFbNrs.Contains(c.FbNr)));
|
||||||
|
ctx.AddRange(areaCommitments.Where(c => duplicateMgNrs.Contains(c.MgNr) && !duplicateFbNrs.Contains(c.FbNr)));
|
||||||
|
}
|
||||||
|
if (importNewMembers) {
|
||||||
|
ctx.AddRange(members.Where(m => !duplicateMgNrs.Contains(m.MgNr)));
|
||||||
|
ctx.AddRange(billingAddresses.Where(a => !duplicateMgNrs.Contains(a.MgNr)));
|
||||||
|
ctx.AddRange(telephoneNumbers.Where(n => !duplicateMgNrs.Contains(n.MgNr)));
|
||||||
|
ctx.AddRange(emailAddresses.Where(a => !duplicateMgNrs.Contains(a.MgNr)));
|
||||||
|
ctx.UpdateRange(areaCommitments.Where(c => !duplicateMgNrs.Contains(c.MgNr) && duplicateFbNrs.Contains(c.FbNr)));
|
||||||
|
ctx.AddRange(areaCommitments.Where(c => !duplicateMgNrs.Contains(c.MgNr) && !duplicateFbNrs.Contains(c.FbNr)));
|
||||||
|
}
|
||||||
|
if (members.Count > 0) {
|
||||||
|
var n = importNewMembers ? members.Count - duplicateMgNrs.Count : 0;
|
||||||
|
var o = importDuplicateMembers ? duplicateMgNrs.Count : 0;
|
||||||
|
importedMembers.Add((meta.FileName, meta.ZwstId, meta.Device, n, o, members.Count - n - o, meta.MemberFilters));
|
||||||
|
}
|
||||||
|
if (areaCommitments.Count > 0) {
|
||||||
|
var imported = areaCommitments.Where(c => (importNewMembers && !duplicateMgNrs.Contains(c.MgNr)) || (importDuplicateMembers && duplicateMgNrs.Contains(c.MgNr))).ToList();
|
||||||
|
importedAreaComs.Add((meta.FileName, meta.ZwstId, meta.Device, imported.Count, areaCommitments.Count - imported.Count, meta.AreaComFilters));
|
||||||
|
}
|
||||||
|
|
||||||
|
if (allowedDuplicateLsNrs.Count > 0) {
|
||||||
|
var dids = deliveries
|
||||||
|
.Where(d => allowedDuplicateLsNrs.Contains(d.LsNr))
|
||||||
|
.Select(d => (d.Year, d.DId))
|
||||||
|
.ToList();
|
||||||
|
ctx.RemoveRange(ctx.DeliveryParts
|
||||||
|
.Where(p => allowedDuplicateLsNrs.Contains(p.Delivery.LsNr))
|
||||||
|
.SelectMany(p => p.PartModifiers));
|
||||||
|
ctx.RemoveRange(ctx.DeliveryParts.Where(p => allowedDuplicateLsNrs.Contains(p.Delivery.LsNr)));
|
||||||
|
ctx.UpdateRange(deliveries.Where(d => dids.Contains((d.Year, d.DId))));
|
||||||
|
ctx.AddRange(deliveryParts.Where(p => dids.Contains((p.Year, p.DId))));
|
||||||
|
ctx.AddRange(modifiers.Where(m => dids.Contains((m.Year, m.DId))));
|
||||||
|
}
|
||||||
|
if (importDuplicateDeliveries) {
|
||||||
|
var l = duplicateLsNrs.Except(allowedDuplicateLsNrs).ToList();
|
||||||
|
var dids = deliveries
|
||||||
|
.Where(d => l.Contains(d.LsNr))
|
||||||
|
.Select(d => (d.Year, d.DId))
|
||||||
|
.ToList();
|
||||||
|
ctx.RemoveRange(ctx.DeliveryParts
|
||||||
|
.Where(p => l.Contains(p.Delivery.LsNr))
|
||||||
|
.SelectMany(p => p.PartModifiers));
|
||||||
|
ctx.RemoveRange(ctx.DeliveryParts.Where(p => l.Contains(p.Delivery.LsNr)));
|
||||||
|
ctx.UpdateRange(deliveries.Where(d => dids.Contains((d.Year, d.DId))));
|
||||||
|
ctx.AddRange(deliveryParts.Where(p => dids.Contains((p.Year, p.DId))));
|
||||||
|
ctx.AddRange(modifiers.Where(m => dids.Contains((m.Year, m.DId))));
|
||||||
|
}
|
||||||
|
if (importNewDeliveries) {
|
||||||
|
ctx.AddRange(deliveries.Where(d => !duplicateDIds.Contains((d.Year, d.DId))));
|
||||||
|
ctx.AddRange(deliveryParts.Where(p => !duplicateDIds.Contains((p.Year, p.DId))));
|
||||||
|
ctx.AddRange(modifiers.Where(m => !duplicateDIds.Contains((m.Year, m.DId))));
|
||||||
|
}
|
||||||
|
if (deliveries.Count > 0) {
|
||||||
|
var n = importNewDeliveries ? deliveries.Count - duplicateDIds.Count : 0;
|
||||||
|
var o = allowedDuplicateLsNrs.Count + (importDuplicateDeliveries ? duplicateDIds.Count - allowedDuplicateLsNrs.Count : 0);
|
||||||
|
importedDeliveries.Add((meta.FileName, meta.ZwstId, meta.Device, n, o, deliveries.Count - n - o, meta.DeliveryFilters));
|
||||||
|
}
|
||||||
|
|
||||||
|
await ctx.SaveChangesAsync();
|
||||||
|
await AddImportedFiles(Path.GetFileName(meta.FileName));
|
||||||
}
|
}
|
||||||
if (overwriteDelivieries) {
|
|
||||||
ctx.RemoveRange(ctx.Deliveries.Where(d => duplicateLsNrs.Contains(d.LsNr)));
|
|
||||||
ctx.AddRange(deliveries);
|
|
||||||
ctx.AddRange(deliveryParts);
|
|
||||||
ctx.AddRange(modifiers);
|
|
||||||
} else {
|
|
||||||
ctx.AddRange(deliveries.Where(d => !duplicateDIds.Contains((d.Year, d.DId))));
|
|
||||||
ctx.AddRange(deliveryParts.Where(p => !duplicateDIds.Contains((p.Year, p.DId))));
|
|
||||||
ctx.AddRange(modifiers.Where(m => !duplicateDIds.Contains((m.Year, m.DId))));
|
|
||||||
}
|
|
||||||
await ctx.SaveChangesAsync();
|
|
||||||
await AddImportedFiles(filenames.Select(f => Path.GetFileName(f)));
|
|
||||||
await App.HintContextChange();
|
await App.HintContextChange();
|
||||||
|
|
||||||
MessageBox.Show(
|
MessageBox.Show(
|
||||||
$"Das importieren der Daten war erfolgreich!\n" +
|
$"Das importieren der Daten war erfolgreich!\n" +
|
||||||
$"Folgendes wurde importiert:\n" +
|
$"Folgendes wurde importiert:\n" +
|
||||||
$" Lieferungen: {deliveries.Count}\n" +
|
string.Join("\n", [
|
||||||
string.Join("\n", metaData.Select(d => $" {d.Name} ({d.DeliveryNum})\n {d.Filters}")) +
|
$"Mitglieder: {importedMembers.Sum(d => d.New + d.Overwritten)}",
|
||||||
"\n", "Importieren erfolgreich",
|
..importedMembers.Select(d =>
|
||||||
|
$" {d.FileName} ({d.New + d.Overwritten})\n" +
|
||||||
|
$" ({d.New} neu, {d.Overwritten} überschrieben, {d.NotImported} nicht importiert)\n" +
|
||||||
|
$" Zweigstelle: {branches[d.ZwstId].Name} (Gerät {d.Device})\n" +
|
||||||
|
$" Filter: {d.Filters}"),
|
||||||
|
$"Flächenbindungen: {importedAreaComs.Sum(d => d.Imported)}",
|
||||||
|
..importedAreaComs.Select(d =>
|
||||||
|
$" {d.FileName} ({d.Imported})\n" +
|
||||||
|
$" ({d.Imported} importiert, {d.NotImported} nicht importiert)\n" +
|
||||||
|
$" Zweigstelle: {branches[d.ZwstId].Name} (Gerät {d.Device})\n" +
|
||||||
|
$" Filter: {d.Filters}"),
|
||||||
|
$"Lieferungen: {importedDeliveries.Sum(d => d.New + d.Overwritten)}",
|
||||||
|
..importedDeliveries.Select(d =>
|
||||||
|
$" {d.FileName} ({d.New + d.Overwritten})\n" +
|
||||||
|
$" ({d.New} neu, {d.Overwritten} überschr., {d.NotImported} nicht importiert)\n" +
|
||||||
|
$" Zwst.: {branches[d.ZwstId].Name} (Gerät {d.Device})\n" +
|
||||||
|
$" Filter: {d.Filters}")
|
||||||
|
]),
|
||||||
|
"Importieren erfolgreich",
|
||||||
MessageBoxButton.OK, MessageBoxImage.Information);
|
MessageBoxButton.OK, MessageBoxImage.Information);
|
||||||
} catch (Exception exc) {
|
} catch (Exception exc) {
|
||||||
MessageBox.Show(exc.Message, "Fehler", MessageBoxButton.OK, MessageBoxImage.Error);
|
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, "Fehler", MessageBoxButton.OK, MessageBoxImage.Error);
|
||||||
}
|
}
|
||||||
|
GC.Collect();
|
||||||
|
GC.WaitForPendingFinalizers();
|
||||||
}
|
}
|
||||||
|
|
||||||
public static async Task ExportDeliveries(string filename, IEnumerable<Delivery> deliveries, IEnumerable<string> filters) {
|
private static bool ImportQuestion(string branch, string device, string subject, bool duplicate, int number) {
|
||||||
File.Delete(filename);
|
return MessageBox.Show(
|
||||||
using var zip = ZipFile.Open(filename, ZipArchiveMode.Create);
|
$"Sollen {number} {(duplicate ? "" : "neue ")}{subject} durch die Zweigstelle\n" +
|
||||||
|
$"{branch} (Gerät {device}) {(duplicate ? "überschrieben" : "importiert")} werden?",
|
||||||
|
$"{subject} importieren",
|
||||||
|
MessageBoxButton.YesNo, MessageBoxImage.Question, MessageBoxResult.Yes
|
||||||
|
) == MessageBoxResult.Yes;
|
||||||
|
}
|
||||||
|
|
||||||
var version = zip.CreateEntry("version", CompressionLevel.NoCompression);
|
public static Task Export(string filename, IEnumerable<Member> members, IEnumerable<string> filters) {
|
||||||
using (var writer = new StreamWriter(version.Open(), Utils.UTF8)) {
|
return new ElwigExport {
|
||||||
await writer.WriteAsync("elwig:1");
|
Members = (members, filters)
|
||||||
}
|
}.Export(filename);
|
||||||
|
}
|
||||||
|
|
||||||
var meta = zip.CreateEntry("meta.json", CompressionLevel.NoCompression);
|
public static Task Export(string filename, IEnumerable<Member> members, IEnumerable<AreaCom> areaComs, IEnumerable<string> filters) {
|
||||||
using (var writer = new StreamWriter(meta.Open(), Utils.UTF8)) {
|
return new ElwigExport {
|
||||||
await writer.WriteAsync(
|
Members = (members, filters),
|
||||||
$"{{\"timestamp\": \"{DateTime.UtcNow:yyyy-MM-ddTHH:mm:ssZ}\", " +
|
AreaComs = (areaComs, ["von exportierten Mitgliedern"]),
|
||||||
$"\"zwstid\": \"{App.ZwstId}\", \"device\": \"{Environment.MachineName}\", " +
|
}.Export(filename);
|
||||||
$"\"deliveries\": {{" +
|
}
|
||||||
$"\"count\": {deliveries.Count()}, " +
|
|
||||||
$"\"parts\": {deliveries.Sum(d => d.Parts.Count)}, " +
|
|
||||||
$"\"filters\": [{string.Join(", ", filters.Select(f => '"' + f + '"'))}]" +
|
|
||||||
$"}}}}");
|
|
||||||
}
|
|
||||||
|
|
||||||
var json = zip.CreateEntry("deliveries.json");
|
public static Task Export(string filename, IEnumerable<Delivery> deliveries, IEnumerable<string> filters) {
|
||||||
using (var writer = new StreamWriter(json.Open(), Utils.UTF8)) {
|
return new ElwigExport {
|
||||||
foreach (var d in deliveries) {
|
Deliveries = (deliveries, filters)
|
||||||
await writer.WriteLineAsync(DeliveryToJson(d).ToJsonString());
|
}.Export(filename);
|
||||||
|
}
|
||||||
|
|
||||||
|
public class ElwigExport {
|
||||||
|
public (IEnumerable<Member> Members, IEnumerable<string> Filters)? Members { get; set; }
|
||||||
|
public (IEnumerable<AreaCom> AreaComs, IEnumerable<string> Filters)? AreaComs { get; set; }
|
||||||
|
public (IEnumerable<Delivery> Deliveries, IEnumerable<string> Filters)? Deliveries { get; set; }
|
||||||
|
|
||||||
|
public async Task Export(string filename) {
|
||||||
|
File.Delete(filename);
|
||||||
|
using var zip = ZipFile.Open(filename, ZipArchiveMode.Create);
|
||||||
|
|
||||||
|
var version = zip.CreateEntry("version", CompressionLevel.NoCompression);
|
||||||
|
using (var writer = new StreamWriter(version.Open(), Utils.UTF8)) {
|
||||||
|
await writer.WriteAsync("elwig:1");
|
||||||
|
}
|
||||||
|
|
||||||
|
var meta = zip.CreateEntry("meta.json", CompressionLevel.NoCompression);
|
||||||
|
using (var writer = new StreamWriter(meta.Open(), Utils.UTF8)) {
|
||||||
|
var obj = new JsonObject {
|
||||||
|
["timestamp"] = $"{DateTime.UtcNow:yyyy-MM-ddTHH:mm:ssZ}",
|
||||||
|
["zwstid"] = App.ZwstId,
|
||||||
|
["device"] = Environment.MachineName,
|
||||||
|
};
|
||||||
|
if (Members != null)
|
||||||
|
obj["members"] = new JsonObject {
|
||||||
|
["count"] = Members.Value.Members.Count(),
|
||||||
|
["filters"] = new JsonArray(Members.Value.Filters.Select(f => (JsonNode)f).ToArray()),
|
||||||
|
};
|
||||||
|
if (AreaComs != null)
|
||||||
|
obj["area_commitments"] = new JsonObject {
|
||||||
|
["count"] = AreaComs.Value.AreaComs.Count(),
|
||||||
|
["filters"] = new JsonArray(AreaComs.Value.Filters.Select(f => (JsonNode)f).ToArray()),
|
||||||
|
};
|
||||||
|
if (Deliveries != null)
|
||||||
|
obj["deliveries"] = new JsonObject {
|
||||||
|
["count"] = Deliveries.Value.Deliveries.Count(),
|
||||||
|
["parts"] = Deliveries.Value.Deliveries.Sum(d => d.Parts.Count),
|
||||||
|
["filters"] = new JsonArray(Deliveries.Value.Filters.Select(f => (JsonNode)f).ToArray()),
|
||||||
|
};
|
||||||
|
await writer.WriteAsync(obj.ToJsonString(JsonOpts));
|
||||||
|
}
|
||||||
|
|
||||||
|
// TODO encrypt files
|
||||||
|
if (Members != null) {
|
||||||
|
var json = zip.CreateEntry("members.json", CompressionLevel.SmallestSize);
|
||||||
|
using var writer = new StreamWriter(json.Open(), Utils.UTF8);
|
||||||
|
foreach (var m in Members.Value.Members) {
|
||||||
|
await writer.WriteLineAsync(m.ToJson().ToJsonString(JsonOpts));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (AreaComs != null) {
|
||||||
|
var json = zip.CreateEntry("area_commitments.json", CompressionLevel.SmallestSize);
|
||||||
|
using var writer = new StreamWriter(json.Open(), Utils.UTF8);
|
||||||
|
foreach (var c in AreaComs.Value.AreaComs) {
|
||||||
|
await writer.WriteLineAsync(c.ToJson().ToJsonString(JsonOpts));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (Deliveries != null) {
|
||||||
|
var json = zip.CreateEntry("deliveries.json", CompressionLevel.SmallestSize);
|
||||||
|
using var writer = new StreamWriter(json.Open(), Utils.UTF8);
|
||||||
|
foreach (var d in Deliveries.Value.Deliveries) {
|
||||||
|
await writer.WriteLineAsync(d.ToJson().ToJsonString(JsonOpts));
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public static JsonObject DeliveryToJson(Delivery d) {
|
public static JsonObject ToJson(this Member m) {
|
||||||
|
return new JsonObject {
|
||||||
|
["mgnr"] = m.MgNr,
|
||||||
|
["predecessor_mgnr"] = m.PredecessorMgNr,
|
||||||
|
["prefix"] = m.Prefix,
|
||||||
|
["given_name"] = m.GivenName,
|
||||||
|
["middle_names"] = m.MiddleName,
|
||||||
|
["family_name"] = m.FamilyName,
|
||||||
|
["suffix"] = m.Suffix,
|
||||||
|
["birthday"] = m.Birthday,
|
||||||
|
["entry_date"] = m.EntryDate != null ? $"{m.EntryDate:yyyy-MM-dd}" : null,
|
||||||
|
["exit_date"] = m.ExitDate != null ? $"{m.ExitDate:yyyy-MM-dd}" : null,
|
||||||
|
["business_shares"] = m.BusinessShares,
|
||||||
|
["accounting_nr"] = m.AccountingNr,
|
||||||
|
["zwstid"] = m.ZwstId,
|
||||||
|
["lfbis_nr"] = m.LfbisNr,
|
||||||
|
["ustid_nr"] = m.UstIdNr,
|
||||||
|
["volllieferant"] = m.IsVollLieferant,
|
||||||
|
["buchführend"] = m.IsBuchführend,
|
||||||
|
["organic"] = m.IsOrganic,
|
||||||
|
["funktionär"] = m.IsFunktionär,
|
||||||
|
["active"] = m.IsActive,
|
||||||
|
["deceased"] = m.IsDeceased,
|
||||||
|
["iban"] = m.Iban,
|
||||||
|
["bic"] = m.Bic,
|
||||||
|
["default_kgnr"] = m.DefaultKgNr,
|
||||||
|
["contact_postal"] = m.ContactViaPost,
|
||||||
|
["contact_email"] = m.ContactViaEmail,
|
||||||
|
["address"] = new JsonObject {
|
||||||
|
["address"] = m.Address,
|
||||||
|
["postal_dest"] = m.PostalDestId,
|
||||||
|
["country"] = m.CountryNum,
|
||||||
|
},
|
||||||
|
["billing_address"] = m.BillingAddress != null ? new JsonObject {
|
||||||
|
["name"] = m.BillingAddress.Name,
|
||||||
|
["address"] = m.BillingAddress.Address,
|
||||||
|
["postal_dest"] = m.BillingAddress.PostalDestId,
|
||||||
|
["country"] = m.BillingAddress.CountryNum,
|
||||||
|
} : null,
|
||||||
|
["telephone_numbers"] = new JsonArray(m.TelephoneNumbers.OrderBy(n => n.Nr).Select(n => {
|
||||||
|
var obj = new JsonObject {
|
||||||
|
["number"] = n.Number,
|
||||||
|
["type"] = n.Type,
|
||||||
|
};
|
||||||
|
if (n.Comment != null) obj["comment"] = n.Comment;
|
||||||
|
return obj;
|
||||||
|
}).ToArray()),
|
||||||
|
["email_addresses"] = new JsonArray(m.EmailAddresses.OrderBy(a => a.Nr).Select(a => {
|
||||||
|
var obj = new JsonObject {
|
||||||
|
["address"] = a.Address,
|
||||||
|
};
|
||||||
|
if (a.Comment != null) obj["comment"] = a.Comment;
|
||||||
|
return obj;
|
||||||
|
}).ToArray()),
|
||||||
|
["comment"] = m.Comment,
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
|
public static (Member, BillingAddr?, List<MemberTelNr>, List<MemberEmailAddr>) ToMember(this JsonNode json) {
|
||||||
|
var mgnr = json["mgnr"]!.AsValue().GetValue<int>();
|
||||||
|
return (new Member {
|
||||||
|
MgNr = mgnr,
|
||||||
|
PredecessorMgNr = json["predecessor_mgnr"]?.AsValue().GetValue<int>(),
|
||||||
|
Prefix = json["prefix"]?.AsValue().GetValue<string>(),
|
||||||
|
GivenName = json["given_name"]!.AsValue().GetValue<string>(),
|
||||||
|
MiddleName = json["middle_names"]?.AsValue().GetValue<string>(),
|
||||||
|
FamilyName = json["family_name"]!.AsValue().GetValue<string>(),
|
||||||
|
Suffix = json["suffix"]?.AsValue().GetValue<string>(),
|
||||||
|
Birthday = json["birthday"]?.AsValue().GetValue<string>(),
|
||||||
|
EntryDateString = json["entry_date"]?.AsValue().GetValue<string>(),
|
||||||
|
ExitDateString = json["exit_date"]?.AsValue().GetValue<string>(),
|
||||||
|
BusinessShares = json["business_shares"]?.AsValue().GetValue<int>() ?? 0,
|
||||||
|
AccountingNr = json["accounting_nr"]?.AsValue().GetValue<string>(),
|
||||||
|
ZwstId = json["zwstid"]?.AsValue().GetValue<string>(),
|
||||||
|
LfbisNr = json["lfbis_nr"]?.AsValue().GetValue<string>(),
|
||||||
|
UstIdNr = json["ustid_nr"]?.AsValue().GetValue<string>(),
|
||||||
|
IsVollLieferant = json["volllieferant"]?.AsValue().GetValue<bool>() ?? false,
|
||||||
|
IsBuchführend = json["buchführend"]?.AsValue().GetValue<bool>() ?? false,
|
||||||
|
IsOrganic = json["organic"]?.AsValue().GetValue<bool>() ?? false,
|
||||||
|
IsFunktionär = json["funktionär"]?.AsValue().GetValue<bool>() ?? false,
|
||||||
|
IsActive = json["active"]?.AsValue().GetValue<bool>() ?? false,
|
||||||
|
IsDeceased = json["deceased"]?.AsValue().GetValue<bool>() ?? false,
|
||||||
|
Iban = json["iban"]?.AsValue().GetValue<string>(),
|
||||||
|
Bic = json["bic"]?.AsValue().GetValue<string>(),
|
||||||
|
CountryNum = json["address"]!["country"]!.AsValue().GetValue<int>(),
|
||||||
|
PostalDestId = json["address"]!["postal_dest"]!.AsValue().GetValue<string>(),
|
||||||
|
Address = json["address"]!["address"]!.AsValue().GetValue<string>(),
|
||||||
|
DefaultKgNr = json["default_kgnr"]?.AsValue().GetValue<int>(),
|
||||||
|
ContactViaPost = json["contact_postal"]?.AsValue().GetValue<bool>() ?? false,
|
||||||
|
ContactViaEmail = json["contact_email"]?.AsValue().GetValue<bool>() ?? false,
|
||||||
|
Comment = json["comment"]?.AsValue().GetValue<string>(),
|
||||||
|
}, json["billing_address"] is JsonObject a ? new BillingAddr {
|
||||||
|
MgNr = mgnr,
|
||||||
|
Name = a["name"]!.AsValue().GetValue<string>(),
|
||||||
|
CountryNum = a["country"]!.AsValue().GetValue<int>(),
|
||||||
|
PostalDestId = a["postal_dest"]!.AsValue().GetValue<string>(),
|
||||||
|
Address = a["address"]!.AsValue().GetValue<string>(),
|
||||||
|
} : null, json["telephone_numbers"]!.AsArray().Select(n => n!.AsObject()).Select((n, i) => new MemberTelNr {
|
||||||
|
MgNr = mgnr,
|
||||||
|
Nr = i + 1,
|
||||||
|
Type = n["type"]!.AsValue().GetValue<string>(),
|
||||||
|
Number = n["number"]!.AsValue().GetValue<string>(),
|
||||||
|
Comment = n["comment"]?.AsValue().GetValue<string>(),
|
||||||
|
}).ToList(), json["email_addresses"]!.AsArray().Select(a => a!.AsObject()).Select((a, i) => new MemberEmailAddr {
|
||||||
|
MgNr = mgnr,
|
||||||
|
Nr = i + 1,
|
||||||
|
Address = a["address"]!.AsValue().GetValue<string>(),
|
||||||
|
Comment = a["comment"]?.AsValue().GetValue<string>(),
|
||||||
|
}).ToList());
|
||||||
|
}
|
||||||
|
|
||||||
|
public static JsonObject ToJson(this AreaCom c) {
|
||||||
|
return new JsonObject {
|
||||||
|
["fbnr"] = c.FbNr,
|
||||||
|
["mgnr"] = c.MgNr,
|
||||||
|
["vtrgid"] = c.VtrgId,
|
||||||
|
["cultid"] = c.CultId,
|
||||||
|
["area"] = c.Area,
|
||||||
|
["kgnr"] = c.KgNr,
|
||||||
|
["gstnr"] = c.GstNr,
|
||||||
|
["ried"] = c.Rd?.Name,
|
||||||
|
["year_from"] = c.YearFrom,
|
||||||
|
["year_to"] = c.YearTo,
|
||||||
|
["comment"] = c.Comment,
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
|
public static (AreaCom, WbRd?) ToAreaCom(this JsonNode json, Dictionary<int, List<WbRd>> riede) {
|
||||||
|
var kgnr = json["kgnr"]!.AsValue().GetValue<int>();
|
||||||
|
var ried = json["ried"]?.AsValue().GetValue<string>();
|
||||||
|
WbRd? rd = null;
|
||||||
|
bool newRd = false;
|
||||||
|
if (ried != null) {
|
||||||
|
var rde = riede[kgnr] ?? throw new ArgumentException($"KG {kgnr:00000} is no WbKg");
|
||||||
|
rd = rde.FirstOrDefault(r => r.Name == ried);
|
||||||
|
if (rd == null) {
|
||||||
|
newRd = true;
|
||||||
|
rd = new WbRd {
|
||||||
|
KgNr = kgnr,
|
||||||
|
RdNr = (rde.Count == 0 ? 0 : rde.Max(r => r.RdNr)) + 1,
|
||||||
|
Name = ried,
|
||||||
|
};
|
||||||
|
rde.Add(rd);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return (new AreaCom {
|
||||||
|
FbNr = json["fbnr"]!.AsValue().GetValue<int>(),
|
||||||
|
MgNr = json["mgnr"]!.AsValue().GetValue<int>(),
|
||||||
|
VtrgId = json["vtrgid"]!.AsValue().GetValue<string>(),
|
||||||
|
CultId = json["cultid"]?.AsValue().GetValue<string>(),
|
||||||
|
Area = json["area"]!.AsValue().GetValue<int>(),
|
||||||
|
KgNr = kgnr,
|
||||||
|
GstNr = json["gstnr"]?.AsValue().GetValue<string>() ?? "-",
|
||||||
|
RdNr = rd?.RdNr,
|
||||||
|
YearFrom = json["year_from"]!.AsValue().GetValue<int>(),
|
||||||
|
YearTo = json["year_to"]?.AsValue().GetValue<int>(),
|
||||||
|
Comment = json["comment"]?.AsValue().GetValue<string>(),
|
||||||
|
}, newRd ? rd : null);
|
||||||
|
}
|
||||||
|
|
||||||
|
public static JsonObject ToJson(this Delivery d) {
|
||||||
return new JsonObject {
|
return new JsonObject {
|
||||||
["lsnr"] = d.LsNr,
|
["lsnr"] = d.LsNr,
|
||||||
["year"] = d.Year,
|
["year"] = d.Year,
|
||||||
@ -194,7 +590,7 @@ namespace Elwig.Helpers.Export {
|
|||||||
if (p.Temperature != null) obj["temperature"] = p.Temperature;
|
if (p.Temperature != null) obj["temperature"] = p.Temperature;
|
||||||
if (p.Acid != null) obj["acid"] = p.Acid;
|
if (p.Acid != null) obj["acid"] = p.Acid;
|
||||||
if (p.ScaleId != null) obj["scale_id"] = p.ScaleId;
|
if (p.ScaleId != null) obj["scale_id"] = p.ScaleId;
|
||||||
if (p.WeighingId != null) obj["weighing_id"] = p.WeighingId;
|
if (p.WeighingData != null) obj["weighing_data"] = JsonNode.Parse(p.WeighingData);
|
||||||
if (p.WeighingReason != null) obj["weighing_reason"] = p.WeighingReason;
|
if (p.WeighingReason != null) obj["weighing_reason"] = p.WeighingReason;
|
||||||
return obj;
|
return obj;
|
||||||
}).ToArray()),
|
}).ToArray()),
|
||||||
@ -202,9 +598,15 @@ namespace Elwig.Helpers.Export {
|
|||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
public static (Delivery, List<DeliveryPart>, List<DeliveryPartModifier>) JsonToDelivery(JsonNode json, Dictionary<int, int> currentDids) {
|
public static (Delivery, List<DeliveryPart>, List<DeliveryPartModifier>) ToDelivery(this JsonNode json, Dictionary<string, int> currentLsNrs, Dictionary<int, int> currentDids) {
|
||||||
var year = json["year"]!.AsValue().GetValue<int>();
|
var year = json["year"]!.AsValue().GetValue<int>();
|
||||||
var did = ++currentDids[year];
|
var lsnr = json["lsnr"]!.AsValue().GetValue<string>();
|
||||||
|
var did = currentLsNrs.GetValueOrDefault(lsnr, -1);
|
||||||
|
if (did == -1) {
|
||||||
|
if (!currentDids.ContainsKey(year)) currentDids[year] = 0;
|
||||||
|
did = ++currentDids[year];
|
||||||
|
}
|
||||||
|
currentLsNrs[lsnr] = did;
|
||||||
return (new Delivery {
|
return (new Delivery {
|
||||||
Year = year,
|
Year = year,
|
||||||
DId = did,
|
DId = did,
|
||||||
@ -212,7 +614,7 @@ namespace Elwig.Helpers.Export {
|
|||||||
TimeString = json["time"]?.AsValue().GetValue<string>(),
|
TimeString = json["time"]?.AsValue().GetValue<string>(),
|
||||||
ZwstId = json["zwstid"]!.AsValue().GetValue<string>(),
|
ZwstId = json["zwstid"]!.AsValue().GetValue<string>(),
|
||||||
LNr = json["lnr"]!.AsValue().GetValue<int>(),
|
LNr = json["lnr"]!.AsValue().GetValue<int>(),
|
||||||
LsNr = json["lsnr"]!.AsValue().GetValue<string>(),
|
LsNr = lsnr,
|
||||||
MgNr = json["mgnr"]!.AsValue().GetValue<int>(),
|
MgNr = json["mgnr"]!.AsValue().GetValue<int>(),
|
||||||
Comment = json["comment"]?.AsValue().GetValue<string>(),
|
Comment = json["comment"]?.AsValue().GetValue<string>(),
|
||||||
}, json["parts"]!.AsArray().Select(p => p!.AsObject()).Select(p => new DeliveryPart {
|
}, json["parts"]!.AsArray().Select(p => p!.AsObject()).Select(p => new DeliveryPart {
|
||||||
@ -238,7 +640,7 @@ namespace Elwig.Helpers.Export {
|
|||||||
Temperature = p["temperature"]?.AsValue().GetValue<double>(),
|
Temperature = p["temperature"]?.AsValue().GetValue<double>(),
|
||||||
Acid = p["acid"]?.AsValue().GetValue<double>(),
|
Acid = p["acid"]?.AsValue().GetValue<double>(),
|
||||||
ScaleId = p["scale_id"]?.AsValue().GetValue<string>(),
|
ScaleId = p["scale_id"]?.AsValue().GetValue<string>(),
|
||||||
WeighingId = p["weighing_id"]?.AsValue().GetValue<string>(),
|
WeighingData = p["weighing_data"]?.AsObject().ToJsonString(JsonOpts),
|
||||||
WeighingReason = p["weighing_reason"]?.AsValue().GetValue<string>(),
|
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,
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
using Elwig.Models.Dtos;
|
using Elwig.Models.Dtos;
|
||||||
using System;
|
using System;
|
||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
using System.Data.Entity.Core.Common.CommandTrees.ExpressionBuilder;
|
using System.Data.Entity.Core.Common.CommandTrees.ExpressionBuilder;
|
||||||
@ -6,6 +6,7 @@ using System.Globalization;
|
|||||||
using System.IO;
|
using System.IO;
|
||||||
using System.IO.Compression;
|
using System.IO.Compression;
|
||||||
using System.Linq;
|
using System.Linq;
|
||||||
|
using System.Security;
|
||||||
using System.Threading.Tasks;
|
using System.Threading.Tasks;
|
||||||
|
|
||||||
namespace Elwig.Helpers.Export {
|
namespace Elwig.Helpers.Export {
|
||||||
@ -312,7 +313,7 @@ namespace Elwig.Helpers.Export {
|
|||||||
}
|
}
|
||||||
c = $"<{ct} office:value-type=\"float\" calcext:value-type=\"float\" office:value=\"{v.ToString(CultureInfo.InvariantCulture)}\"{add}><text:p>{data}</text:p></{ct}>";
|
c = $"<{ct} office:value-type=\"float\" calcext:value-type=\"float\" office:value=\"{v.ToString(CultureInfo.InvariantCulture)}\"{add}><text:p>{data}</text:p></{ct}>";
|
||||||
} else {
|
} else {
|
||||||
c = $"<{ct} office:value-type=\"string\" calcext:value-type=\"string\"{add}><text:p>{data}</text:p></{ct}>";
|
c = $"<{ct} office:value-type=\"string\" calcext:value-type=\"string\"{add}><text:p>{SecurityElement.Escape(data.ToString())}</text:p></{ct}>";
|
||||||
}
|
}
|
||||||
|
|
||||||
return $" {c}\r\n" + (colSpan > 1 ? $" <table:covered-table-cell table:number-rows-repeated=\"{colSpan - 1}\"/>\r\n" : "");
|
return $" {c}\r\n" + (colSpan > 1 ? $" <table:covered-table-cell table:number-rows-repeated=\"{colSpan - 1}\"/>\r\n" : "");
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
namespace Elwig.Helpers {
|
namespace Elwig.Helpers {
|
||||||
public enum ExportMode {
|
public enum ExportMode {
|
||||||
Show, SaveList, SavePdf, Print, Email, Export, Upload
|
Show, SaveList, SavePdf, Print, Email, Export, Upload
|
||||||
}
|
}
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
using System;
|
using System;
|
||||||
using System.IO;
|
using System.IO;
|
||||||
using System.Net.Http;
|
using System.Net.Http;
|
||||||
using System.Runtime.InteropServices;
|
using System.Runtime.InteropServices;
|
||||||
|
@ -94,7 +94,11 @@ namespace Elwig.Helpers.Printing {
|
|||||||
|
|
||||||
public static async Task Print(string path, int copies = 1) {
|
public static async Task Print(string path, int copies = 1) {
|
||||||
try {
|
try {
|
||||||
var p = new Process() { StartInfo = new() { FileName = PdfToPrinter } };
|
var p = new Process() { StartInfo = new() {
|
||||||
|
FileName = PdfToPrinter,
|
||||||
|
CreateNoWindow = true,
|
||||||
|
UseShellExecute = false,
|
||||||
|
} };
|
||||||
p.StartInfo.ArgumentList.Add(path);
|
p.StartInfo.ArgumentList.Add(path);
|
||||||
p.StartInfo.ArgumentList.Add("/s");
|
p.StartInfo.ArgumentList.Add("/s");
|
||||||
p.StartInfo.ArgumentList.Add($"copies={copies}");
|
p.StartInfo.ArgumentList.Add($"copies={copies}");
|
||||||
|
@ -36,7 +36,7 @@ namespace Elwig.Helpers {
|
|||||||
|
|
||||||
public static int CurrentYear => DateTime.Now.Year;
|
public static int CurrentYear => DateTime.Now.Year;
|
||||||
public static int CurrentNextSeason => DateTime.Now.Year - (DateTime.Now.Month <= 3 ? 1 : 0);
|
public static int CurrentNextSeason => DateTime.Now.Year - (DateTime.Now.Month <= 3 ? 1 : 0);
|
||||||
public static int CurrentLastSeason => DateTime.Now.Year - (DateTime.Now.Month <= 7 ? 1 : 0);
|
public static int CurrentLastSeason => DateTime.Now.Year - (DateTime.Now.Month <= 6 ? 1 : 0);
|
||||||
public static int FollowingSeason => DateTime.Now.Year + (DateTime.Now.Month >= 11 ? 1 : 0);
|
public static int FollowingSeason => DateTime.Now.Year + (DateTime.Now.Month >= 11 ? 1 : 0);
|
||||||
public static DateTime Today => (DateTime.Now.Hour >= 3) ? DateTime.Today : DateTime.Today.AddDays(-1);
|
public static DateTime Today => (DateTime.Now.Hour >= 3) ? DateTime.Today : DateTime.Today.AddDays(-1);
|
||||||
|
|
||||||
@ -197,7 +197,7 @@ namespace Elwig.Helpers {
|
|||||||
}
|
}
|
||||||
|
|
||||||
public static void MailTo(string emailAddress) {
|
public static void MailTo(string emailAddress) {
|
||||||
MailTo(new string[] { emailAddress });
|
MailTo([emailAddress]);
|
||||||
}
|
}
|
||||||
|
|
||||||
public static void MailTo(IEnumerable<string> emailAddresses) {
|
public static void MailTo(IEnumerable<string> emailAddresses) {
|
||||||
@ -537,6 +537,11 @@ namespace Elwig.Helpers {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public static int GetEntityIdetifierForPk(params object?[] primaryKey) {
|
||||||
|
var pk = primaryKey.Select(k => k?.GetHashCode() ?? 0).ToArray();
|
||||||
|
return ((IStructuralEquatable)pk).GetHashCode(EqualityComparer<int>.Default);
|
||||||
|
}
|
||||||
|
|
||||||
public static int? GetEntityIdentifier(object? obj) {
|
public static int? GetEntityIdentifier(object? obj) {
|
||||||
if (obj == null) {
|
if (obj == null) {
|
||||||
return null;
|
return null;
|
||||||
@ -552,15 +557,15 @@ namespace Elwig.Helpers {
|
|||||||
}
|
}
|
||||||
|
|
||||||
public static Expression<Func<AreaCom, bool>> ActiveAreaCommitments() => ActiveAreaCommitments(CurrentYear);
|
public static Expression<Func<AreaCom, bool>> ActiveAreaCommitments() => ActiveAreaCommitments(CurrentYear);
|
||||||
public static Expression<Func<AreaCom, bool>> ActiveAreaCommitments(int yearTo) =>
|
public static Expression<Func<AreaCom, bool>> ActiveAreaCommitments(int year) =>
|
||||||
c => (c.YearFrom <= yearTo) && (c.YearTo == null || c.YearTo >= yearTo);
|
c => (c.YearFrom <= year) && (c.YearTo == null || c.YearTo >= year);
|
||||||
|
|
||||||
public static IQueryable<AreaCom> ActiveAreaCommitments(IQueryable<AreaCom> query) => ActiveAreaCommitments(query, CurrentYear);
|
public static IQueryable<AreaCom> ActiveAreaCommitments(IQueryable<AreaCom> query) => ActiveAreaCommitments(query, CurrentYear);
|
||||||
public static IQueryable<AreaCom> ActiveAreaCommitments(IQueryable<AreaCom> query, int yearTo) =>
|
public static IQueryable<AreaCom> ActiveAreaCommitments(IQueryable<AreaCom> query, int year) =>
|
||||||
query.Where(ActiveAreaCommitments(yearTo));
|
query.Where(ActiveAreaCommitments(year));
|
||||||
|
|
||||||
public static IEnumerable<AreaCom> ActiveAreaCommitments(IEnumerable<AreaCom> query) => ActiveAreaCommitments(query, CurrentYear);
|
public static IEnumerable<AreaCom> ActiveAreaCommitments(IEnumerable<AreaCom> query) => ActiveAreaCommitments(query, CurrentYear);
|
||||||
public static IEnumerable<AreaCom> ActiveAreaCommitments(IEnumerable<AreaCom> query, int yearTo) =>
|
public static IEnumerable<AreaCom> ActiveAreaCommitments(IEnumerable<AreaCom> query, int year) =>
|
||||||
query.Where(c => ActiveAreaCommitments(yearTo).Invoke(c));
|
query.Where(c => ActiveAreaCommitments(year).Invoke(c));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
using System;
|
using System;
|
||||||
using System.IO;
|
using System.IO;
|
||||||
using System.Text;
|
using System.Text;
|
||||||
using System.Threading;
|
using System.Threading;
|
||||||
@ -79,7 +79,7 @@ namespace Elwig.Helpers.Weighing {
|
|||||||
identNr = identNr.Length > 0 && identNr != "0" ? identNr : null;
|
identNr = identNr.Length > 0 && identNr != "0" ? identNr : null;
|
||||||
var parsedDate = DateOnly.Parse(date);
|
var parsedDate = DateOnly.Parse(date);
|
||||||
return new() {
|
return new() {
|
||||||
Weight = int.Parse(netto),
|
NetWeight = int.Parse(netto),
|
||||||
WeighingId = identNr,
|
WeighingId = identNr,
|
||||||
FullWeighingId = identNr != null ? $"{parsedDate:yyyy-MM-dd}/{identNr}" : null,
|
FullWeighingId = identNr != null ? $"{parsedDate:yyyy-MM-dd}/{identNr}" : null,
|
||||||
Date = parsedDate,
|
Date = parsedDate,
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
using System;
|
using System;
|
||||||
using System.IO;
|
using System.IO;
|
||||||
using System.IO.Ports;
|
using System.IO.Ports;
|
||||||
using System.Text;
|
using System.Text;
|
||||||
@ -69,13 +69,14 @@ namespace Elwig.Helpers.Weighing {
|
|||||||
var time = line[37..43];
|
var time = line[37..43];
|
||||||
|
|
||||||
identNr = identNr.Length > 0 && identNr != "0" ? identNr : null;
|
identNr = identNr.Length > 0 && identNr != "0" ? identNr : null;
|
||||||
var parsedDate = DateOnly.ParseExact(date, "yyyyMMdd");
|
|
||||||
return new() {
|
return new() {
|
||||||
Weight = int.Parse(netto),
|
GrossWeight = int.Parse(brutto),
|
||||||
|
TareWeight = int.Parse(tara),
|
||||||
|
NetWeight = int.Parse(netto),
|
||||||
WeighingId = identNr,
|
WeighingId = identNr,
|
||||||
FullWeighingId = identNr,
|
FullWeighingId = identNr,
|
||||||
Date = parsedDate,
|
Date = DateOnly.TryParseExact(date, "yyyyMMdd", out var d) ? d : null,
|
||||||
Time = TimeOnly.ParseExact(time, "HHmmss"),
|
Time = TimeOnly.TryParseExact(time, "HHmmss", out var t) ? t : null,
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1,8 +1,8 @@
|
|||||||
using System.Threading.Tasks;
|
using System.Threading.Tasks;
|
||||||
|
|
||||||
namespace Elwig.Helpers.Weighing {
|
namespace Elwig.Helpers.Weighing {
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Interface for controlling a a scale which responds to commands sent to it
|
/// Interface for controlling a weighing scale which responds to commands sent to it
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public interface ICommandScale : IScale {
|
public interface ICommandScale : IScale {
|
||||||
/// <summary>
|
/// <summary>
|
||||||
|
@ -1,6 +1,6 @@
|
|||||||
namespace Elwig.Helpers.Weighing {
|
namespace Elwig.Helpers.Weighing {
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Interface for controlling a a scale which automatically sends weighing updates
|
/// Interface for controlling a weighing scale which automatically sends weighing updates
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public interface IEventScale : IScale {
|
public interface IEventScale : IScale {
|
||||||
|
|
||||||
|
@ -2,7 +2,7 @@ using System;
|
|||||||
|
|
||||||
namespace Elwig.Helpers.Weighing {
|
namespace Elwig.Helpers.Weighing {
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Interface for controlling a industrial scale (industrial terminal, "IT")
|
/// Interface for controlling a industrial weighing scale (industrial terminal, "IT")
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public interface IScale : IDisposable {
|
public interface IScale : IDisposable {
|
||||||
/// <summary>
|
/// <summary>
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
using System.IO.Ports;
|
using System.IO.Ports;
|
||||||
using System.IO;
|
using System.IO;
|
||||||
using System.Net.Sockets;
|
using System.Net.Sockets;
|
||||||
using System;
|
using System;
|
||||||
|
@ -38,12 +38,12 @@ namespace Elwig.Helpers.Weighing {
|
|||||||
}
|
}
|
||||||
|
|
||||||
var error = line[1..3];
|
var error = line[1..3];
|
||||||
|
string msg = $"Unbekannter Fehler (Fehler code {error})";
|
||||||
if (error[0] == '0') {
|
if (error[0] == '0') {
|
||||||
if (error[1] != '0') {
|
if (error[1] != '0') {
|
||||||
throw new IOException($"Invalid response from scale (error code {error})");
|
throw new IOException($"Invalid response from scale (error code {error})");
|
||||||
}
|
}
|
||||||
} else if (error[0] == '1') {
|
} else if (error[0] == '1') {
|
||||||
string msg = $"Unbekannter Fehler (Fehler code {error})";
|
|
||||||
switch (error[1]) {
|
switch (error[1]) {
|
||||||
case '1': msg = "Allgemeiner Waagenfehler"; break;
|
case '1': msg = "Allgemeiner Waagenfehler"; break;
|
||||||
case '2': msg = "Waage in Überlast"; break;
|
case '2': msg = "Waage in Überlast"; break;
|
||||||
@ -53,8 +53,12 @@ namespace Elwig.Helpers.Weighing {
|
|||||||
case '7': msg = "Druckmuster enthält ungültiges Kommando"; break;
|
case '7': msg = "Druckmuster enthält ungültiges Kommando"; break;
|
||||||
}
|
}
|
||||||
throw new IOException($"Waagenfehler {error}: {msg}");
|
throw new IOException($"Waagenfehler {error}: {msg}");
|
||||||
|
} else if (error[0] == '2') {
|
||||||
|
switch (error[1]) {
|
||||||
|
case '0': msg = "Brutto negativ"; break;
|
||||||
|
}
|
||||||
|
throw new IOException($"Fehler {error}: {msg}");
|
||||||
} else if (error[0] == '3') {
|
} else if (error[0] == '3') {
|
||||||
string msg = $"Unbekannter Fehler (Fehler code {error})";
|
|
||||||
switch (error[1]) {
|
switch (error[1]) {
|
||||||
case '1': msg = "Übertragunsfehler"; break;
|
case '1': msg = "Übertragunsfehler"; break;
|
||||||
case '2': msg = "Ungültiger Befehl"; break;
|
case '2': msg = "Ungültiger Befehl"; break;
|
||||||
@ -98,7 +102,9 @@ namespace Elwig.Helpers.Weighing {
|
|||||||
identNr = identNr.Length > 0 && identNr != "0" ? identNr : null;
|
identNr = identNr.Length > 0 && identNr != "0" ? identNr : null;
|
||||||
var parsedDate = DateOnly.Parse(date);
|
var parsedDate = DateOnly.Parse(date);
|
||||||
return new() {
|
return new() {
|
||||||
Weight = int.Parse(netto),
|
GrossWeight = int.Parse(brutto),
|
||||||
|
TareWeight = int.Parse(tara),
|
||||||
|
NetWeight = int.Parse(netto),
|
||||||
WeighingId = identNr,
|
WeighingId = identNr,
|
||||||
FullWeighingId = identNr != null ? $"{parsedDate:yyyy-MM-dd}/{identNr}" : null,
|
FullWeighingId = identNr != null ? $"{parsedDate:yyyy-MM-dd}/{identNr}" : null,
|
||||||
Date = parsedDate,
|
Date = parsedDate,
|
||||||
|
@ -1,12 +1,7 @@
|
|||||||
using System;
|
using System;
|
||||||
|
|
||||||
namespace Elwig.Helpers.Weighing {
|
namespace Elwig.Helpers.Weighing {
|
||||||
public class WeighingEventArgs : EventArgs {
|
public class WeighingEventArgs(WeighingResult result) : EventArgs {
|
||||||
|
public readonly WeighingResult Result = result;
|
||||||
public WeighingResult Result { get; set; }
|
|
||||||
|
|
||||||
public WeighingEventArgs(WeighingResult result) {
|
|
||||||
Result = result;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -1,14 +1,25 @@
|
|||||||
using System;
|
using System;
|
||||||
|
using System.Text.Json.Nodes;
|
||||||
|
|
||||||
namespace Elwig.Helpers.Weighing {
|
namespace Elwig.Helpers.Weighing {
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Result of a weighing process on an industrial scale
|
/// Result of a weighing process on an industrial weighing scale
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public struct WeighingResult {
|
public struct WeighingResult {
|
||||||
|
/// <summary>
|
||||||
|
/// Measured gross weight in kg
|
||||||
|
/// </summary>
|
||||||
|
public int? GrossWeight;
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Measured tare weight in kg
|
||||||
|
/// </summary>
|
||||||
|
public int? TareWeight;
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Measured net weight in kg
|
/// Measured net weight in kg
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public int? Weight;
|
public int? NetWeight;
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Weighing id (or IdentNr) provided by the scale
|
/// Weighing id (or IdentNr) provided by the scale
|
||||||
@ -30,12 +41,22 @@ namespace Elwig.Helpers.Weighing {
|
|||||||
/// </summary>
|
/// </summary>
|
||||||
public TimeOnly? Time;
|
public TimeOnly? Time;
|
||||||
|
|
||||||
/// <returns><Weight/WeighingId/Date/Time></returns>
|
/// <returns><[GrossWeight-TaraWeight=]NetWeight/WeighingId/Date/Time></returns>
|
||||||
public override readonly string ToString() {
|
public override readonly string ToString() {
|
||||||
var w = Weight != null ? $"{Weight}kg" : "";
|
var w = NetWeight != null ? (GrossWeight != null && TareWeight != null ? $"{GrossWeight}-{TareWeight}=" : "") + $"{NetWeight}kg" : "";
|
||||||
return $"<{w}/{WeighingId}/{Date:yyyy-MM-dd}/{Time:HH:mm}>";
|
return $"<{w}/{WeighingId}/{Date:yyyy-MM-dd}/{Time:HH:mm}>";
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public readonly JsonObject ToJson() {
|
||||||
|
var obj = new JsonObject();
|
||||||
|
if (FullWeighingId != null) obj["id"] = FullWeighingId;
|
||||||
|
if (WeighingId != null) obj["nr"] = int.Parse(WeighingId);
|
||||||
|
if (Date != null) obj["date"] = $"{Date:yyyy-MM-dd}";
|
||||||
|
if (Time != null) obj["time"] = $"{Time:HH:mm:ss}";
|
||||||
|
if (GrossWeight != null) obj["gross_weight"] = GrossWeight;
|
||||||
|
if (TareWeight != null) obj["tare_weight"] = TareWeight;
|
||||||
|
if (NetWeight != null) obj["net_weight"] = NetWeight;
|
||||||
|
return obj;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
using Microsoft.EntityFrameworkCore;
|
using Microsoft.EntityFrameworkCore;
|
||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
using System.ComponentModel.DataAnnotations.Schema;
|
using System.ComponentModel.DataAnnotations.Schema;
|
||||||
using System.Linq;
|
using System.Linq;
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
using Elwig.Helpers;
|
using Elwig.Helpers;
|
||||||
using Elwig.Helpers.Billing;
|
using Elwig.Helpers.Billing;
|
||||||
using Microsoft.EntityFrameworkCore;
|
using Microsoft.EntityFrameworkCore;
|
||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
using Elwig.Helpers.Billing;
|
using Elwig.Helpers.Billing;
|
||||||
using Elwig.Models.Entities;
|
using Elwig.Models.Entities;
|
||||||
using Microsoft.EntityFrameworkCore;
|
using Microsoft.EntityFrameworkCore;
|
||||||
using System;
|
using System;
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
using System;
|
using System;
|
||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
using System.Linq;
|
using System.Linq;
|
||||||
using System.Reflection;
|
using System.Reflection;
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
using Elwig.Models.Entities;
|
using Elwig.Models.Entities;
|
||||||
using Microsoft.EntityFrameworkCore;
|
using Microsoft.EntityFrameworkCore;
|
||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
using System.Linq;
|
using System.Linq;
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
using Elwig.Documents;
|
using Elwig.Documents;
|
||||||
using Elwig.Models.Entities;
|
using Elwig.Models.Entities;
|
||||||
using Microsoft.EntityFrameworkCore;
|
using Microsoft.EntityFrameworkCore;
|
||||||
using System;
|
using System;
|
||||||
@ -14,16 +14,18 @@ namespace Elwig.Models.Dtos {
|
|||||||
("Pos", "Pos.", null, 10),
|
("Pos", "Pos.", null, 10),
|
||||||
("Date", "Datum", null, 20),
|
("Date", "Datum", null, 20),
|
||||||
("Time", "Zeit", null, 20),
|
("Time", "Zeit", null, 20),
|
||||||
|
("DeliveryBranch", "Zweigstelle", null, 30),
|
||||||
("MgNr", "MgNr.", null, 12),
|
("MgNr", "MgNr.", null, 12),
|
||||||
("Name1", "Name", null, 40),
|
("Name1", "Name", null, 40),
|
||||||
("Name2", "Vorname", null, 40),
|
("Name2", "Vorname", null, 40),
|
||||||
|
("MemberBranch", "Stamm-Zwst.", null, 30),
|
||||||
("SortId", "Sorte", null, 10),
|
("SortId", "Sorte", null, 10),
|
||||||
("AttrId", "Attr.", null, 15),
|
("AttrId", "Attr.", null, 15),
|
||||||
("CultId", "Bewirt.", null, 15),
|
("CultId", "Bewirt.", null, 15),
|
||||||
("QualId", "Qualität", null, 15),
|
("QualId", "Qualität", null, 15),
|
||||||
("Gradation", "Gradation", "°Oe|°KMW", 40),
|
("Gradation", "Gradation", "°Oe|°KMW", 40),
|
||||||
("Weight", "Gewicht", "kg", 20),
|
("Weight", "Gewicht", "kg", 20),
|
||||||
("NetGross", "bto./nto.", null, 20),
|
("IsNetWeight", "Gerebelt", null, 20),
|
||||||
("HkId", "Herkunft", null, 20),
|
("HkId", "Herkunft", null, 20),
|
||||||
("Modifiers", "Zu-/Abschläge", null, 40),
|
("Modifiers", "Zu-/Abschläge", null, 40),
|
||||||
("Comment", "Anmerkung", null, 60),
|
("Comment", "Anmerkung", null, 60),
|
||||||
@ -35,7 +37,7 @@ namespace Elwig.Models.Dtos {
|
|||||||
|
|
||||||
public static async Task<DeliveryJournalData> FromQuery(IQueryable<DeliveryPart> query, List<string> filterNames) {
|
public static async Task<DeliveryJournalData> FromQuery(IQueryable<DeliveryPart> query, List<string> filterNames) {
|
||||||
return new((await query
|
return new((await query
|
||||||
.Include(p => p.Delivery.Member)
|
.Include(p => p.Delivery.Member.Branch)
|
||||||
.Include(p => p.Delivery.Branch)
|
.Include(p => p.Delivery.Branch)
|
||||||
.Include(p => p.PartModifiers).ThenInclude(m => m.Modifier)
|
.Include(p => p.PartModifiers).ThenInclude(m => m.Modifier)
|
||||||
.Include(p => p.Variety)
|
.Include(p => p.Variety)
|
||||||
@ -53,10 +55,12 @@ namespace Elwig.Models.Dtos {
|
|||||||
public int Pos;
|
public int Pos;
|
||||||
public DateOnly Date;
|
public DateOnly Date;
|
||||||
public TimeOnly? Time;
|
public TimeOnly? Time;
|
||||||
|
public string DeliveryBranch;
|
||||||
public int MgNr;
|
public int MgNr;
|
||||||
public string Name1;
|
public string Name1;
|
||||||
public string Name2;
|
public string Name2;
|
||||||
public string AdministrativeName;
|
public string AdministrativeName;
|
||||||
|
public string? MemberBranch;
|
||||||
public string SortId;
|
public string SortId;
|
||||||
public string Variety;
|
public string Variety;
|
||||||
public string? AttrId;
|
public string? AttrId;
|
||||||
@ -71,7 +75,6 @@ namespace Elwig.Models.Dtos {
|
|||||||
public double Oe => Gradation.Oe;
|
public double Oe => Gradation.Oe;
|
||||||
public int Weight { get; set; }
|
public int Weight { get; set; }
|
||||||
public bool IsNetWeight;
|
public bool IsNetWeight;
|
||||||
public string NetGross => IsNetWeight ? "n" : "b";
|
|
||||||
public string? Modifiers;
|
public string? Modifiers;
|
||||||
public string? Comment;
|
public string? Comment;
|
||||||
|
|
||||||
@ -83,10 +86,12 @@ namespace Elwig.Models.Dtos {
|
|||||||
Pos = p.DPNr;
|
Pos = p.DPNr;
|
||||||
Date = d.Date;
|
Date = d.Date;
|
||||||
Time = d.Time;
|
Time = d.Time;
|
||||||
|
DeliveryBranch = d.Branch.Name;
|
||||||
MgNr = m.MgNr;
|
MgNr = m.MgNr;
|
||||||
Name1 = m.FamilyName;
|
Name1 = m.FamilyName;
|
||||||
Name2 = m.AdministrativeName2;
|
Name2 = m.AdministrativeName2;
|
||||||
AdministrativeName = m.AdministrativeName;
|
AdministrativeName = m.AdministrativeName;
|
||||||
|
MemberBranch = m.Branch?.Name;
|
||||||
|
|
||||||
SortId = p.SortId;
|
SortId = p.SortId;
|
||||||
Variety = p.Variety.Name;
|
Variety = p.Variety.Name;
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
using Microsoft.EntityFrameworkCore;
|
using Microsoft.EntityFrameworkCore;
|
||||||
using System;
|
using System;
|
||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
using System.ComponentModel.DataAnnotations.Schema;
|
using System.ComponentModel.DataAnnotations.Schema;
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
using Elwig.Documents;
|
using Elwig.Documents;
|
||||||
using Elwig.Models.Entities;
|
using Elwig.Models.Entities;
|
||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
using System.Threading.Tasks;
|
using System.Threading.Tasks;
|
||||||
@ -34,7 +34,11 @@ namespace Elwig.Models.Dtos {
|
|||||||
("UstIdNr", "UID", null, 25),
|
("UstIdNr", "UID", null, 25),
|
||||||
("Iban", "IBAN", null, 45),
|
("Iban", "IBAN", null, 45),
|
||||||
("Bic", "BIC", null, 30),
|
("Bic", "BIC", null, 30),
|
||||||
("Comment", "Anmerkung", null, 60),
|
("TelNrLandline", "Festnetz", null, 35),
|
||||||
|
("TelNrMobile", "Mobil", null, 35),
|
||||||
|
("EmailAddress", "E-Mail", null, 70),
|
||||||
|
("AdditionalContact", "Weitere", null, 70),
|
||||||
|
("Comment", "Anmerkung", null, 80),
|
||||||
];
|
];
|
||||||
|
|
||||||
public MemberListData(IEnumerable<MemberListRow> rows, List<string> filterNames) :
|
public MemberListData(IEnumerable<MemberListRow> rows, List<string> filterNames) :
|
||||||
@ -48,6 +52,9 @@ namespace Elwig.Models.Dtos {
|
|||||||
.Include(m => m.Branch)
|
.Include(m => m.Branch)
|
||||||
.Include(m => m.PostalDest.AtPlz!.Ort)
|
.Include(m => m.PostalDest.AtPlz!.Ort)
|
||||||
.Include(m => m.BillingAddress!.PostalDest.AtPlz!.Ort)
|
.Include(m => m.BillingAddress!.PostalDest.AtPlz!.Ort)
|
||||||
|
.Include(m => m.TelephoneNumbers)
|
||||||
|
.Include(m => m.EmailAddresses)
|
||||||
|
.AsSplitQuery()
|
||||||
.ToListAsync()).Select(m => new MemberListRow(m, areaCom[m.MgNr])), filterNames);
|
.ToListAsync()).Select(m => new MemberListRow(m, areaCom[m.MgNr])), filterNames);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -76,6 +83,10 @@ namespace Elwig.Models.Dtos {
|
|||||||
public bool IsActive;
|
public bool IsActive;
|
||||||
public DateOnly? EntryDate;
|
public DateOnly? EntryDate;
|
||||||
public DateOnly? ExitDate;
|
public DateOnly? ExitDate;
|
||||||
|
public string? TelNrLandline;
|
||||||
|
public string? TelNrMobile;
|
||||||
|
public string? EmailAddress;
|
||||||
|
public string? AdditionalContact;
|
||||||
public string? Comment;
|
public string? Comment;
|
||||||
|
|
||||||
public MemberListRow(Member m, int? areaCom = null) {
|
public MemberListRow(Member m, int? areaCom = null) {
|
||||||
@ -103,6 +114,15 @@ namespace Elwig.Models.Dtos {
|
|||||||
IsActive = m.IsActive;
|
IsActive = m.IsActive;
|
||||||
EntryDate = m.EntryDate;
|
EntryDate = m.EntryDate;
|
||||||
ExitDate = m.ExitDate;
|
ExitDate = m.ExitDate;
|
||||||
|
TelNrLandline = m.TelephoneNumbers.OrderBy(n => n.Nr).FirstOrDefault(n => n.Type == "landline")?.Number;
|
||||||
|
TelNrMobile = m.TelephoneNumbers.OrderBy(n => n.Nr).FirstOrDefault(n => n.Type == "mobile")?.Number;
|
||||||
|
EmailAddress = m.EmailAddresses.OrderBy(a => a.Nr).FirstOrDefault()?.Address;
|
||||||
|
AdditionalContact = string.Join(", ", m.TelephoneNumbers
|
||||||
|
.OrderBy(n => n.Nr)
|
||||||
|
.Select(n => n.Number)
|
||||||
|
.Except([TelNrLandline, TelNrMobile])
|
||||||
|
.Distinct()
|
||||||
|
.Concat(m.EmailAddresses.OrderBy(a => a.Nr).Select(a => a.Address).Except([EmailAddress])));
|
||||||
Comment = m.Comment;
|
Comment = m.Comment;
|
||||||
AreaCommitment = areaCom == 0 ? null : areaCom;
|
AreaCommitment = areaCom == 0 ? null : areaCom;
|
||||||
}
|
}
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
using Microsoft.EntityFrameworkCore;
|
using Microsoft.EntityFrameworkCore;
|
||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
using System.ComponentModel.DataAnnotations.Schema;
|
using System.ComponentModel.DataAnnotations.Schema;
|
||||||
using System.Threading.Tasks;
|
using System.Threading.Tasks;
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
using Elwig.Documents;
|
using Elwig.Documents;
|
||||||
using Elwig.Helpers;
|
using Elwig.Helpers;
|
||||||
using Elwig.Models.Entities;
|
using Elwig.Models.Entities;
|
||||||
using Microsoft.EntityFrameworkCore;
|
using Microsoft.EntityFrameworkCore;
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
using Elwig.Models.Entities;
|
using Elwig.Models.Entities;
|
||||||
using Microsoft.EntityFrameworkCore;
|
using Microsoft.EntityFrameworkCore;
|
||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
using System.ComponentModel.DataAnnotations.Schema;
|
using System.ComponentModel.DataAnnotations.Schema;
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
using Elwig.Models.Entities;
|
using Elwig.Models.Entities;
|
||||||
using Microsoft.EntityFrameworkCore;
|
using Microsoft.EntityFrameworkCore;
|
||||||
using System;
|
using System;
|
||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
|
@ -1,8 +1,10 @@
|
|||||||
using Elwig.Helpers;
|
using Elwig.Helpers;
|
||||||
using Microsoft.EntityFrameworkCore;
|
using Microsoft.EntityFrameworkCore;
|
||||||
|
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.Text.Json.Nodes;
|
||||||
|
|
||||||
namespace Elwig.Models.Entities {
|
namespace Elwig.Models.Entities {
|
||||||
[Table("delivery_part"), PrimaryKey("Year", "DId", "DPNr")]
|
[Table("delivery_part"), PrimaryKey("Year", "DId", "DPNr")]
|
||||||
@ -99,8 +101,26 @@ namespace Elwig.Models.Entities {
|
|||||||
[Column("scale_id")]
|
[Column("scale_id")]
|
||||||
public string? ScaleId { get; set; }
|
public string? ScaleId { get; set; }
|
||||||
|
|
||||||
[Column("weighing_id")]
|
[Column("weighing_data")]
|
||||||
public string? WeighingId { get; set; }
|
public string? WeighingData { get; set; }
|
||||||
|
[NotMapped]
|
||||||
|
public (string? Id, int? Gross, int? Tare, int? Net, DateOnly? Date, TimeOnly? Time) WeighingInfo {
|
||||||
|
get {
|
||||||
|
try {
|
||||||
|
var obj = JsonNode.Parse(WeighingData!)!.AsObject();
|
||||||
|
return (
|
||||||
|
obj["id"]?.AsValue().GetValue<string>(),
|
||||||
|
obj["gross_weight"]?.AsValue().GetValue<int>(),
|
||||||
|
obj["tare_weight"]?.AsValue().GetValue<int>(),
|
||||||
|
obj["net_weight"]?.AsValue().GetValue<int>(),
|
||||||
|
DateOnly.TryParseExact(obj["date"]?.AsValue().GetValue<string>(), "yyyy-MM-dd", out var d) ? d : null,
|
||||||
|
TimeOnly.TryParseExact(obj["time"]?.AsValue().GetValue<string>(), ["HH:mm:ss", "HH:mm"], out var t) ? t : null
|
||||||
|
);
|
||||||
|
} catch {
|
||||||
|
return (null, null, null, null, null, null);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
[Column("weighing_reason")]
|
[Column("weighing_reason")]
|
||||||
public string? WeighingReason { get; set; }
|
public string? WeighingReason { get; set; }
|
||||||
|
@ -156,8 +156,8 @@ namespace Elwig.Models.Entities {
|
|||||||
[InverseProperty(nameof(AreaCom.Member))]
|
[InverseProperty(nameof(AreaCom.Member))]
|
||||||
public virtual ICollection<AreaCom> AreaCommitments { get; private set; } = null!;
|
public virtual ICollection<AreaCom> AreaCommitments { get; private set; } = null!;
|
||||||
|
|
||||||
public IQueryable<AreaCom> ActiveAreaCommitments(AppDbContext ctx) {
|
public IQueryable<AreaCom> ActiveAreaCommitments(AppDbContext ctx, int? year = null) {
|
||||||
return ctx.AreaCommitments.Where(c => c.MgNr == MgNr).Where(Utils.ActiveAreaCommitments());
|
return ctx.AreaCommitments.Where(c => c.MgNr == MgNr).Where(Utils.ActiveAreaCommitments(year ?? Utils.CurrentYear));
|
||||||
}
|
}
|
||||||
|
|
||||||
[InverseProperty(nameof(BillingAddr.Member))]
|
[InverseProperty(nameof(BillingAddr.Member))]
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
using Microsoft.EntityFrameworkCore;
|
using Microsoft.EntityFrameworkCore;
|
||||||
using System;
|
using System;
|
||||||
using System.ComponentModel.DataAnnotations.Schema;
|
using System.ComponentModel.DataAnnotations.Schema;
|
||||||
|
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
using Elwig.Helpers;
|
using Elwig.Helpers;
|
||||||
using Microsoft.EntityFrameworkCore;
|
using Microsoft.EntityFrameworkCore;
|
||||||
using System.ComponentModel.DataAnnotations.Schema;
|
using System.ComponentModel.DataAnnotations.Schema;
|
||||||
|
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
namespace Elwig.Models {
|
namespace Elwig.Models {
|
||||||
public interface IDelivery {
|
public interface IDelivery {
|
||||||
int Weight { get; }
|
int Weight { get; }
|
||||||
double Kmw { get; }
|
double Kmw { get; }
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
<?xml version="1.0" encoding="utf-8"?>
|
<?xml version="1.0" encoding="utf-8"?>
|
||||||
<!--
|
<!--
|
||||||
https://go.microsoft.com/fwlink/?LinkID=208121.
|
https://go.microsoft.com/fwlink/?LinkID=208121.
|
||||||
-->
|
-->
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
-- schema version 23 to 24
|
-- schema version 23 to 24
|
||||||
|
|
||||||
ALTER TABLE modifier DROP COLUMN standard;
|
ALTER TABLE modifier DROP COLUMN standard;
|
||||||
ALTER TABLE modifier DROP COLUMN quick_select;
|
ALTER TABLE modifier DROP COLUMN quick_select;
|
||||||
|
4
Elwig/Resources/Sql/24-25.sql
Normal file
4
Elwig/Resources/Sql/24-25.sql
Normal file
@ -0,0 +1,4 @@
|
|||||||
|
-- schema version 24 to 25
|
||||||
|
|
||||||
|
ALTER TABLE delivery_part RENAME COLUMN weighing_id TO weighing_data;
|
||||||
|
UPDATE delivery_part SET weighing_data = '{"id":"' || weighing_data || '","nr":' || SUBSTR(weighing_data, INSTR(weighing_data, '/') + 1) || '}';
|
243
Elwig/Services/AreaComService.cs
Normal file
243
Elwig/Services/AreaComService.cs
Normal file
@ -0,0 +1,243 @@
|
|||||||
|
using Elwig.Helpers;
|
||||||
|
using Elwig.Models.Entities;
|
||||||
|
using Elwig.ViewModels;
|
||||||
|
using Microsoft.EntityFrameworkCore;
|
||||||
|
using System.Collections.Generic;
|
||||||
|
using System.Linq;
|
||||||
|
using System.Threading.Tasks;
|
||||||
|
using System.Windows.Controls;
|
||||||
|
using System.Windows;
|
||||||
|
|
||||||
|
namespace Elwig.Services {
|
||||||
|
public static class AreaComService {
|
||||||
|
|
||||||
|
public static async Task InitInputs(this AreaComAdminViewModel vm) {
|
||||||
|
using var ctx = new AppDbContext();
|
||||||
|
vm.FbNr = await ctx.NextFbNr();
|
||||||
|
vm.MgNr = vm.FilterMember.MgNr;
|
||||||
|
vm.YearFrom = Utils.CurrentYear;
|
||||||
|
vm.WineCult = null;
|
||||||
|
}
|
||||||
|
|
||||||
|
public static void ClearInputs(this AreaComAdminViewModel vm) {
|
||||||
|
}
|
||||||
|
|
||||||
|
public static void FillInputs(this AreaComAdminViewModel vm, AreaCom a) {
|
||||||
|
vm.FbNr = a.FbNr;
|
||||||
|
vm.MgNr = a.MgNr;
|
||||||
|
vm.YearFrom = a.YearFrom;
|
||||||
|
vm.YearTo = a.YearTo;
|
||||||
|
vm.AreaComType = ControlUtils.GetItemFromSourceWithPk(vm.AreaComTypeSource, a.VtrgId) as AreaComType;
|
||||||
|
vm.WineCult = ControlUtils.GetItemFromSourceWithPk(vm.WineCultSource, a.CultId) as WineCult;
|
||||||
|
vm.Comment = a.Comment;
|
||||||
|
vm.Kg = ControlUtils.GetItemFromSourceWithPk(vm.KgSource, a.KgNr) as AT_Kg;
|
||||||
|
vm.Rd = ControlUtils.GetItemFromSourceWithPk(vm.RdSource, a.KgNr, a.RdNr) as WbRd;
|
||||||
|
vm.GstNr = a.GstNr;
|
||||||
|
vm.Area = a.Area;
|
||||||
|
}
|
||||||
|
|
||||||
|
public static async Task<(List<string>, IQueryable<AreaCom>, List<string>)> GetFilters(this AreaComAdminViewModel vm, AppDbContext ctx) {
|
||||||
|
List<string> filterNames = [];
|
||||||
|
IQueryable<AreaCom> areaComQuery = ctx.AreaCommitments.Where(a => a.MgNr == vm.FilterMember.MgNr).OrderBy(a => a.FbNr);
|
||||||
|
if (vm.ShowOnlyActiveAreaComs) {
|
||||||
|
areaComQuery = Utils.ActiveAreaCommitments(areaComQuery, Utils.CurrentLastSeason);
|
||||||
|
filterNames.Add($"laufend {Utils.CurrentLastSeason}");
|
||||||
|
}
|
||||||
|
|
||||||
|
var filterVar = new List<string>();
|
||||||
|
var filterNotVar = new List<string>();
|
||||||
|
var filterAttr = new List<string>();
|
||||||
|
var filterNotAttr = new List<string>();
|
||||||
|
|
||||||
|
var filter = vm.TextFilter;
|
||||||
|
if (filter.Count > 0) {
|
||||||
|
var var = await ctx.WineVarieties.ToDictionaryAsync(v => v.SortId, v => v);
|
||||||
|
var attr = await ctx.WineAttributes.ToDictionaryAsync(a => a.Name.ToLower().Split(" ")[0], a => a);
|
||||||
|
var attrId = await ctx.WineAttributes.ToDictionaryAsync(a => a.AttrId, a => a);
|
||||||
|
|
||||||
|
for (int i = 0; i < filter.Count; i++) {
|
||||||
|
var e = filter[i];
|
||||||
|
if (e.Length == 2 && var.ContainsKey(e.ToUpper())) {
|
||||||
|
filterVar.Add(e.ToUpper());
|
||||||
|
filter.RemoveAt(i--);
|
||||||
|
filterNames.Add(var[e.ToUpper()].Name);
|
||||||
|
} else if (e.Length == 3 && e[0] == '!' && var.ContainsKey(e[1..].ToUpper())) {
|
||||||
|
filterNotVar.Add(e[1..].ToUpper());
|
||||||
|
filter.RemoveAt(i--);
|
||||||
|
filterNames.Add($"ohne {var[e.ToUpper()].Name}");
|
||||||
|
} else if (attr.ContainsKey(e.ToLower())) {
|
||||||
|
var a = attr[e.ToLower()];
|
||||||
|
filterAttr.Add(a.AttrId);
|
||||||
|
filter.RemoveAt(i--);
|
||||||
|
filterNames.Add($"Attribut {a.Name}");
|
||||||
|
} else if (e[0] == '!' && attr.ContainsKey(e[1..].ToLower())) {
|
||||||
|
var a = attr[e[1..].ToLower()];
|
||||||
|
filterNotAttr.Add(a.AttrId);
|
||||||
|
filter.RemoveAt(i--);
|
||||||
|
filterNames.Add($"ohne Attribut {a.Name}");
|
||||||
|
} else if (e.Length > 2 && var.ContainsKey(e.ToUpper()[..2]) && attrId.ContainsKey(e[2..].ToUpper())) {
|
||||||
|
filterVar.Add(e[..2].ToUpper());
|
||||||
|
filterAttr.Add(e[2..].ToUpper());
|
||||||
|
filter.RemoveAt(i--);
|
||||||
|
filterNames.Add(var[e[..2].ToUpper()].Name);
|
||||||
|
filterNames.Add($"Attribut {attrId[e[2..].ToUpper()].Name}");
|
||||||
|
} else if (e[0] == '!' && e.Length > 3 && var.ContainsKey(e.ToUpper()[1..3]) && attrId.ContainsKey(e[3..].ToUpper())) {
|
||||||
|
filterNotVar.Add(e[1..3].ToUpper());
|
||||||
|
filterNotAttr.Add(e[3..].ToUpper());
|
||||||
|
filter.RemoveAt(i--);
|
||||||
|
filterNames.Add($"ohne {var[e[1..3].ToUpper()].Name}");
|
||||||
|
filterNames.Add($"ohne Attribut {attrId[e[3..].ToUpper()].Name}");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (filterVar.Count > 0) areaComQuery = areaComQuery.Where(a => filterVar.Contains(a.AreaComType.WineVar.SortId));
|
||||||
|
if (filterNotVar.Count > 0) areaComQuery = areaComQuery.Where(a => !filterNotVar.Contains(a.AreaComType.WineVar.SortId));
|
||||||
|
if (filterAttr.Count > 0) areaComQuery = areaComQuery.Where(a => a.AreaComType.WineAttr!.AttrId != null && filterAttr.Contains(a.AreaComType.WineAttr.AttrId));
|
||||||
|
if (filterNotAttr.Count > 0) areaComQuery = areaComQuery.Where(a => a.AreaComType.WineAttr!.AttrId == null || !filterNotAttr.Contains(a.AreaComType.WineAttr.AttrId));
|
||||||
|
}
|
||||||
|
|
||||||
|
return (filterNames, areaComQuery, filter);
|
||||||
|
}
|
||||||
|
|
||||||
|
public static async Task<int> UpdateAreaCommitment(this AreaComAdminViewModel vm, int? oldFbNr) {
|
||||||
|
using var ctx = new AppDbContext();
|
||||||
|
int newFbNr = (int)vm.FbNr!;
|
||||||
|
|
||||||
|
var a = new AreaCom {
|
||||||
|
FbNr = oldFbNr ?? newFbNr,
|
||||||
|
MgNr = (int)vm.MgNr!,
|
||||||
|
YearFrom = (int)vm.YearFrom!,
|
||||||
|
YearTo = vm.YearTo,
|
||||||
|
VtrgId = vm.AreaComType!.VtrgId,
|
||||||
|
CultId = vm.WineCult?.CultId,
|
||||||
|
Comment = string.IsNullOrEmpty(vm.Comment) ? null : vm.Comment,
|
||||||
|
KgNr = vm.Kg!.KgNr,
|
||||||
|
RdNr = vm.Rd?.RdNr,
|
||||||
|
GstNr = vm.GstNr!.Trim(),
|
||||||
|
Area = (int)vm.Area!,
|
||||||
|
};
|
||||||
|
|
||||||
|
if (vm.Rd?.RdNr == 0) {
|
||||||
|
vm.Rd.RdNr = await ctx.NextRdNr(a.KgNr);
|
||||||
|
a.RdNr = vm.Rd.RdNr;
|
||||||
|
ctx.Add(vm.Rd);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (oldFbNr != null) {
|
||||||
|
ctx.Update(a);
|
||||||
|
} else {
|
||||||
|
ctx.Add(a);
|
||||||
|
}
|
||||||
|
|
||||||
|
await ctx.SaveChangesAsync();
|
||||||
|
|
||||||
|
if (newFbNr != a.FbNr) {
|
||||||
|
await ctx.Database.ExecuteSqlAsync($"UPDATE area_commitment SET fbnr = {newFbNr} WHERE fbnr = {oldFbNr}");
|
||||||
|
}
|
||||||
|
|
||||||
|
await 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) {
|
||||||
|
var tb = new TextBlock() {
|
||||||
|
Text = text,
|
||||||
|
TextAlignment = alignRight ? TextAlignment.Right : alignCenter ? TextAlignment.Center : TextAlignment.Left,
|
||||||
|
Margin = new(0, 12 * row, 0, 0),
|
||||||
|
FontWeight = bold ? FontWeights.Bold : FontWeights.Normal,
|
||||||
|
};
|
||||||
|
tb.SetValue(Grid.ColumnProperty, col);
|
||||||
|
tb.SetValue(Grid.ColumnSpanProperty, colSpan);
|
||||||
|
grid.Children.Add(tb);
|
||||||
|
}
|
||||||
|
|
||||||
|
private static void AddToolTipRow(Grid grid, int row, string? h1, string? h2, int area, int? min, int? max) {
|
||||||
|
var bold = h2 == null;
|
||||||
|
if (h1 != null) AddToolTipCell(grid, h1 + ":", row, 0, (h2 == null) ? 2 : 1, bold);
|
||||||
|
if (h2 != null) AddToolTipCell(grid, h2 + ":", row, 1, 1, bold);
|
||||||
|
AddToolTipCell(grid, $"{area:N0} m²", row, 2, 1, bold, true);
|
||||||
|
AddToolTipCell(grid, min == null ? "" : $"{min:N0} kg", row, 3, 1, bold, true);
|
||||||
|
AddToolTipCell(grid, max == null ? "" : $"{max:N0} kg", row, 4, 1, bold, true);
|
||||||
|
}
|
||||||
|
|
||||||
|
public static async Task<(string, Grid)> GenerateToolTip(IQueryable<AreaCom> areaComs, int maxKgPerHa) {
|
||||||
|
var grid = new Grid();
|
||||||
|
grid.ColumnDefinitions.Add(new() { Width = new(10) });
|
||||||
|
grid.ColumnDefinitions.Add(new() { Width = new(60) });
|
||||||
|
grid.ColumnDefinitions.Add(new() { Width = new(80) });
|
||||||
|
grid.ColumnDefinitions.Add(new() { Width = new(80) });
|
||||||
|
grid.ColumnDefinitions.Add(new() { Width = new(80) });
|
||||||
|
AddToolTipCell(grid, "Lieferpflicht", 0, 3, 1, false, false, true);
|
||||||
|
AddToolTipCell(grid, "Lieferrecht", 0, 4, 1, false, false, true);
|
||||||
|
var text = "-";
|
||||||
|
|
||||||
|
var area = await areaComs.SumAsync(p => p.Area);
|
||||||
|
text = $"{area:N0} m²";
|
||||||
|
AddToolTipRow(grid, 1, "Geb. Fläche", null, area, null, null);
|
||||||
|
|
||||||
|
if (await areaComs.AnyAsync()) {
|
||||||
|
var attrGroups = await areaComs
|
||||||
|
.Where(c => c.AreaComType.WineAttr != null)
|
||||||
|
.GroupBy(c => c.AreaComType.WineAttr!.Name)
|
||||||
|
.Select(g => new {
|
||||||
|
Attr = g.Key,
|
||||||
|
Area = g.Sum(c => c.Area),
|
||||||
|
Min = g.Sum(c => c.Area * (c.AreaComType.MinKgPerHa ?? 0) / 10_000),
|
||||||
|
Max = g.Sum(c => c.Area * (c.AreaComType.WineAttr!.MaxKgPerHa ?? maxKgPerHa) / 10_000),
|
||||||
|
})
|
||||||
|
.OrderByDescending(g => g.Area)
|
||||||
|
.ThenBy(g => g.Attr)
|
||||||
|
.ToListAsync();
|
||||||
|
var groups = await areaComs
|
||||||
|
.Where(c => c.AreaComType.WineAttr != null)
|
||||||
|
.GroupBy(c => new {
|
||||||
|
Attr = c.AreaComType.WineAttr!.Name,
|
||||||
|
c.AreaComType.SortId,
|
||||||
|
})
|
||||||
|
.Select(g => new {
|
||||||
|
g.Key.Attr,
|
||||||
|
g.Key.SortId,
|
||||||
|
Area = g.Sum(c => c.Area),
|
||||||
|
Min = g.Sum(c => c.Area * (c.AreaComType.MinKgPerHa ?? 0) / 10_000),
|
||||||
|
Max = g.Sum(c => c.Area * (c.AreaComType.WineAttr!.MaxKgPerHa ?? maxKgPerHa) / 10_000),
|
||||||
|
})
|
||||||
|
.OrderByDescending(g => g.Area)
|
||||||
|
.ThenBy(g => g.Attr)
|
||||||
|
.ThenBy(g => g.SortId)
|
||||||
|
.ToListAsync();
|
||||||
|
|
||||||
|
var noAttr = await areaComs
|
||||||
|
.Where(c => c.AreaComType.WineAttr == null || !c.AreaComType.WineAttr.IsStrict)
|
||||||
|
.GroupBy(c => c.AreaComType.SortId)
|
||||||
|
.Select(g => new {
|
||||||
|
SortId = g.Key,
|
||||||
|
Area = g.Sum(c => c.Area),
|
||||||
|
Min = g.Sum(c => c.Area * (c.AreaComType.MinKgPerHa ?? 0) / 10_000),
|
||||||
|
Max = g.Sum(c => c.Area * (c.AreaComType.WineAttr!.MaxKgPerHa ?? maxKgPerHa) / 10_000),
|
||||||
|
})
|
||||||
|
.OrderByDescending(g => g.Area)
|
||||||
|
.ThenBy(g => g.SortId)
|
||||||
|
.ToListAsync();
|
||||||
|
|
||||||
|
int rowNum = 2;
|
||||||
|
if (noAttr.Count > 0) {
|
||||||
|
rowNum++;
|
||||||
|
AddToolTipRow(grid, rowNum++, null, null, noAttr.Sum(g => g.Area), noAttr.Sum(g => g.Min), noAttr.Sum(g => g.Max));
|
||||||
|
foreach (var g in noAttr) {
|
||||||
|
AddToolTipRow(grid, rowNum++, null, g.SortId, g.Area, g.Min, g.Max);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
foreach (var attrG in attrGroups) {
|
||||||
|
rowNum++;
|
||||||
|
AddToolTipRow(grid, rowNum++, attrG.Attr, null, attrG.Area, attrG.Min, attrG.Max);
|
||||||
|
foreach (var g in groups.Where(g => g.Attr == attrG.Attr).OrderByDescending(g => g.Area).ThenBy(g => g.SortId)) {
|
||||||
|
AddToolTipRow(grid, rowNum++, null, g.SortId, g.Area, g.Min, g.Max);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return (text, grid);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
820
Elwig/Services/DeliveryService.cs
Normal file
820
Elwig/Services/DeliveryService.cs
Normal file
@ -0,0 +1,820 @@
|
|||||||
|
using Elwig.Documents;
|
||||||
|
using Elwig.Helpers.Export;
|
||||||
|
using Elwig.Helpers;
|
||||||
|
using Elwig.Models.Dtos;
|
||||||
|
using Elwig.Models.Entities;
|
||||||
|
using Microsoft.Win32;
|
||||||
|
using System.Collections.Generic;
|
||||||
|
using System.Linq;
|
||||||
|
using System.Threading.Tasks;
|
||||||
|
using System.Windows.Input;
|
||||||
|
using System.Windows;
|
||||||
|
using System;
|
||||||
|
using Elwig.ViewModels;
|
||||||
|
using LinqKit;
|
||||||
|
using System.Globalization;
|
||||||
|
using System.Linq.Expressions;
|
||||||
|
using Microsoft.EntityFrameworkCore;
|
||||||
|
using System.IO;
|
||||||
|
using Microsoft.EntityFrameworkCore.ChangeTracking;
|
||||||
|
using System.Windows.Controls;
|
||||||
|
using System.Net.Http;
|
||||||
|
|
||||||
|
namespace Elwig.Services {
|
||||||
|
public static class DeliveryService {
|
||||||
|
|
||||||
|
public enum ExportSubject {
|
||||||
|
FromFilters, FromToday, FromSeasonAndBranch, Selected,
|
||||||
|
};
|
||||||
|
|
||||||
|
public static async Task<Member?> GetMemberAsync(int mgnr) {
|
||||||
|
using var ctx = new AppDbContext();
|
||||||
|
return await ctx.Members
|
||||||
|
.Include(m => m.PostalDest.AtPlz!.Ort)
|
||||||
|
.Include(m => m.DefaultWbKg!.AtKg)
|
||||||
|
.FirstOrDefaultAsync(m => m.MgNr == mgnr);
|
||||||
|
}
|
||||||
|
|
||||||
|
public static Member? GetMember(int mgnr) {
|
||||||
|
return GetMemberAsync(mgnr).GetAwaiter().GetResult();
|
||||||
|
}
|
||||||
|
|
||||||
|
public static void ClearInputs(this DeliveryAdminViewModel vm) {
|
||||||
|
}
|
||||||
|
|
||||||
|
public static void FillInputs(this DeliveryAdminViewModel vm, Delivery d) {
|
||||||
|
vm.MgNrString = $"{d.MgNr}";
|
||||||
|
vm.Branch = (Branch?)ControlUtils.GetItemFromSourceWithPk(vm.BranchSource, d.ZwstId);
|
||||||
|
vm.LsNr = d.LsNr;
|
||||||
|
vm.Date = $"{d.Date:dd.MM.yyyy}";
|
||||||
|
vm.Time = $"{d.Time:HH:mm}";
|
||||||
|
vm.Comment = d.Comment ?? "";
|
||||||
|
|
||||||
|
vm.SortId = "";
|
||||||
|
vm.GradationKmwString = "";
|
||||||
|
vm.WeightString = "";
|
||||||
|
vm.IsManualWeighing = false;
|
||||||
|
vm.PartComment = "";
|
||||||
|
vm.TemperatureString = "";
|
||||||
|
vm.AcidString = "";
|
||||||
|
}
|
||||||
|
|
||||||
|
public static void FillInputs(this DeliveryAdminViewModel vm, DeliveryPart p) {
|
||||||
|
vm.SortId = p.SortId;
|
||||||
|
vm.WineAttr = ControlUtils.GetItemFromSourceWithPk(vm.WineAttrSource, p.AttrId) as WineAttr;
|
||||||
|
vm.WineCult = ControlUtils.GetItemFromSourceWithPk(vm.WineCultSource, p.CultId) as WineCult;
|
||||||
|
vm.GradationKmwString = $"{p.Kmw:N1}";
|
||||||
|
vm.WineQualityLevel = (WineQualLevel?)ControlUtils.GetItemFromSourceWithPk(vm.WineQualityLevelSource, p.QualId);
|
||||||
|
vm.WineKg = ControlUtils.GetItemFromSourceWithPk(vm.WineKgSource, p.KgNr) as AT_Kg;
|
||||||
|
vm.WineRd = ControlUtils.GetItemFromSourceWithPk(vm.WineRdSource, p.KgNr, p.RdNr) as WbRd;
|
||||||
|
vm.WineOrigin = ControlUtils.GetItemFromSourceWithPk(vm.WineOriginSource, p.HkId) as WineOrigin;
|
||||||
|
vm.WeightString = $"{p.Weight:N0}";
|
||||||
|
vm.IsManualWeighing = p.IsManualWeighing;
|
||||||
|
vm.IsNetWeight = p.IsNetWeight;
|
||||||
|
|
||||||
|
vm.Modifiers.Clear();
|
||||||
|
foreach (var m in p.Modifiers) {
|
||||||
|
vm.Modifiers.Add((Modifier)ControlUtils.GetItemFromSourceWithPk(vm.ModifiersSource, m.Year, m.ModId)!);
|
||||||
|
}
|
||||||
|
|
||||||
|
vm.PartComment = p.Comment ?? "";
|
||||||
|
vm.TemperatureString = (p.Temperature != null) ? $"{p.Temperature:N1}" : "";
|
||||||
|
vm.AcidString = (p.Acid != null) ? $"{p.Acid:N1}" : "";
|
||||||
|
vm.IsLesewagen = p.IsLesewagen ?? false;
|
||||||
|
vm.IsHandPicked = p.IsHandPicked;
|
||||||
|
vm.IsGebunden = p.IsGebunden;
|
||||||
|
|
||||||
|
vm.ScaleId = p.ScaleId;
|
||||||
|
vm.WeighingData = p.WeighingData;
|
||||||
|
vm.ManualWeighingReason = p.WeighingReason;
|
||||||
|
}
|
||||||
|
|
||||||
|
public static async Task<(List<string>, IQueryable<Delivery>, IQueryable<DeliveryPart>, Predicate<DeliveryPart>, List<string>)> GetFilters(this DeliveryAdminViewModel vm, AppDbContext ctx) {
|
||||||
|
List<string> filterNames = [];
|
||||||
|
IQueryable<Delivery> deliveryQuery = ctx.Deliveries;
|
||||||
|
if (vm.IsReceipt && App.BranchNum > 1) {
|
||||||
|
deliveryQuery = deliveryQuery.Where(d => d.ZwstId == App.ZwstId);
|
||||||
|
filterNames.Add($"Zweigstelle {App.BranchName}");
|
||||||
|
}
|
||||||
|
if (vm.FilterMember != null) {
|
||||||
|
deliveryQuery = deliveryQuery.Where(d => d.MgNr == vm.FilterMember.MgNr);
|
||||||
|
filterNames.Add(vm.FilterMember.AdministrativeName);
|
||||||
|
}
|
||||||
|
if (vm.FilterTodayOnly) {
|
||||||
|
deliveryQuery = deliveryQuery
|
||||||
|
.Where(d => (d.DateString == Utils.Today.ToString("yyyy-MM-dd") && (d.TimeString == null || d.TimeString.CompareTo("03:00:00") > 0)) ||
|
||||||
|
(d.DateString == Utils.Today.AddDays(1).ToString("yyyy-MM-dd") && (d.TimeString == null || d.TimeString.CompareTo("03:00:00") <= 0)));
|
||||||
|
filterNames.Add(Utils.Today.ToString("dd.MM.yyyy"));
|
||||||
|
} else if (!vm.FilterAllSeasons) {
|
||||||
|
deliveryQuery = deliveryQuery.Where(d => d.Year == vm.FilterSeason);
|
||||||
|
filterNames.Add($"{vm.FilterSeason}");
|
||||||
|
}
|
||||||
|
|
||||||
|
Expression<Func<DeliveryPart, bool>> prd = p => true;
|
||||||
|
|
||||||
|
var filterVar = new List<string>();
|
||||||
|
var filterNotVar = new List<string>();
|
||||||
|
var filterQual = new List<string>();
|
||||||
|
var filterNotQual = new List<string>();
|
||||||
|
var filterMgNr = new List<int>();
|
||||||
|
var filterZwst = new List<string>();
|
||||||
|
var filterAttr = new List<string>();
|
||||||
|
var filterNotAttr = new List<string>();
|
||||||
|
var filterCult = new List<string>();
|
||||||
|
var filterNotCult = new List<string>();
|
||||||
|
var filterDate = new List<(string?, string?)>();
|
||||||
|
var filterTime = new List<(string?, string?)>();
|
||||||
|
int filterYearGt = 0, filterYearLt = 0;
|
||||||
|
double filterKmwGt = 0, filterKmwLt = 0;
|
||||||
|
double filterOeGt = 0, filterOeLt = 0;
|
||||||
|
|
||||||
|
var filter = vm.TextFilter;
|
||||||
|
if (filter.Count > 0) {
|
||||||
|
var var = await ctx.WineVarieties.ToDictionaryAsync(v => v.SortId, v => v);
|
||||||
|
var qual = await ctx.WineQualityLevels.Where(q => !q.IsPredicate).ToDictionaryAsync(q => q.QualId, q => q);
|
||||||
|
var mgnr = await ctx.Members.ToDictionaryAsync(m => m.MgNr.ToString(), m => m);
|
||||||
|
var zwst = await ctx.Branches.ToDictionaryAsync(b => b.Name.ToLower().Split(" ")[0], b => b);
|
||||||
|
var attr = await ctx.WineAttributes.ToDictionaryAsync(a => a.Name.ToLower().Split(' ')[0], a => a);
|
||||||
|
var cult = await ctx.WineCultivations.ToDictionaryAsync(c => c.Name.ToLower().Split(' ')[0], c => c);
|
||||||
|
|
||||||
|
for (int i = 0; i < filter.Count; i++) {
|
||||||
|
var e = filter[i];
|
||||||
|
if (e.ToLower() is "r" or "rot") {
|
||||||
|
filterVar.AddRange(var.Values.Where(v => v.IsRed).Select(v => v.SortId));
|
||||||
|
filter.RemoveAt(i--);
|
||||||
|
filterNames.Add("Rotweinsorten");
|
||||||
|
} else if (e.ToLower() is "w" or "weiß" or "weiss") {
|
||||||
|
filterVar.AddRange(var.Values.Where(v => v.IsWhite).Select(v => v.SortId));
|
||||||
|
filter.RemoveAt(i--);
|
||||||
|
filterNames.Add("Weißweinsorten");
|
||||||
|
} else if (e.Length >= 3 && e.Length <= 8 && "gebunden".StartsWith(e, StringComparison.CurrentCultureIgnoreCase)) {
|
||||||
|
prd = prd.And(p => p.IsGebunden == true);
|
||||||
|
filter.RemoveAt(i--);
|
||||||
|
filterNames.Add("gebunden");
|
||||||
|
} else if (e.Length >= 4 && e.Length <= 9 && "!gebunden".StartsWith(e, StringComparison.CurrentCultureIgnoreCase)) {
|
||||||
|
prd = prd.And(p => p.IsGebunden != true);
|
||||||
|
filter.RemoveAt(i--);
|
||||||
|
filterNames.Add("nicht gebunden");
|
||||||
|
} else if (e.Length >= 5 && e.Length <= 10 && "ungebunden".StartsWith(e, StringComparison.CurrentCultureIgnoreCase)) {
|
||||||
|
prd = prd.And(p => p.IsGebunden == false);
|
||||||
|
filter.RemoveAt(i--);
|
||||||
|
filterNames.Add("ungebunden");
|
||||||
|
} else if (e.Length >= 6 && e.Length <= 11 && "!ungebunden".StartsWith(e, StringComparison.CurrentCultureIgnoreCase)) {
|
||||||
|
prd = prd.And(p => p.IsGebunden != false);
|
||||||
|
filter.RemoveAt(i--);
|
||||||
|
filterNames.Add("nicht ungebunden");
|
||||||
|
} else if (e.Length >= 5 && e.Length <= 8 && "handlese".StartsWith(e, StringComparison.CurrentCultureIgnoreCase)) {
|
||||||
|
prd = prd.And(p => p.IsHandPicked == true);
|
||||||
|
filter.RemoveAt(i--);
|
||||||
|
filterNames.Add("Handlese");
|
||||||
|
} else if (e.Length >= 6 && e.Length <= 9 && "!handlese".StartsWith(e, StringComparison.CurrentCultureIgnoreCase)) {
|
||||||
|
prd = prd.And(p => p.IsHandPicked == false);
|
||||||
|
filter.RemoveAt(i--);
|
||||||
|
filterNames.Add("keine Handlese");
|
||||||
|
} else if (e.Length >= 5 && e.Length <= 11 && "handwiegung".StartsWith(e, StringComparison.CurrentCultureIgnoreCase)) {
|
||||||
|
prd = prd.And(p => p.IsManualWeighing == true);
|
||||||
|
filter.RemoveAt(i--);
|
||||||
|
filterNames.Add("Handwiegung");
|
||||||
|
} else if (e.Length >= 6 && e.Length <= 12 && "!handwiegung".StartsWith(e, StringComparison.CurrentCultureIgnoreCase)) {
|
||||||
|
prd = prd.And(p => p.IsManualWeighing == false);
|
||||||
|
filter.RemoveAt(i--);
|
||||||
|
filterNames.Add("keine Handwiegung");
|
||||||
|
} else if (e.ToLower() == "!gerebelt") {
|
||||||
|
prd = prd.And(p => p.IsNetWeight == false);
|
||||||
|
filter.RemoveAt(i--);
|
||||||
|
filterNames.Add("brutto Wiegung");
|
||||||
|
} else if (e.ToLower() == "gerebelt") {
|
||||||
|
prd = prd.And(p => p.IsNetWeight == true);
|
||||||
|
filter.RemoveAt(i--);
|
||||||
|
filterNames.Add("netto Wiegung");
|
||||||
|
} else if (e.Length >= 5 && e.Length <= 9 && "lesewagen".StartsWith(e, StringComparison.CurrentCultureIgnoreCase)) {
|
||||||
|
prd = prd.And(p => p.IsLesewagen == true);
|
||||||
|
filter.RemoveAt(i--);
|
||||||
|
filterNames.Add("Lesewagen");
|
||||||
|
} else if (e.Length >= 6 && e.Length <= 10 && "!lesewagen".StartsWith(e, StringComparison.CurrentCultureIgnoreCase)) {
|
||||||
|
prd = prd.And(p => p.IsLesewagen == false);
|
||||||
|
filter.RemoveAt(i--);
|
||||||
|
filterNames.Add("kein Lesewagen");
|
||||||
|
} else if (e.Length == 2 && var.ContainsKey(e.ToUpper())) {
|
||||||
|
filterVar.Add(e.ToUpper());
|
||||||
|
filter.RemoveAt(i--);
|
||||||
|
filterNames.Add(var[e.ToUpper()].Name);
|
||||||
|
} else if (e.Length == 3 && e[0] == '!' && var.ContainsKey(e[1..].ToUpper())) {
|
||||||
|
filterNotVar.Add(e[1..].ToUpper());
|
||||||
|
filter.RemoveAt(i--);
|
||||||
|
filterNames.Add("außer " + var[e[1..].ToUpper()].Name);
|
||||||
|
} else if (e.Length == 3 && qual.ContainsKey(e.ToUpper())) {
|
||||||
|
var qualId = e.ToUpper();
|
||||||
|
filterQual.Add(qualId);
|
||||||
|
filter.RemoveAt(i--);
|
||||||
|
filterNames.Add(qualId == "WEI" ? "abgewertet" : qual[e.ToUpper()].Name);
|
||||||
|
} else if (e[0] == '!' && qual.ContainsKey(e[1..].ToUpper())) {
|
||||||
|
var qualId = e[1..].ToUpper();
|
||||||
|
filterNotQual.Add(qualId);
|
||||||
|
filter.RemoveAt(i--);
|
||||||
|
filterNames.Add(qualId == "WEI" ? "nicht abgewertet" : "außer " + qual[e[1..].ToUpper()].Name);
|
||||||
|
} else if (e.Length >= 5 && e.Length <= 10 && "abgewertet".StartsWith(e, StringComparison.CurrentCultureIgnoreCase)) {
|
||||||
|
filterQual.Add("WEI");
|
||||||
|
filter.RemoveAt(i--);
|
||||||
|
filterNames.Add("abgewertet");
|
||||||
|
} else if (e.Length >= 6 && e.Length <= 11 && "!abgewertet".StartsWith(e, StringComparison.CurrentCultureIgnoreCase)) {
|
||||||
|
filterNotQual.Add("WEI");
|
||||||
|
filter.RemoveAt(i--);
|
||||||
|
filterNames.Add("nicht abgewertet");
|
||||||
|
} else if (e.All(char.IsAsciiDigit) && mgnr.TryGetValue(e, out var member)) {
|
||||||
|
filterMgNr.Add(int.Parse(e));
|
||||||
|
filter.RemoveAt(i--);
|
||||||
|
filterNames.Add(member.AdministrativeName);
|
||||||
|
} else if (attr.ContainsKey(e.ToLower())) {
|
||||||
|
var a = attr[e.ToLower()];
|
||||||
|
filterAttr.Add(a.AttrId);
|
||||||
|
filter.RemoveAt(i--);
|
||||||
|
filterNames.Add($"Attribut {a.Name}");
|
||||||
|
} else if (e[0] == '!' && attr.ContainsKey(e[1..].ToLower())) {
|
||||||
|
var a = attr[e[1..].ToLower()];
|
||||||
|
filterNotAttr.Add(a.AttrId);
|
||||||
|
filter.RemoveAt(i--);
|
||||||
|
filterNames.Add($"ohne Attribut {a.Name}");
|
||||||
|
} else if (cult.ContainsKey(e.ToLower())) {
|
||||||
|
var c = cult[e.ToLower()];
|
||||||
|
filterCult.Add(c.CultId);
|
||||||
|
filter.RemoveAt(i--);
|
||||||
|
filterNames.Add($"Bewirtschaftung {c.Name}");
|
||||||
|
} else if (e[0] == '!' && cult.ContainsKey(e[1..].ToLower())) {
|
||||||
|
var c = cult[e[1..].ToLower()];
|
||||||
|
filterNotCult.Add(c.CultId);
|
||||||
|
filter.RemoveAt(i--);
|
||||||
|
filterNames.Add($"ohne Bewirtschaftung {c.Name}");
|
||||||
|
} else if (zwst.ContainsKey(e.ToLower())) {
|
||||||
|
var b = zwst[e.ToLower()];
|
||||||
|
filterZwst.Add(b.ZwstId);
|
||||||
|
filter.RemoveAt(i--);
|
||||||
|
filterNames.Add($"Zweigstelle {b.Name}");
|
||||||
|
} else if (e.StartsWith('>') || e.StartsWith('<')) {
|
||||||
|
if (double.TryParse(e[1..], out var num)) {
|
||||||
|
switch ((e[0], num)) {
|
||||||
|
case ('>', <= 30): filterKmwGt = num; break;
|
||||||
|
case ('<', <= 30): filterKmwLt = num; break;
|
||||||
|
case ('>', >= 1900): filterYearGt = (int)num; break;
|
||||||
|
case ('<', >= 1900): filterYearLt = (int)num; break;
|
||||||
|
case ('>', _): filterOeGt = num; break;
|
||||||
|
case ('<', _): filterOeLt = num; break;
|
||||||
|
}
|
||||||
|
filter.RemoveAt(i--);
|
||||||
|
}
|
||||||
|
if (e.Length == 1) filter.RemoveAt(i--);
|
||||||
|
} else if (e.Length > 1 && Utils.FromToRegex.IsMatch(e)) {
|
||||||
|
var parts = e.Split("-");
|
||||||
|
double? from = (parts[0].Length > 0) ? double.Parse(parts[0], CultureInfo.InvariantCulture) : null;
|
||||||
|
double? to = (parts[1].Length > 0) ? double.Parse(parts[1], CultureInfo.InvariantCulture) : null;
|
||||||
|
switch ((from, to)) {
|
||||||
|
case ( <= 30, <= 30):
|
||||||
|
case ( <= 30, null):
|
||||||
|
case (null, <= 30):
|
||||||
|
filterKmwGt = from ?? 0;
|
||||||
|
filterKmwLt = to ?? 0;
|
||||||
|
break;
|
||||||
|
case ( >= 1900, >= 1900):
|
||||||
|
case ( >= 1900, null):
|
||||||
|
case (null, >= 1900):
|
||||||
|
filterYearGt = (int)(from ?? 0);
|
||||||
|
filterYearLt = (int)(to ?? -1) + 1;
|
||||||
|
break;
|
||||||
|
case (_, _):
|
||||||
|
filterOeGt = from ?? 0;
|
||||||
|
filterOeLt = to ?? 0;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
filter.RemoveAt(i--);
|
||||||
|
} else if (e.Length > 1 && Utils.FromToTimeRegex.IsMatch(e)) {
|
||||||
|
var parts = e.Split("-");
|
||||||
|
filterTime.Add((TimeOnly.TryParse(parts[0], out var from) ? $"{from:HH:mm}" : null, TimeOnly.TryParse(parts[1], out var to) ? $"{to:HH:mm}" : null));
|
||||||
|
filter.RemoveAt(i--);
|
||||||
|
var t = filterTime.Last();
|
||||||
|
if (t.Item1 != null && t.Item2 != null) {
|
||||||
|
filterNames.Add($"{t.Item1}–{t.Item2}");
|
||||||
|
} else if (t.Item1 != null) {
|
||||||
|
filterNames.Add($"ab {t.Item1}");
|
||||||
|
} else if (t.Item2 != null) {
|
||||||
|
filterNames.Add($"bis {t.Item2}");
|
||||||
|
}
|
||||||
|
} else if (DateOnly.TryParse(e, out var date)) {
|
||||||
|
var s = date.ToString("yyyy-MM-dd");
|
||||||
|
filterDate.Add((s, s));
|
||||||
|
filter.RemoveAt(i--);
|
||||||
|
if (filterNames.Contains($"{vm.FilterSeason}") && vm.FilterSeason == date.Year)
|
||||||
|
filterNames.Remove($"{vm.FilterSeason}");
|
||||||
|
filterNames.Add(date.ToString("dd.MM.yyyy"));
|
||||||
|
} else if (Utils.DateFromToRegex.IsMatch(e)) {
|
||||||
|
var parts = e.Split("-");
|
||||||
|
if (parts.Length == 1) {
|
||||||
|
// single date
|
||||||
|
var dParts = parts[0].Split('.');
|
||||||
|
var s = $"{dParts[2]}-{dParts[1].PadLeft(2, '0')}-{dParts[0].PadLeft(2, '0')}";
|
||||||
|
filterDate.Add((s, s));
|
||||||
|
filter.RemoveAt(i--);
|
||||||
|
var n = string.Join('.', s.Split('-').Reverse());
|
||||||
|
if (dParts[2] == "") {
|
||||||
|
filterNames.Remove($"{vm.FilterSeason}");
|
||||||
|
filterNames.Add(n + $"{vm.FilterSeason}");
|
||||||
|
} else {
|
||||||
|
if ($"{vm.FilterSeason}" == dParts[2])
|
||||||
|
filterNames.Remove($"{vm.FilterSeason}");
|
||||||
|
filterNames.Add(n);
|
||||||
|
}
|
||||||
|
} else if (parts.Length == 2) {
|
||||||
|
// from/to date
|
||||||
|
var d1Parts = parts[0].Split('.');
|
||||||
|
var d2Parts = parts[1].Split('.');
|
||||||
|
var s1 = d1Parts.Length < 2 ? null : $"{d1Parts.ElementAtOrDefault(2)}-{d1Parts[1].PadLeft(2, '0')}-{d1Parts[0].PadLeft(2, '0')}";
|
||||||
|
var s2 = d2Parts.Length < 2 ? null : $"{d2Parts.ElementAtOrDefault(2)}-{d2Parts[1].PadLeft(2, '0')}-{d2Parts[0].PadLeft(2, '0')}";
|
||||||
|
filterDate.Add((s1, s2));
|
||||||
|
filter.RemoveAt(i--);
|
||||||
|
var n1 = s1 == null ? null : string.Join('.', s1.Split('-').Reverse());
|
||||||
|
var n2 = s2 == null ? null : string.Join('.', s2.Split('-').Reverse());
|
||||||
|
if (n1 != null && n2 != null) {
|
||||||
|
filterNames.Add($"{n1}–{n2}");
|
||||||
|
} else if (n1 != null) {
|
||||||
|
filterNames.Add($"ab dem {n1}");
|
||||||
|
} else if (n2 != null) {
|
||||||
|
filterNames.Add($"bis zum {n2}");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
} else if (e.Length > 2 && e.StartsWith('"') && e.EndsWith('"')) {
|
||||||
|
filter[i] = e[1..^1];
|
||||||
|
} else if (e.Length <= 2) {
|
||||||
|
filter.RemoveAt(i--);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (filterYearGt > 0) prd = prd.And(p => p.Year >= filterYearGt);
|
||||||
|
if (filterYearLt > 0) prd = prd.And(p => p.Year < filterYearLt);
|
||||||
|
if (filterMgNr.Count > 0) prd = prd.And(p => filterMgNr.Contains(p.Delivery.MgNr));
|
||||||
|
if (filterDate.Count > 0) {
|
||||||
|
var pr = PredicateBuilder.New<DeliveryPart>(false);
|
||||||
|
foreach (var (d1, d2) in filterDate)
|
||||||
|
pr.Or(p => (d1 == null || d1.CompareTo(p.Delivery.DateString.Substring(10 - d1.Length)) <= 0) && (d2 == null || d2.CompareTo(p.Delivery.DateString.Substring(10 - d2.Length)) >= 0));
|
||||||
|
prd = prd.And(pr);
|
||||||
|
}
|
||||||
|
if (filterTime.Count > 0) {
|
||||||
|
var pr = PredicateBuilder.New<DeliveryPart>(false);
|
||||||
|
foreach (var (t1, t2) in filterTime)
|
||||||
|
pr.Or(p => (t1 == null || t1.CompareTo(p.Delivery.TimeString) <= 0) && (t2 == null || t2.CompareTo(p.Delivery.TimeString) > 0));
|
||||||
|
prd = prd.And(p => p.Delivery.TimeString != null).And(pr);
|
||||||
|
}
|
||||||
|
if (filterVar.Count > 0) prd = prd.And(p => filterVar.Contains(p.SortId));
|
||||||
|
if (filterNotVar.Count > 0) prd = prd.And(p => !filterNotVar.Contains(p.SortId));
|
||||||
|
if (filterQual.Count > 0) prd = prd.And(p => filterQual.Contains(p.QualId));
|
||||||
|
if (filterNotQual.Count > 0) prd = prd.And(p => !filterNotQual.Contains(p.QualId));
|
||||||
|
if (filterZwst.Count > 0) prd = prd.And(p => filterZwst.Contains(p.Delivery.ZwstId));
|
||||||
|
if (filterAttr.Count > 0) prd = prd.And(p => p.AttrId != null && filterAttr.Contains(p.AttrId));
|
||||||
|
if (filterNotAttr.Count > 0) prd = prd.And(p => p.AttrId == null || !filterNotAttr.Contains(p.AttrId));
|
||||||
|
if (filterCult.Count > 0) prd = prd.And(p => p.CultId != null && filterCult.Contains(p.CultId));
|
||||||
|
if (filterNotCult.Count > 0) prd = prd.And(p => p.CultId == null || !filterNotCult.Contains(p.CultId));
|
||||||
|
if (filterKmwGt > 0) prd = prd.And(p => p.Kmw >= filterKmwGt);
|
||||||
|
if (filterKmwLt > 0) prd = prd.And(p => p.Kmw < filterKmwLt);
|
||||||
|
if (filterOeGt > 0) prd = prd.And(p => p.Kmw * (4.54 + 0.022 * p.Kmw) >= filterOeGt);
|
||||||
|
if (filterOeLt > 0) prd = prd.And(p => p.Kmw * (4.54 + 0.022 * p.Kmw) < filterOeLt);
|
||||||
|
|
||||||
|
if (filterYearGt > 0 && filterYearLt > 0) {
|
||||||
|
filterNames.Insert(0, $"{filterYearGt}–{filterYearLt - 1}");
|
||||||
|
} else if (filterYearGt > 0) {
|
||||||
|
filterNames.Insert(0, $"ab {filterYearGt}");
|
||||||
|
} else if (filterYearLt > 0) {
|
||||||
|
filterNames.Insert(0, $"bis {filterYearLt - 1}");
|
||||||
|
}
|
||||||
|
if (filterKmwGt > 0 && filterKmwLt > 0) {
|
||||||
|
filterNames.Add($"{filterKmwGt:N1}–{filterKmwLt:N1} °KMW");
|
||||||
|
} else if (filterKmwGt > 0) {
|
||||||
|
filterNames.Add($"ab {filterKmwGt:N1} °KMW");
|
||||||
|
} else if (filterKmwLt > 0) {
|
||||||
|
filterNames.Add($"unter {filterKmwLt:N1} °KMW");
|
||||||
|
}
|
||||||
|
if (filterOeGt > 0 && filterOeLt > 0) {
|
||||||
|
filterNames.Add($"{filterOeGt:N1}–{filterOeLt:N1} °Oe");
|
||||||
|
} else if (filterOeGt > 0) {
|
||||||
|
filterNames.Add($"ab {filterOeGt:N1} °Oe");
|
||||||
|
} else if (filterOeLt > 0) {
|
||||||
|
filterNames.Add($"unter {filterOeLt:N1} °Oe");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
IQueryable<DeliveryPart> dpq = deliveryQuery
|
||||||
|
.SelectMany(d => d.Parts)
|
||||||
|
.Where(prd)
|
||||||
|
.OrderBy(p => p.Delivery.DateString)
|
||||||
|
.ThenBy(p => p.Delivery.TimeString)
|
||||||
|
.ThenBy(p => p.Delivery.LsNr)
|
||||||
|
.ThenBy(p => p.DPNr);
|
||||||
|
|
||||||
|
return (filterNames, dpq.Select(p => p.Delivery).Distinct().OrderBy(d => d.DateString).ThenBy(d => d.TimeString), dpq, prd.Invoke, filter);
|
||||||
|
}
|
||||||
|
|
||||||
|
public static async Task<DeliveryPart> UpdateDeliveryPart(this DeliveryAdminViewModel vm, int? oldYear, int? oldDid, int? oldDpnr, bool dateHasChanged, bool timeHasChanged, bool timeIsDefault) {
|
||||||
|
using var ctx = new AppDbContext();
|
||||||
|
|
||||||
|
int year = oldYear ?? Utils.CurrentYear;
|
||||||
|
int did = oldDid ?? await ctx.NextDId(year);
|
||||||
|
int dpnr = oldDpnr ?? await ctx.NextDPNr(year, did);
|
||||||
|
|
||||||
|
var oldDelivery = await ctx.Deliveries.FindAsync(year, did);
|
||||||
|
bool deliveryNew = (oldDid == null);
|
||||||
|
bool partNew = (oldDpnr == null);
|
||||||
|
var originalMgNr = oldDelivery?.MgNr;
|
||||||
|
var originalMemberKgNr = oldDelivery?.Member.DefaultKgNr;
|
||||||
|
|
||||||
|
var date = DateOnly.ParseExact(vm.Date!, "dd.MM.yyyy");
|
||||||
|
int? newLnr = (deliveryNew || dateHasChanged) ? await ctx.NextLNr(date) : null;
|
||||||
|
|
||||||
|
string? newTimeString = null;
|
||||||
|
if (partNew && timeIsDefault) {
|
||||||
|
newTimeString = DateTime.Now.ToString("HH:mm:ss");
|
||||||
|
} else if (partNew || timeHasChanged) {
|
||||||
|
newTimeString = string.IsNullOrEmpty(vm.Time) ? null : vm.Time + ":00";
|
||||||
|
}
|
||||||
|
|
||||||
|
var d = new Delivery {
|
||||||
|
Year = year,
|
||||||
|
DId = did,
|
||||||
|
DateString = $"{date:yyyy-MM-dd}",
|
||||||
|
TimeString = newTimeString ?? oldDelivery?.TimeString,
|
||||||
|
LNr = newLnr ?? oldDelivery!.LNr,
|
||||||
|
ZwstId = vm.Branch!.ZwstId,
|
||||||
|
LsNr = vm.LsNr!,
|
||||||
|
MgNr = (int)vm.MgNr!,
|
||||||
|
Comment = string.IsNullOrEmpty(vm.Comment) ? null : vm.Comment,
|
||||||
|
};
|
||||||
|
|
||||||
|
var p = new DeliveryPart {
|
||||||
|
Year = year,
|
||||||
|
DId = did,
|
||||||
|
DPNr = dpnr,
|
||||||
|
|
||||||
|
SortId = vm.WineVar!.SortId,
|
||||||
|
AttrId = vm.WineAttr?.AttrId,
|
||||||
|
CultId = vm.WineCult?.CultId,
|
||||||
|
Kmw = (double)vm.GradationKmw!,
|
||||||
|
QualId = vm.WineQualityLevel!.QualId,
|
||||||
|
HkId = vm.WineOrigin!.HkId,
|
||||||
|
KgNr = vm.WineKg?.KgNr,
|
||||||
|
RdNr = vm.WineRd?.RdNr,
|
||||||
|
|
||||||
|
IsNetWeight = vm.IsNetWeight,
|
||||||
|
IsHandPicked = vm.IsHandPicked,
|
||||||
|
IsLesewagen = vm.IsLesewagen,
|
||||||
|
IsGebunden = vm.IsGebunden,
|
||||||
|
Temperature = vm.Temperature,
|
||||||
|
Acid = vm.Acid,
|
||||||
|
Comment = string.IsNullOrEmpty(vm.PartComment) ? null : vm.PartComment,
|
||||||
|
|
||||||
|
Weight = (int)vm.Weight!,
|
||||||
|
IsManualWeighing = vm.IsManualWeighing,
|
||||||
|
ScaleId = vm.ScaleId,
|
||||||
|
WeighingData = vm.WeighingData,
|
||||||
|
WeighingReason = vm.ManualWeighingReason,
|
||||||
|
};
|
||||||
|
|
||||||
|
try {
|
||||||
|
if (oldDelivery != null && ctx.Entry(oldDelivery) is EntityEntry<Delivery> entry) {
|
||||||
|
entry.State = EntityState.Detached;
|
||||||
|
}
|
||||||
|
if (!deliveryNew) {
|
||||||
|
ctx.Update(d);
|
||||||
|
} else {
|
||||||
|
ctx.Add(d);
|
||||||
|
}
|
||||||
|
if (!partNew) {
|
||||||
|
ctx.Update(p);
|
||||||
|
} else {
|
||||||
|
ctx.Add(p);
|
||||||
|
}
|
||||||
|
|
||||||
|
ctx.UpdateDeliveryPartModifiers(p, await ctx.DeliveryPartModifiers
|
||||||
|
.Where(m => m.Year == p.Year && m.DId == p.DId && m.DPNr == p.DPNr)
|
||||||
|
.Select(m => m.Modifier)
|
||||||
|
.ToListAsync(), vm.Modifiers);
|
||||||
|
|
||||||
|
if (originalMgNr != null && originalMgNr.Value != d.MgNr) {
|
||||||
|
// update origin (KgNr), if default is selected
|
||||||
|
var newKgNr = (await ctx.Members.FindAsync(d.MgNr))?.DefaultKgNr;
|
||||||
|
foreach (var part in d.Parts.Where(part => part.DPNr != dpnr && part.KgNr == originalMemberKgNr)) {
|
||||||
|
part.KgNr = newKgNr;
|
||||||
|
ctx.Update(part);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
await ctx.SaveChangesAsync();
|
||||||
|
} 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, "Lieferung aktualisieren", MessageBoxButton.OK, MessageBoxImage.Error);
|
||||||
|
}
|
||||||
|
|
||||||
|
return p;
|
||||||
|
}
|
||||||
|
|
||||||
|
public static async Task GenerateDeliveryNote(int year, int did, ExportMode mode) {
|
||||||
|
Mouse.OverrideCursor = Cursors.AppStarting;
|
||||||
|
try {
|
||||||
|
using var ctx = new AppDbContext();
|
||||||
|
var d = (await ctx.Deliveries.FindAsync(year, did))!;
|
||||||
|
using var doc = new DeliveryNote(d, ctx);
|
||||||
|
await Utils.ExportDocument(doc, mode, d.LsNr, (d.Member, $"{DeliveryNote.Name} Nr. {d.LsNr}", $"Im Anhang finden Sie den {DeliveryNote.Name} Nr. {d.LsNr}"));
|
||||||
|
} catch (Exception exc) {
|
||||||
|
MessageBox.Show(exc.Message, "Fehler", MessageBoxButton.OK, MessageBoxImage.Error);
|
||||||
|
}
|
||||||
|
Mouse.OverrideCursor = null;
|
||||||
|
}
|
||||||
|
|
||||||
|
public static async Task GenerateDeliveryJournal(this DeliveryAdminViewModel vm, ExportSubject subject, ExportMode mode) {
|
||||||
|
using var ctx = new AppDbContext();
|
||||||
|
IQueryable<DeliveryPart> query;
|
||||||
|
List<string> filterNames = [];
|
||||||
|
if (subject == ExportSubject.FromFilters) {
|
||||||
|
var (f, _, q, _, _) = await vm.GetFilters(ctx);
|
||||||
|
query = q;
|
||||||
|
filterNames.AddRange(f);
|
||||||
|
} else if (subject == ExportSubject.FromToday) {
|
||||||
|
var date = $"{Utils.Today:yyyy-MM-dd}";
|
||||||
|
query = ctx.DeliveryParts
|
||||||
|
.Where(p => p.Delivery.DateString == date);
|
||||||
|
filterNames.Add($"{Utils.Today:dd.MM.yyyy}");
|
||||||
|
} else if (subject == ExportSubject.FromSeasonAndBranch) {
|
||||||
|
query = ctx.DeliveryParts
|
||||||
|
.Where(p => p.Year == Utils.CurrentLastSeason && p.Delivery.ZwstId == App.ZwstId);
|
||||||
|
filterNames.AddRange([$"{Utils.CurrentLastSeason}", $"Zweigstelle {App.BranchName}"]);
|
||||||
|
} else if (subject == ExportSubject.Selected) {
|
||||||
|
var lsnr = vm.SelectedDelivery?.LsNr;
|
||||||
|
if (lsnr == null) return;
|
||||||
|
query = ctx.DeliveryParts
|
||||||
|
.Where(p => p.Delivery.LsNr == lsnr);
|
||||||
|
filterNames.Add(lsnr);
|
||||||
|
} else {
|
||||||
|
throw new ArgumentException("Invalid value for ExportSubject");
|
||||||
|
}
|
||||||
|
|
||||||
|
query = query
|
||||||
|
.OrderBy(p => p.Delivery.DateString)
|
||||||
|
.ThenBy(p => p.Delivery.TimeString)
|
||||||
|
.ThenBy(p => p.Delivery.LsNr)
|
||||||
|
.ThenBy(p => p.DPNr);
|
||||||
|
|
||||||
|
if (mode == ExportMode.SaveList) {
|
||||||
|
var d = new SaveFileDialog() {
|
||||||
|
FileName = $"{DeliveryJournal.Name}.ods",
|
||||||
|
DefaultExt = "ods",
|
||||||
|
Filter = "OpenDocument Format Spreadsheet (*.ods)|*.ods",
|
||||||
|
Title = $"{DeliveryJournal.Name} speichern unter - Elwig"
|
||||||
|
};
|
||||||
|
if (d.ShowDialog() == true) {
|
||||||
|
Mouse.OverrideCursor = Cursors.AppStarting;
|
||||||
|
try {
|
||||||
|
var data = await DeliveryJournalData.FromQuery(query, filterNames);
|
||||||
|
using var ods = new OdsFile(d.FileName);
|
||||||
|
await ods.AddTable(data);
|
||||||
|
} catch (Exception exc) {
|
||||||
|
MessageBox.Show(exc.Message, "Fehler", MessageBoxButton.OK, MessageBoxImage.Error);
|
||||||
|
}
|
||||||
|
Mouse.OverrideCursor = null;
|
||||||
|
}
|
||||||
|
} else if (mode == ExportMode.Export) {
|
||||||
|
var d = new SaveFileDialog() {
|
||||||
|
FileName = subject == ExportSubject.Selected ? $"Lieferung_{vm.SelectedDelivery?.LsNr}.elwig.zip" : $"Lieferungen_{DateTime.Now:yyyy-MM-dd_HH-mm-ss}_{App.ZwstId}.elwig.zip",
|
||||||
|
DefaultExt = "elwig.zip",
|
||||||
|
Filter = "Elwig-Export-Datei (*.elwig.zip)|*.elwig.zip",
|
||||||
|
Title = $"{DeliveryJournal.Name} speichern unter - Elwig"
|
||||||
|
};
|
||||||
|
if (d.ShowDialog() == true) {
|
||||||
|
Mouse.OverrideCursor = Cursors.AppStarting;
|
||||||
|
try {
|
||||||
|
await ElwigData.Export(d.FileName, await query
|
||||||
|
.Select(p => p.Delivery)
|
||||||
|
.Distinct()
|
||||||
|
.Include(d => d.Parts)
|
||||||
|
.ThenInclude(p => p.PartModifiers)
|
||||||
|
.AsSplitQuery()
|
||||||
|
.ToListAsync(), filterNames);
|
||||||
|
} catch (Exception exc) {
|
||||||
|
MessageBox.Show(exc.Message, "Fehler", MessageBoxButton.OK, MessageBoxImage.Error);
|
||||||
|
}
|
||||||
|
Mouse.OverrideCursor = null;
|
||||||
|
}
|
||||||
|
} else if (mode == ExportMode.Upload && App.Config.SyncUrl != null) {
|
||||||
|
Mouse.OverrideCursor = Cursors.AppStarting;
|
||||||
|
try {
|
||||||
|
var filename = $"{DateTime.Now:yyyy-MM-dd_HH-mm-ss}_{App.ZwstId}.elwig.zip";
|
||||||
|
var path = Path.Combine(App.TempPath, filename);
|
||||||
|
var list = await query
|
||||||
|
.Select(p => p.Delivery)
|
||||||
|
.Distinct()
|
||||||
|
.Include(d => d.Parts)
|
||||||
|
.ThenInclude(p => p.PartModifiers)
|
||||||
|
.AsSplitQuery()
|
||||||
|
.ToListAsync();
|
||||||
|
if (list.Count == 0) {
|
||||||
|
MessageBox.Show("Es wurden keine Lieferungen zum Hochladen ausgewählt!", "Lieferungen hochladen",
|
||||||
|
MessageBoxButton.OK, MessageBoxImage.Error);
|
||||||
|
} else {
|
||||||
|
await ElwigData.Export(path, list, filterNames);
|
||||||
|
await Utils.UploadExportData(path, App.Config.SyncUrl, App.Config.SyncUsername, App.Config.SyncPassword);
|
||||||
|
MessageBox.Show($"Hochladen von {list.Count} Lieferungen erfolgreich!", "Lieferungen hochgeladen",
|
||||||
|
MessageBoxButton.OK, MessageBoxImage.Information);
|
||||||
|
}
|
||||||
|
} catch (HttpRequestException exc) {
|
||||||
|
MessageBox.Show("Eventuell Internetverbindung prüfen!\n\n" + exc.Message, "Lieferungen hochladen", MessageBoxButton.OK, MessageBoxImage.Error);
|
||||||
|
} catch (TaskCanceledException exc) {
|
||||||
|
MessageBox.Show("Eventuell Internetverbindung prüfen!\n\n" + exc.Message, "Fehler", MessageBoxButton.OK, MessageBoxImage.Error);
|
||||||
|
} catch (Exception exc) {
|
||||||
|
MessageBox.Show(exc.Message, "Fehler", MessageBoxButton.OK, MessageBoxImage.Error);
|
||||||
|
}
|
||||||
|
Mouse.OverrideCursor = null;
|
||||||
|
} else {
|
||||||
|
Mouse.OverrideCursor = Cursors.AppStarting;
|
||||||
|
try {
|
||||||
|
var data = await DeliveryJournalData.FromQuery(query, filterNames);
|
||||||
|
using var doc = new DeliveryJournal(string.Join(" / ", filterNames), data);
|
||||||
|
await Utils.ExportDocument(doc, mode);
|
||||||
|
} catch (Exception exc) {
|
||||||
|
MessageBox.Show(exc.Message, "Fehler", MessageBoxButton.OK, MessageBoxImage.Error);
|
||||||
|
}
|
||||||
|
Mouse.OverrideCursor = null;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public static async Task GenerateWineQualityStatistics(this DeliveryAdminViewModel vm, ExportSubject subject, ExportMode mode) {
|
||||||
|
using var ctx = new AppDbContext();
|
||||||
|
IQueryable<DeliveryPart> query;
|
||||||
|
List<string> filterNames = [];
|
||||||
|
if (subject == ExportSubject.FromFilters) {
|
||||||
|
var (f, _, q, _, _) = await vm.GetFilters(ctx);
|
||||||
|
query = q;
|
||||||
|
filterNames.AddRange(f);
|
||||||
|
} else if (subject == ExportSubject.FromToday) {
|
||||||
|
var date = $"{Utils.Today:yyyy-MM-dd}";
|
||||||
|
query = ctx.DeliveryParts
|
||||||
|
.Where(p => p.Delivery.DateString == date);
|
||||||
|
filterNames.Add($"{Utils.Today:dd.MM.yyyy}");
|
||||||
|
} else {
|
||||||
|
throw new ArgumentException("Invalid value for ExportSubject");
|
||||||
|
}
|
||||||
|
|
||||||
|
Mouse.OverrideCursor = Cursors.AppStarting;
|
||||||
|
try {
|
||||||
|
var data = await WineQualityStatisticsData.FromQuery(query, App.Client.OrderingMemberList);
|
||||||
|
using var doc = new WineQualityStatistics(string.Join(" / ", filterNames), data);
|
||||||
|
await Utils.ExportDocument(doc, mode);
|
||||||
|
} catch (Exception exc) {
|
||||||
|
MessageBox.Show(exc.Message, "Fehler", MessageBoxButton.OK, MessageBoxImage.Error);
|
||||||
|
}
|
||||||
|
Mouse.OverrideCursor = null;
|
||||||
|
}
|
||||||
|
|
||||||
|
private static void AddToolTipCell(Grid grid, string text, int row, int col, int colSpan = 1, bool bold = false, bool alignRight = false, bool alignCenter = false) {
|
||||||
|
var tb = new TextBlock() {
|
||||||
|
Text = text,
|
||||||
|
TextAlignment = alignRight ? TextAlignment.Right : alignCenter ? TextAlignment.Center : TextAlignment.Left,
|
||||||
|
Margin = new(0, 12 * row, 0, 0),
|
||||||
|
FontWeight = bold ? FontWeights.Bold : FontWeights.Normal,
|
||||||
|
};
|
||||||
|
tb.SetValue(Grid.ColumnProperty, col);
|
||||||
|
tb.SetValue(Grid.ColumnSpanProperty, colSpan);
|
||||||
|
grid.Children.Add(tb);
|
||||||
|
}
|
||||||
|
|
||||||
|
private static void AddWeightToolTipRow(Grid grid, int row, string? h1, string? h2, int weight, int? total1, int total2) {
|
||||||
|
var bold = h2 == null;
|
||||||
|
if (h1 != null) AddToolTipCell(grid, h1 + ":", row, 0, (h2 == null) ? 2 : 1, bold);
|
||||||
|
if (h2 != null) AddToolTipCell(grid, h2 + ":", row, 1, 1, bold);
|
||||||
|
AddToolTipCell(grid, $"{weight:N0} kg", row, 2, 1, bold, true);
|
||||||
|
if (total1 != null && total1 != 0)
|
||||||
|
AddToolTipCell(grid, $"{weight * 100.0 / total1:N1} %", row, 3, 1, bold, true);
|
||||||
|
if (total2 != 0)
|
||||||
|
AddToolTipCell(grid, $"{weight * 100.0 / total2:N1} %", row, 4, 1, bold, true);
|
||||||
|
}
|
||||||
|
|
||||||
|
private static void AddGradationToolTipRow(Grid grid, int row, string? h1, string? h2, double min, double avg, double max) {
|
||||||
|
var bold = h2 == null;
|
||||||
|
if (h1 != null) AddToolTipCell(grid, h1 + ":", row, 0, (h2 == null) ? 2 : 1, bold);
|
||||||
|
if (h2 != null) AddToolTipCell(grid, h2 + ":", row, 1, 1, bold);
|
||||||
|
AddToolTipCell(grid, $"{min:N1}°", row, 2, 1, bold, true);
|
||||||
|
AddToolTipCell(grid, $"{avg:N1}°", row, 3, 1, bold, true);
|
||||||
|
AddToolTipCell(grid, $"{max:N1}°", row, 4, 1, bold, true);
|
||||||
|
}
|
||||||
|
|
||||||
|
public static async Task<(string WeightText, Grid WeightGrid, string GradationText, Grid GradationGrid)> GenerateToolTip(IQueryable<DeliveryPart> deliveryParts) {
|
||||||
|
var wGrid = new Grid();
|
||||||
|
wGrid.ColumnDefinitions.Add(new() { Width = new(10) });
|
||||||
|
wGrid.ColumnDefinitions.Add(new() { Width = new(60) });
|
||||||
|
wGrid.ColumnDefinitions.Add(new() { Width = new(80) });
|
||||||
|
wGrid.ColumnDefinitions.Add(new() { Width = new(50) });
|
||||||
|
wGrid.ColumnDefinitions.Add(new() { Width = new(50) });
|
||||||
|
var wText = "-";
|
||||||
|
|
||||||
|
var gGrid = new Grid();
|
||||||
|
gGrid.ColumnDefinitions.Add(new() { Width = new(10) });
|
||||||
|
gGrid.ColumnDefinitions.Add(new() { Width = new(60) });
|
||||||
|
gGrid.ColumnDefinitions.Add(new() { Width = new(35) });
|
||||||
|
gGrid.ColumnDefinitions.Add(new() { Width = new(35) });
|
||||||
|
gGrid.ColumnDefinitions.Add(new() { Width = new(35) });
|
||||||
|
AddToolTipCell(gGrid, "Min.", 0, 2, 1, false, false, true);
|
||||||
|
AddToolTipCell(gGrid, "⌀", 0, 3, 1, false, false, true);
|
||||||
|
AddToolTipCell(gGrid, "Max.", 0, 4, 1, false, false, true);
|
||||||
|
var gText = "-";
|
||||||
|
|
||||||
|
var weight = await deliveryParts.SumAsync(p => p.Weight);
|
||||||
|
wText = $"{weight:N0} kg";
|
||||||
|
AddWeightToolTipRow(wGrid, 0, "Gewicht", null, weight, null, weight);
|
||||||
|
|
||||||
|
if (await deliveryParts.AnyAsync()) {
|
||||||
|
var kmwMin = await deliveryParts.MinAsync(p => p.Kmw);
|
||||||
|
var kmwAvg = Utils.AggregateDeliveryPartsKmw(deliveryParts);
|
||||||
|
var kmwMax = await deliveryParts.MaxAsync(p => p.Kmw);
|
||||||
|
gText = $"{kmwMin:N1}° / {kmwAvg:N1}° / {kmwMax:N1}°";
|
||||||
|
AddGradationToolTipRow(gGrid, 1, "Gradation", null, kmwMin, kmwAvg, kmwMax);
|
||||||
|
|
||||||
|
var attrGroups = await deliveryParts
|
||||||
|
.GroupBy(p => new { Attr = p.Attribute!.Name, Cult = p.Cultivation!.Name })
|
||||||
|
.Select(g => new {
|
||||||
|
g.Key.Attr,
|
||||||
|
g.Key.Cult,
|
||||||
|
Weight = g.Sum(p => p.Weight),
|
||||||
|
Min = g.Min(p => p.Kmw),
|
||||||
|
Avg = g.Sum(p => p.Kmw * p.Weight) / g.Sum(p => p.Weight),
|
||||||
|
Max = g.Max(p => p.Kmw),
|
||||||
|
})
|
||||||
|
.OrderByDescending(g => g.Weight)
|
||||||
|
.ThenBy(g => g.Attr)
|
||||||
|
.ToListAsync();
|
||||||
|
var sortGroups = await deliveryParts
|
||||||
|
.GroupBy(p => p.SortId)
|
||||||
|
.Select(g => new {
|
||||||
|
SortId = g.Key,
|
||||||
|
Weight = g.Sum(p => p.Weight),
|
||||||
|
Min = g.Min(p => p.Kmw),
|
||||||
|
Avg = g.Sum(p => p.Kmw * p.Weight) / g.Sum(p => p.Weight),
|
||||||
|
Max = g.Max(p => p.Kmw),
|
||||||
|
})
|
||||||
|
.OrderByDescending(g => g.Weight)
|
||||||
|
.ThenBy(g => g.SortId)
|
||||||
|
.ToListAsync();
|
||||||
|
var groups = await deliveryParts
|
||||||
|
.GroupBy(p => new {
|
||||||
|
Attr = p.Attribute!.Name,
|
||||||
|
Cult = p.Cultivation!.Name,
|
||||||
|
p.SortId,
|
||||||
|
})
|
||||||
|
.Select(g => new {
|
||||||
|
g.Key.Attr,
|
||||||
|
g.Key.Cult,
|
||||||
|
g.Key.SortId,
|
||||||
|
Weight = g.Sum(p => p.Weight),
|
||||||
|
Min = g.Min(p => p.Kmw),
|
||||||
|
Avg = g.Sum(p => p.Kmw * p.Weight) / g.Sum(p => p.Weight),
|
||||||
|
Max = g.Max(p => p.Kmw)
|
||||||
|
})
|
||||||
|
.OrderByDescending(g => g.SortId)
|
||||||
|
.ThenBy(g => g.Attr)
|
||||||
|
.ThenBy(g => g.SortId)
|
||||||
|
.ToListAsync();
|
||||||
|
|
||||||
|
int rowNum = 1;
|
||||||
|
foreach (var attrG in attrGroups) {
|
||||||
|
rowNum++;
|
||||||
|
var name = attrG.Attr == null && attrG.Cult == null ? null : attrG.Attr + (attrG.Attr != null && attrG.Cult != null ? " / " : "") + attrG.Cult;
|
||||||
|
AddWeightToolTipRow(wGrid, rowNum++, name, null, attrG.Weight, attrG.Weight, weight);
|
||||||
|
foreach (var g in groups.Where(g => g.Attr == attrG.Attr && g.Cult == attrG.Cult).OrderByDescending(g => g.Weight).ThenBy(g => g.SortId)) {
|
||||||
|
AddWeightToolTipRow(wGrid, rowNum++, null, g.SortId, g.Weight, attrG.Weight, weight);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
rowNum = 2;
|
||||||
|
foreach (var attrG in attrGroups) {
|
||||||
|
rowNum++;
|
||||||
|
var name = attrG.Attr == null && attrG.Cult == null ? null : attrG.Attr + (attrG.Attr != null && attrG.Cult != null ? " / " : "") + attrG.Cult;
|
||||||
|
AddGradationToolTipRow(gGrid, rowNum++, name, null, attrG.Min, attrG.Avg, attrG.Max);
|
||||||
|
foreach (var g in groups.Where(g => g.Attr == attrG.Attr && g.Cult == attrG.Cult).OrderByDescending(g => g.Avg).ThenBy(g => g.SortId)) {
|
||||||
|
AddGradationToolTipRow(gGrid, rowNum++, null, g.SortId, g.Min, g.Avg, g.Max);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (attrGroups.Count == 1) {
|
||||||
|
var g = attrGroups.First();
|
||||||
|
var name = g.Attr == null && g.Cult == null ? null : g.Attr + (g.Attr != null && g.Cult != null ? " / " : "") + g.Cult;
|
||||||
|
if (name != null) {
|
||||||
|
wText += $" [{name}]";
|
||||||
|
gText += $" [{name}]";
|
||||||
|
}
|
||||||
|
if (sortGroups.Count > 1 && sortGroups.Count <= 4) {
|
||||||
|
wText += $" = {string.Join(" + ", sortGroups.Select(g => $"{g.Weight:N0} kg ({(double)g.Weight / weight:0%})" + (g.SortId == null ? "" : $" [{g.SortId}]")))}";
|
||||||
|
gText += $" = {string.Join(" + ", sortGroups.Select(g => $"{g.Min:N1}/{g.Avg:N1}/{g.Max:N1}" + (g.SortId == null ? "" : $" [{g.SortId}]")))}";
|
||||||
|
|
||||||
|
}
|
||||||
|
} else if (attrGroups.Count <= 4) {
|
||||||
|
wText += $" = {string.Join(" + ", attrGroups.Select(g => $"{g.Weight:N0} kg ({(double)g.Weight / weight:0%})" + (g.Attr == null && g.Cult == null ? "" : $" [{g.Attr}{(g.Attr != null && g.Cult != null ? " / " : "")}{g.Cult}]")))}";
|
||||||
|
gText += $" = {string.Join(" + ", attrGroups.Select(g => $"{g.Min:N1}/{g.Avg:N1}/{g.Max:N1}" + (g.Attr == null && g.Cult == null ? "" : $" [{g.Attr}{(g.Attr != null && g.Cult != null ? " / " : "")}{g.Cult}]")))}";
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return (wText, wGrid, gText, gGrid);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
620
Elwig/Services/MemberService.cs
Normal file
620
Elwig/Services/MemberService.cs
Normal file
@ -0,0 +1,620 @@
|
|||||||
|
using Elwig.Helpers;
|
||||||
|
using Elwig.Models.Entities;
|
||||||
|
using System.Collections.Generic;
|
||||||
|
using System.Linq;
|
||||||
|
using System.Threading.Tasks;
|
||||||
|
using System;
|
||||||
|
using Microsoft.EntityFrameworkCore;
|
||||||
|
using Elwig.Documents;
|
||||||
|
using System.Windows.Input;
|
||||||
|
using System.Windows;
|
||||||
|
using Elwig.Helpers.Billing;
|
||||||
|
using Elwig.Models.Dtos;
|
||||||
|
using Elwig.Helpers.Export;
|
||||||
|
using Microsoft.Win32;
|
||||||
|
using Elwig.ViewModels;
|
||||||
|
using System.IO;
|
||||||
|
using System.Net.Http;
|
||||||
|
|
||||||
|
namespace Elwig.Services {
|
||||||
|
public static class MemberService {
|
||||||
|
|
||||||
|
public enum ExportSubject {
|
||||||
|
All, AllActive, FromFilters, Selected,
|
||||||
|
};
|
||||||
|
|
||||||
|
public static async Task InitInputs(this MemberAdminViewModel vm) {
|
||||||
|
using var ctx = new AppDbContext();
|
||||||
|
vm.MgNrString = $"{await ctx.NextMgNr()}";
|
||||||
|
vm.EntryDate = DateTime.Now.ToString("dd.MM.yyyy");
|
||||||
|
if (vm.BranchSource.Count() == 1)
|
||||||
|
vm.Branch = vm.BranchSource.First();
|
||||||
|
vm.IsActive = true;
|
||||||
|
vm.ContactViaPost = true;
|
||||||
|
vm.EnableMemberReferenceButton = false;
|
||||||
|
}
|
||||||
|
|
||||||
|
public static void ClearInputs(this MemberAdminViewModel vm) {
|
||||||
|
vm.IsMemberSelected = false;
|
||||||
|
vm.MemberHasEmail = false;
|
||||||
|
vm.MemberCanSendEmail = false;
|
||||||
|
vm.EnableMemberReferenceButton = false;
|
||||||
|
vm.StatusDeliveriesLastSeason = "-";
|
||||||
|
vm.StatusDeliveriesLastSeasonInfo = $"{Utils.CurrentLastSeason - 1}";
|
||||||
|
vm.StatusDeliveriesLastSeasonToolTip = null;
|
||||||
|
vm.StatusDeliveriesThisSeason = "-";
|
||||||
|
vm.StatusDeliveriesThisSeasonInfo = $"{Utils.CurrentLastSeason}";
|
||||||
|
vm.StatusDeliveriesThisSeasonToolTip = null;
|
||||||
|
vm.StatusAreaCommitment = "-";
|
||||||
|
vm.StatusAreaCommitmentInfo = $"{Utils.CurrentLastSeason}";
|
||||||
|
vm.StatusAreaCommitmentToolTip = null;
|
||||||
|
vm.Age = "-";
|
||||||
|
}
|
||||||
|
|
||||||
|
public static async Task FillInputs(this MemberAdminViewModel vm, Member m) {
|
||||||
|
vm.IsMemberSelected = true;
|
||||||
|
vm.MgNrString = $"{m.MgNr}";
|
||||||
|
vm.PredecessorMgNrString = $"{m.PredecessorMgNr}";
|
||||||
|
vm.EnableMemberReferenceButton = m.PredecessorMgNr != null;
|
||||||
|
vm.Prefix = m.Prefix;
|
||||||
|
vm.GivenName = m.GivenName;
|
||||||
|
vm.FamilyName = m.FamilyName;
|
||||||
|
vm.Suffix = m.Suffix;
|
||||||
|
vm.Birthday = (m.Birthday != null) ? string.Join(".", m.Birthday.Split("-").Reverse()) : null;
|
||||||
|
if (m.Birthday?.Length == 10) {
|
||||||
|
vm.Age = Utils.GetAge(DateOnly.ParseExact(m.Birthday, "yyyy-MM-dd")).ToString();
|
||||||
|
} else if (m.Birthday != null) {
|
||||||
|
vm.Age = "ca. " + (DateTime.Now.Year - int.Parse(m.Birthday[^4..])).ToString();
|
||||||
|
} else {
|
||||||
|
vm.Age = "-";
|
||||||
|
}
|
||||||
|
vm.IsDeceased = m.IsDeceased;
|
||||||
|
vm.Address = m.Address;
|
||||||
|
if (m.PostalDest.AtPlz is AT_PlzDest p) {
|
||||||
|
vm.PlzString = $"{p.Plz}";
|
||||||
|
vm.Ort = ControlUtils.GetItemFromSource(vm.OrtSource, p);
|
||||||
|
} else {
|
||||||
|
vm.PlzString = null;
|
||||||
|
vm.Ort = null;
|
||||||
|
}
|
||||||
|
|
||||||
|
var emailAddrs = m.EmailAddresses.OrderBy(a => a.Nr).ToList();
|
||||||
|
for (int i = 0; i < vm.EmailAddresses.Count; i++) {
|
||||||
|
if (i < emailAddrs.Count) {
|
||||||
|
var emailAddr = emailAddrs[i];
|
||||||
|
vm.EmailAddresses[i] = emailAddr.Address;
|
||||||
|
} else {
|
||||||
|
vm.EmailAddresses[i] = null;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
var phoneNrs = m.TelephoneNumbers.OrderBy(p => p.Nr).ToList();
|
||||||
|
for (int i = 0; i < vm.PhoneNrs.Count; i++) {
|
||||||
|
if (i < phoneNrs.Count) {
|
||||||
|
var phoneNr = phoneNrs[i];
|
||||||
|
var idx = vm.PhoneNrTypes.Select((e, i) => (e, i)).FirstOrDefault(kv => kv.e.Key == phoneNr.Type).i;
|
||||||
|
vm.PhoneNrs[i] = new(idx, phoneNr.Number, phoneNr.Comment);
|
||||||
|
} else {
|
||||||
|
vm.PhoneNrs[i] = new();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
vm.Iban = m.Iban;
|
||||||
|
vm.Bic = m.Bic;
|
||||||
|
|
||||||
|
vm.UstIdNr = m.UstIdNr;
|
||||||
|
vm.LfbisNr = m.LfbisNr;
|
||||||
|
vm.IsBuchführend = m.IsBuchführend;
|
||||||
|
vm.IsOrganic = m.IsOrganic;
|
||||||
|
|
||||||
|
var billingAddr = m.BillingAddress;
|
||||||
|
if (billingAddr != null) {
|
||||||
|
vm.BillingName = billingAddr.Name;
|
||||||
|
vm.BillingAddress = billingAddr.Address;
|
||||||
|
if (billingAddr.PostalDest.AtPlz is AT_PlzDest b) {
|
||||||
|
vm.BillingPlzString = $"{b.Plz}";
|
||||||
|
vm.BillingOrt = ControlUtils.GetItemFromSource(vm.BillingOrtSource, b);
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
vm.BillingName = null;
|
||||||
|
vm.BillingAddress = null;
|
||||||
|
vm.BillingPlzString = null;
|
||||||
|
vm.BillingOrt = null;
|
||||||
|
}
|
||||||
|
|
||||||
|
vm.EntryDate = (m.EntryDateString != null) ? string.Join(".", m.EntryDateString.Split("-").Reverse()) : null;
|
||||||
|
vm.ExitDate = (m.ExitDateString != null) ? string.Join(".", m.ExitDateString.Split("-").Reverse()) : null;
|
||||||
|
vm.BusinessSharesString = $"{m.BusinessShares}";
|
||||||
|
vm.AccountingNr = m.AccountingNr;
|
||||||
|
vm.Branch = (Branch?)ControlUtils.GetItemFromSourceWithPk(vm.BranchSource, m.ZwstId);
|
||||||
|
vm.DefaultKg = (AT_Kg?)ControlUtils.GetItemFromSourceWithPk(vm.DefaultKgSource, m.DefaultKgNr);
|
||||||
|
vm.Comment = m.Comment;
|
||||||
|
vm.IsActive = m.IsActive;
|
||||||
|
vm.IsVollLieferant = m.IsVollLieferant;
|
||||||
|
vm.IsFunktionär = m.IsFunktionär;
|
||||||
|
vm.ContactViaPost = m.ContactViaPost;
|
||||||
|
vm.ContactViaEmail = m.ContactViaEmail;
|
||||||
|
|
||||||
|
Dictionary<int, int> deliveries;
|
||||||
|
using (var ctx = new AppDbContext()) {
|
||||||
|
var d1 = ctx.Deliveries.Where(d => d.Year == Utils.CurrentLastSeason - 1 && d.MgNr == m.MgNr);
|
||||||
|
var (_, d1Grid, _, _) = await DeliveryService.GenerateToolTip(d1.SelectMany(d => d.Parts));
|
||||||
|
vm.StatusDeliveriesLastSeasonInfo = $"{Utils.CurrentLastSeason - 1}";
|
||||||
|
vm.StatusDeliveriesLastSeason = $"{await d1.CountAsync():N0} ({await d1.SumAsync(d => d.Parts.Count):N0}), {await d1.SelectMany(d => d.Parts).SumAsync(p => p.Weight):N0} kg";
|
||||||
|
vm.StatusDeliveriesLastSeasonToolTip = d1Grid;
|
||||||
|
|
||||||
|
var d2 = ctx.Deliveries.Where(d => d.Year == Utils.CurrentLastSeason && d.MgNr == m.MgNr);
|
||||||
|
var (_, d2Grid, _, _) = await DeliveryService.GenerateToolTip(d2.SelectMany(d => d.Parts));
|
||||||
|
vm.StatusDeliveriesThisSeasonInfo = $"{Utils.CurrentLastSeason}";
|
||||||
|
vm.StatusDeliveriesThisSeason = $"{await d2.CountAsync():N0} ({await d2.SumAsync(d => d.Parts.Count):N0}), {await d2.SelectMany(d => d.Parts).SumAsync(p => p.Weight):N0} kg";
|
||||||
|
vm.StatusDeliveriesThisSeasonToolTip = d2Grid;
|
||||||
|
|
||||||
|
var c = m.ActiveAreaCommitments(ctx, Utils.CurrentLastSeason);
|
||||||
|
var s = await ctx.Seasons.FindAsync(await ctx.Seasons.MaxAsync(s => s.Year));
|
||||||
|
var (text, grid) = await AreaComService.GenerateToolTip(c, s?.MaxKgPerHa ?? 10_000);
|
||||||
|
vm.StatusAreaCommitmentInfo = $"{Utils.CurrentLastSeason}";
|
||||||
|
vm.StatusAreaCommitment = text;
|
||||||
|
vm.StatusAreaCommitmentToolTip = grid;
|
||||||
|
|
||||||
|
deliveries = ctx.Deliveries
|
||||||
|
.Where(d => d.MgNr == m.MgNr)
|
||||||
|
.SelectMany(d => d.Parts)
|
||||||
|
.GroupBy(d => d.Year)
|
||||||
|
.ToDictionary(g => g.Key, g => g.Sum(d => d.Weight));
|
||||||
|
}
|
||||||
|
|
||||||
|
vm.MemberHasEmail = m.EmailAddresses.Count > 0;
|
||||||
|
vm.MemberCanSendEmail = App.Config.Smtp != null && m.EmailAddresses.Count > 0;
|
||||||
|
vm.MemberHasDeliveries = Enumerable.Range(0, 9999).Select(i => deliveries.GetValueOrDefault(i, 0) > 0).ToList();
|
||||||
|
}
|
||||||
|
|
||||||
|
public static async Task<(List<string>, IQueryable<Member>, List<string>)> GetFilters(this MemberAdminViewModel vm, AppDbContext ctx) {
|
||||||
|
List<string> filterNames = [];
|
||||||
|
IQueryable<Member> memberQuery = ctx.Members;
|
||||||
|
if (vm.ShowOnlyActiveMembers) {
|
||||||
|
memberQuery = memberQuery.Where(m => m.IsActive);
|
||||||
|
filterNames.Add("aktive Mitglieder");
|
||||||
|
}
|
||||||
|
|
||||||
|
var filterMgNr = new List<int>();
|
||||||
|
var filterZwst = new List<string>();
|
||||||
|
var filterKgNr = new List<int>();
|
||||||
|
var filterLfbisNr = new List<string>();
|
||||||
|
var filterUstIdNr = new List<string>();
|
||||||
|
var filterAreaCom = new List<string>();
|
||||||
|
|
||||||
|
var filter = vm.TextFilter;
|
||||||
|
if (filter.Count > 0) {
|
||||||
|
var branches = await ctx.Branches.ToListAsync();
|
||||||
|
var mgnr = await ctx.Members.ToDictionaryAsync(m => m.MgNr.ToString(), m => m);
|
||||||
|
var kgs = await ctx.WbKgs.ToDictionaryAsync(k => k.AtKg.Name.ToLower(), k => k.AtKg);
|
||||||
|
var areaComs = await ctx.AreaCommitmentTypes.ToDictionaryAsync(t => $"{t.SortId}{t.AttrId}", t => t);
|
||||||
|
|
||||||
|
for (int i = 0; i < filter.Count; i++) {
|
||||||
|
var e = filter[i];
|
||||||
|
|
||||||
|
if (e.Length >= 5 && e.Length <= 10 && "funktionär".StartsWith(e, StringComparison.CurrentCultureIgnoreCase)) {
|
||||||
|
memberQuery = memberQuery.Where(m => m.IsFunktionär);
|
||||||
|
filter.RemoveAt(i--);
|
||||||
|
filterNames.Add("Funktionäre");
|
||||||
|
} else if (e.Length >= 6 && e.Length <= 11 && e[0] == '!' && "funktionär".StartsWith(e[1..], StringComparison.CurrentCultureIgnoreCase)) {
|
||||||
|
memberQuery = memberQuery.Where(m => !m.IsFunktionär);
|
||||||
|
filter.RemoveAt(i--);
|
||||||
|
filterNames.Add("Nicht-Funktionäre");
|
||||||
|
} else if (e.Equals("bio", StringComparison.CurrentCultureIgnoreCase)) {
|
||||||
|
memberQuery = memberQuery.Where(m => m.IsOrganic);
|
||||||
|
filter.RemoveAt(i--);
|
||||||
|
filterNames.Add("Bio-Betriebe");
|
||||||
|
} else if (e.Equals("!bio", StringComparison.CurrentCultureIgnoreCase)) {
|
||||||
|
memberQuery = memberQuery.Where(m => !m.IsOrganic);
|
||||||
|
filter.RemoveAt(i--);
|
||||||
|
filterNames.Add("Nicht-Bio-Betriebe");
|
||||||
|
} else if (e.Length >= 4 && e.Length <= 13 && "volllieferant".StartsWith(e, StringComparison.CurrentCultureIgnoreCase)) {
|
||||||
|
memberQuery = memberQuery.Where(m => m.IsVollLieferant);
|
||||||
|
filter.RemoveAt(i--);
|
||||||
|
filterNames.Add("Volllieferanten");
|
||||||
|
} else if (e.Length >= 5 && e.Length <= 14 && e[0] == '!' && "volllieferant".StartsWith(e[1..], StringComparison.CurrentCultureIgnoreCase)) {
|
||||||
|
memberQuery = memberQuery.Where(m => !m.IsVollLieferant);
|
||||||
|
filter.RemoveAt(i--);
|
||||||
|
filterNames.Add("Nicht-Vollieferanten");
|
||||||
|
} else if (e.Length >= 5 && e.Length <= 11 && "buchführend".StartsWith(e, StringComparison.CurrentCultureIgnoreCase)) {
|
||||||
|
memberQuery = memberQuery.Where(m => m.IsBuchführend);
|
||||||
|
filter.RemoveAt(i--);
|
||||||
|
filterNames.Add("buchführend");
|
||||||
|
} else if (e.Length >= 6 && e.Length <= 12 && e[0] == '!' && "buchführend".StartsWith(e[1..], StringComparison.CurrentCultureIgnoreCase)) {
|
||||||
|
memberQuery = memberQuery.Where(m => !m.IsBuchführend);
|
||||||
|
filter.RemoveAt(i--);
|
||||||
|
filterNames.Add("pauschaliert");
|
||||||
|
} else if (e.Length >= 8 && e.Length <= 12 && "pauschaliert".StartsWith(e, StringComparison.CurrentCultureIgnoreCase)) {
|
||||||
|
memberQuery = memberQuery.Where(m => !m.IsBuchführend);
|
||||||
|
filter.RemoveAt(i--);
|
||||||
|
filterNames.Add("pauschaliert");
|
||||||
|
} else if (e.Length >= 9 && e.Length <= 13 && e[0] == '!' && "pauschaliert".StartsWith(e[1..], StringComparison.CurrentCultureIgnoreCase)) {
|
||||||
|
memberQuery = memberQuery.Where(m => m.IsBuchführend);
|
||||||
|
filter.RemoveAt(i--);
|
||||||
|
filterNames.Add("buchführend");
|
||||||
|
} else if (e.Equals("email", StringComparison.CurrentCultureIgnoreCase)) {
|
||||||
|
memberQuery = memberQuery.Where(m => m.EmailAddresses.Count > 0);
|
||||||
|
filter.RemoveAt(i--);
|
||||||
|
filterNames.Add("mind. eine E-Mail-Adresse");
|
||||||
|
} else if (e.Equals("!email", StringComparison.CurrentCultureIgnoreCase)) {
|
||||||
|
memberQuery = memberQuery.Where(m => m.EmailAddresses.Count == 0);
|
||||||
|
filter.RemoveAt(i--);
|
||||||
|
filterNames.Add("keine E-Mail-Adresse");
|
||||||
|
} else if (e.Equals("telnr", StringComparison.CurrentCultureIgnoreCase)) {
|
||||||
|
memberQuery = memberQuery.Where(m => m.TelephoneNumbers.Count > 0);
|
||||||
|
filter.RemoveAt(i--);
|
||||||
|
filterNames.Add("mind. eine Tel.-Nr.");
|
||||||
|
} else if (e.Equals("!telnr", StringComparison.CurrentCultureIgnoreCase)) {
|
||||||
|
memberQuery = memberQuery.Where(m => m.TelephoneNumbers.Count == 0);
|
||||||
|
filter.RemoveAt(i--);
|
||||||
|
filterNames.Add("keine Tel.-Nr.");
|
||||||
|
} else if (e.Equals("kontakt:email", StringComparison.CurrentCultureIgnoreCase)) {
|
||||||
|
memberQuery = memberQuery.Where(m => m.ContactViaEmail);
|
||||||
|
filter.RemoveAt(i--);
|
||||||
|
filterNames.Add("Kontaktart E-Mail");
|
||||||
|
} else if (e.Equals("!kontakt:email", StringComparison.CurrentCultureIgnoreCase)) {
|
||||||
|
memberQuery = memberQuery.Where(m => !m.ContactViaEmail);
|
||||||
|
filter.RemoveAt(i--);
|
||||||
|
filterNames.Add("nicht Kontaktart E-Mail");
|
||||||
|
} else if (e.Equals("kontakt:post", StringComparison.CurrentCultureIgnoreCase)) {
|
||||||
|
memberQuery = memberQuery.Where(m => m.ContactViaPost);
|
||||||
|
filter.RemoveAt(i--);
|
||||||
|
filterNames.Add("Kontaktart Post");
|
||||||
|
} else if (e.Equals("!kontakt:post", StringComparison.CurrentCultureIgnoreCase)) {
|
||||||
|
memberQuery = memberQuery.Where(m => !m.ContactViaPost);
|
||||||
|
filter.RemoveAt(i--);
|
||||||
|
filterNames.Add("nicht Kontaktart Post");
|
||||||
|
} else if (e.All(char.IsAsciiDigit) && mgnr.ContainsKey(e)) {
|
||||||
|
filterMgNr.Add(int.Parse(e));
|
||||||
|
filter.RemoveAt(i--);
|
||||||
|
filterNames.Add($"MgNr. {e}");
|
||||||
|
} else if (kgs.TryGetValue(e, out var kg)) {
|
||||||
|
filterKgNr.Add(kg.KgNr);
|
||||||
|
filter.RemoveAt(i--);
|
||||||
|
filterNames.Add($"Stammgemeinde {kg.Name}");
|
||||||
|
} else if (e.StartsWith("zwst:")) {
|
||||||
|
try {
|
||||||
|
var branch = branches.Where(b => b.Name.StartsWith(e[5..], StringComparison.CurrentCultureIgnoreCase)).Single();
|
||||||
|
filterZwst.Add(branch.ZwstId);
|
||||||
|
filter.RemoveAt(i--);
|
||||||
|
filterNames.Add($"Zweigstelle {branch.Name}");
|
||||||
|
} catch (InvalidOperationException) { }
|
||||||
|
} else if (e.StartsWith('+') && e[1..].All(char.IsAsciiDigit)) {
|
||||||
|
memberQuery = memberQuery.Where(m => m.TelephoneNumbers.Any(t => t.Number.Replace(" ", "").StartsWith(e)));
|
||||||
|
filter.RemoveAt(i--);
|
||||||
|
filterNames.Add($"Tel.-Nr. {e}");
|
||||||
|
} else if (areaComs.ContainsKey(e.ToUpper())) {
|
||||||
|
filterAreaCom.Add(e.ToUpper());
|
||||||
|
filter.RemoveAt(i--);
|
||||||
|
filterNames.Add($"Flächenbindung {e.ToUpper()}");
|
||||||
|
} else if (Validator.CheckLfbisNr(e)) {
|
||||||
|
filterLfbisNr.Add(e);
|
||||||
|
filter.RemoveAt(i--);
|
||||||
|
filterNames.Add($"Betriebsnummer {e}");
|
||||||
|
} else if (Validator.CheckUstIdNr(e.ToUpper())) {
|
||||||
|
filterUstIdNr.Add(e.ToUpper());
|
||||||
|
filter.RemoveAt(i--);
|
||||||
|
filterNames.Add($"UID {e.ToUpper()}");
|
||||||
|
} else if (e.Length > 2 && e.StartsWith('"') && e.EndsWith('"')) {
|
||||||
|
filter[i] = e[1..^1];
|
||||||
|
} else if (e.Length < 2) {
|
||||||
|
filter.RemoveAt(i--);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (filterMgNr.Count > 0) memberQuery = memberQuery.Where(m => filterMgNr.Contains(m.MgNr));
|
||||||
|
if (filterKgNr.Count > 0) memberQuery = memberQuery.Where(m => m.DefaultKgNr != null && filterKgNr.Contains((int)m.DefaultKgNr));
|
||||||
|
if (filterZwst.Count > 0) memberQuery = memberQuery.Where(m => m.ZwstId != null && filterZwst.Contains(m.ZwstId));
|
||||||
|
if (filterAreaCom.Count > 0) memberQuery = memberQuery.Where(m => m.AreaCommitments.AsQueryable().Where(Utils.ActiveAreaCommitments()).Any(c => filterAreaCom.Contains(c.VtrgId)));
|
||||||
|
if (filterLfbisNr.Count > 0) memberQuery = memberQuery.Where(m => m.LfbisNr != null && filterLfbisNr.Contains(m.LfbisNr));
|
||||||
|
if (filterUstIdNr.Count > 0) memberQuery = memberQuery.Where(m => m.UstIdNr != null && filterUstIdNr.Contains(m.UstIdNr));
|
||||||
|
}
|
||||||
|
|
||||||
|
return (filterNames, memberQuery, filter);
|
||||||
|
}
|
||||||
|
|
||||||
|
public static async Task GenerateMemberDataSheet(Member m, ExportMode mode) {
|
||||||
|
Mouse.OverrideCursor = Cursors.AppStarting;
|
||||||
|
try {
|
||||||
|
using var ctx = new AppDbContext();
|
||||||
|
using var doc = new MemberDataSheet(m, ctx);
|
||||||
|
await Utils.ExportDocument(doc, mode, emailData: (m, MemberDataSheet.Name, "Im Anhang finden Sie das aktuelle Stammdatenblatt"));
|
||||||
|
} catch (Exception exc) {
|
||||||
|
MessageBox.Show(exc.Message, "Fehler", MessageBoxButton.OK, MessageBoxImage.Error);
|
||||||
|
}
|
||||||
|
Mouse.OverrideCursor = null;
|
||||||
|
}
|
||||||
|
|
||||||
|
public static async Task GenerateDeliveryConfirmation(Member m, int year, ExportMode mode) {
|
||||||
|
Mouse.OverrideCursor = Cursors.AppStarting;
|
||||||
|
try {
|
||||||
|
var b = new Billing(year);
|
||||||
|
await b.FinishSeason();
|
||||||
|
await b.CalculateBuckets();
|
||||||
|
await App.HintContextChange();
|
||||||
|
|
||||||
|
using var ctx = new AppDbContext();
|
||||||
|
var data = await DeliveryConfirmationDeliveryData.ForMember(ctx.DeliveryParts, year, m);
|
||||||
|
using var doc = new DeliveryConfirmation(ctx, year, m, data);
|
||||||
|
await Utils.ExportDocument(doc, mode, emailData: (m, $"{DeliveryConfirmation.Name} {year}", $"Im Anhang finden Sie die Anlieferungsbestätigung {year}"));
|
||||||
|
} catch (Exception exc) {
|
||||||
|
MessageBox.Show(exc.Message, "Fehler", MessageBoxButton.OK, MessageBoxImage.Error);
|
||||||
|
}
|
||||||
|
Mouse.OverrideCursor = null;
|
||||||
|
}
|
||||||
|
|
||||||
|
public static async Task GenerateCreditNote(Member m, int year, int avnr, ExportMode mode) {
|
||||||
|
Mouse.OverrideCursor = Cursors.AppStarting;
|
||||||
|
try {
|
||||||
|
using var ctx = new AppDbContext();
|
||||||
|
var v = (await ctx.PaymentVariants.FindAsync(year, avnr))!;
|
||||||
|
var data = await CreditNoteDeliveryData.ForPaymentVariant(ctx.CreditNoteDeliveryRows, ctx.Seasons, year, avnr);
|
||||||
|
var p = (await ctx.MemberPayments.FindAsync(year, avnr, m.MgNr))!;
|
||||||
|
var b = BillingData.FromJson((await ctx.PaymentVariants.FindAsync(year, avnr))!.Data);
|
||||||
|
|
||||||
|
using var doc = new CreditNote(ctx, p, data[m.MgNr],
|
||||||
|
b.ConsiderContractPenalties, b.ConsiderTotalPenalty, b.ConsiderAutoBusinessShares, b.ConsiderCustomModifiers,
|
||||||
|
await ctx.GetMemberUnderDelivery(year, m.MgNr));
|
||||||
|
await Utils.ExportDocument(doc, mode, emailData: (m, $"{CreditNote.Name} {v.Name}", $"Im Anhang finden Sie die Traubengutschrift {v.Name}"));
|
||||||
|
} catch (Exception exc) {
|
||||||
|
MessageBox.Show(exc.Message, "Fehler", MessageBoxButton.OK, MessageBoxImage.Error);
|
||||||
|
}
|
||||||
|
Mouse.OverrideCursor = null;
|
||||||
|
}
|
||||||
|
|
||||||
|
public static async Task GenerateMemberList(this MemberAdminViewModel vm, ExportSubject subject, ExportMode mode) {
|
||||||
|
using var ctx = new AppDbContext();
|
||||||
|
IQueryable<Member> query;
|
||||||
|
List<string> filterNames = [];
|
||||||
|
if (subject == ExportSubject.All) {
|
||||||
|
query = ctx.Members;
|
||||||
|
} else if (subject == ExportSubject.AllActive) {
|
||||||
|
query = ctx.Members.Where(m => m.IsActive);
|
||||||
|
filterNames.Add("aktive Mitglieder");
|
||||||
|
} else if (subject == ExportSubject.FromFilters) {
|
||||||
|
var (f, q, _) = await vm.GetFilters(ctx);
|
||||||
|
query = q;
|
||||||
|
filterNames.AddRange(f);
|
||||||
|
} else if (subject == ExportSubject.Selected) {
|
||||||
|
var mgnr = vm.SelectedMember?.MgNr;
|
||||||
|
if (mgnr == null) return;
|
||||||
|
query = ctx.Members.Where(m => m.MgNr == mgnr);
|
||||||
|
filterNames.Add($"{mgnr}");
|
||||||
|
} else {
|
||||||
|
throw new ArgumentException("Invalid value for ExportSubject");
|
||||||
|
}
|
||||||
|
|
||||||
|
if (vm.MemberListOrderByMgNr) {
|
||||||
|
query = query
|
||||||
|
.OrderBy(m => m.Branch!.Name)
|
||||||
|
.ThenBy(m => m.MgNr);
|
||||||
|
} else if (vm.MemberListOrderByName) {
|
||||||
|
query = query
|
||||||
|
.OrderBy(m => m.Branch!.Name)
|
||||||
|
.ThenBy(m => m.FamilyName)
|
||||||
|
.ThenBy(m => m.GivenName)
|
||||||
|
.ThenBy(m => m.MgNr);
|
||||||
|
} else if (vm.MemberListOrderByOrt) {
|
||||||
|
query = query
|
||||||
|
.OrderBy(m => m.Branch!.Name)
|
||||||
|
.ThenBy(m => m.DefaultWbKg!.AtKg.Name)
|
||||||
|
.ThenBy(m => m.FamilyName)
|
||||||
|
.ThenBy(m => m.GivenName)
|
||||||
|
.ThenBy(m => m.MgNr);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (mode == ExportMode.SaveList) {
|
||||||
|
var d = new SaveFileDialog() {
|
||||||
|
FileName = $"{MemberList.Name}.ods",
|
||||||
|
DefaultExt = "ods",
|
||||||
|
Filter = "OpenDocument Format Spreadsheet (*.ods)|*.ods",
|
||||||
|
Title = $"{MemberList.Name} speichern unter - Elwig"
|
||||||
|
};
|
||||||
|
if (d.ShowDialog() == true) {
|
||||||
|
Mouse.OverrideCursor = Cursors.AppStarting;
|
||||||
|
try {
|
||||||
|
var data = await MemberListData.FromQuery(query, filterNames);
|
||||||
|
using var ods = new OdsFile(d.FileName);
|
||||||
|
await ods.AddTable(data);
|
||||||
|
} catch (Exception exc) {
|
||||||
|
MessageBox.Show(exc.Message, "Fehler", MessageBoxButton.OK, MessageBoxImage.Error);
|
||||||
|
}
|
||||||
|
Mouse.OverrideCursor = null;
|
||||||
|
}
|
||||||
|
} else if (mode == ExportMode.Export) {
|
||||||
|
var d = new SaveFileDialog() {
|
||||||
|
FileName = subject == ExportSubject.Selected ? $"Mitglied_{vm.SelectedMember?.MgNr}.elwig.zip" : $"Mitglieder_{DateTime.Now:yyyy-MM-dd_HH-mm-ss}_{App.ZwstId}.elwig.zip",
|
||||||
|
DefaultExt = ".elwig.zip",
|
||||||
|
Filter = "Elwig-Export-Datei (*.elwig.zip)|*.elwig.zip",
|
||||||
|
Title = $"{MemberList.Name} speichern unter - Elwig"
|
||||||
|
};
|
||||||
|
if (d.ShowDialog() == true) {
|
||||||
|
Mouse.OverrideCursor = Cursors.AppStarting;
|
||||||
|
try {
|
||||||
|
var members = await query
|
||||||
|
.OrderBy(m => m.MgNr)
|
||||||
|
.Include(m => m.BillingAddress)
|
||||||
|
.Include(m => m.TelephoneNumbers)
|
||||||
|
.Include(m => m.EmailAddresses)
|
||||||
|
.AsSplitQuery()
|
||||||
|
.ToListAsync();
|
||||||
|
var areaComs = await query
|
||||||
|
.SelectMany(m => m.AreaCommitments)
|
||||||
|
.Include(c => c.Rd)
|
||||||
|
.ToListAsync();
|
||||||
|
await ElwigData.Export(d.FileName, members, areaComs, filterNames);
|
||||||
|
} catch (Exception exc) {
|
||||||
|
MessageBox.Show(exc.Message, "Fehler", MessageBoxButton.OK, MessageBoxImage.Error);
|
||||||
|
}
|
||||||
|
Mouse.OverrideCursor = null;
|
||||||
|
}
|
||||||
|
} else if (mode == ExportMode.Upload && App.Config.SyncUrl != null) {
|
||||||
|
Mouse.OverrideCursor = Cursors.AppStarting;
|
||||||
|
try {
|
||||||
|
var filename = $"{DateTime.Now:yyyy-MM-dd_HH-mm-ss}_{App.ZwstId}.elwig.zip";
|
||||||
|
var path = Path.Combine(App.TempPath, filename);
|
||||||
|
var list = await query
|
||||||
|
.OrderBy(m => m.MgNr)
|
||||||
|
.Include(m => m.BillingAddress)
|
||||||
|
.Include(m => m.TelephoneNumbers)
|
||||||
|
.Include(m => m.EmailAddresses)
|
||||||
|
.AsSplitQuery()
|
||||||
|
.ToListAsync();
|
||||||
|
if (list.Count == 0) {
|
||||||
|
MessageBox.Show("Es wurden keine Mitglieder zum Hochladen ausgewählt!", "Mitglieder hochladen",
|
||||||
|
MessageBoxButton.OK, MessageBoxImage.Error);
|
||||||
|
} else {
|
||||||
|
await ElwigData.Export(path, list, filterNames);
|
||||||
|
await Utils.UploadExportData(path, App.Config.SyncUrl, App.Config.SyncUsername, App.Config.SyncPassword);
|
||||||
|
MessageBox.Show($"Hochladen von {list.Count} Mitgliedern erfolgreich!", "Mitglieder hochgeladen",
|
||||||
|
MessageBoxButton.OK, MessageBoxImage.Information);
|
||||||
|
}
|
||||||
|
} catch (HttpRequestException exc) {
|
||||||
|
MessageBox.Show("Eventuell Internetverbindung prüfen!\n\n" + exc.Message, "Lieferungen hochladen", MessageBoxButton.OK, MessageBoxImage.Error);
|
||||||
|
} catch (TaskCanceledException exc) {
|
||||||
|
MessageBox.Show("Eventuell Internetverbindung prüfen!\n\n" + exc.Message, "Fehler", MessageBoxButton.OK, MessageBoxImage.Error);
|
||||||
|
} catch (Exception exc) {
|
||||||
|
MessageBox.Show(exc.Message, "Fehler", MessageBoxButton.OK, MessageBoxImage.Error);
|
||||||
|
}
|
||||||
|
Mouse.OverrideCursor = null;
|
||||||
|
} else {
|
||||||
|
Mouse.OverrideCursor = Cursors.AppStarting;
|
||||||
|
try {
|
||||||
|
var data = await MemberListData.FromQuery(query, filterNames);
|
||||||
|
using var doc = new MemberList(string.Join(" / ", filterNames), data);
|
||||||
|
await Utils.ExportDocument(doc, mode);
|
||||||
|
} catch (Exception exc) {
|
||||||
|
MessageBox.Show(exc.Message, "Fehler", MessageBoxButton.OK, MessageBoxImage.Error);
|
||||||
|
}
|
||||||
|
Mouse.OverrideCursor = null;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public static async Task<int> UpdateMember(this MemberAdminViewModel vm, int? oldMgNr) {
|
||||||
|
using var ctx = new AppDbContext();
|
||||||
|
var newMgNr = (int)vm.MgNr!;
|
||||||
|
var m = new Member {
|
||||||
|
MgNr = oldMgNr ?? newMgNr,
|
||||||
|
PredecessorMgNr = vm.PredecessorMgNr,
|
||||||
|
Prefix = string.IsNullOrEmpty(vm.Prefix) ? null : vm.Prefix,
|
||||||
|
GivenName = vm.GivenName!,
|
||||||
|
FamilyName = vm.FamilyName!,
|
||||||
|
Suffix = string.IsNullOrEmpty(vm.Suffix) ? null : vm.Suffix,
|
||||||
|
Birthday = string.IsNullOrEmpty(vm.Birthday) ? null : string.Join("-", vm.Birthday!.Split(".").Reverse()),
|
||||||
|
IsDeceased = vm.IsDeceased,
|
||||||
|
CountryNum = 40, // Austria AT AUT
|
||||||
|
PostalDestId = vm.Ort!.Id,
|
||||||
|
Address = vm.Address!,
|
||||||
|
|
||||||
|
Iban = string.IsNullOrEmpty(vm.Iban) ? null : vm.Iban?.Replace(" ", ""),
|
||||||
|
Bic = string.IsNullOrEmpty(vm.Bic) ? null : vm.Bic,
|
||||||
|
|
||||||
|
UstIdNr = string.IsNullOrEmpty(vm.UstIdNr) ? null : vm.UstIdNr,
|
||||||
|
LfbisNr = string.IsNullOrEmpty(vm.LfbisNr) ? null : vm.LfbisNr,
|
||||||
|
IsBuchführend = vm.IsBuchführend,
|
||||||
|
IsOrganic = vm.IsOrganic,
|
||||||
|
|
||||||
|
EntryDateString = string.IsNullOrEmpty(vm.EntryDate) ? null : string.Join("-", vm.EntryDate.Split(".").Reverse()),
|
||||||
|
ExitDateString = string.IsNullOrEmpty(vm.ExitDate) ? null : string.Join("-", vm.ExitDate.Split(".").Reverse()),
|
||||||
|
BusinessShares = (int)vm.BusinessShares!,
|
||||||
|
AccountingNr = string.IsNullOrEmpty(vm.AccountingNr) ? null : vm.AccountingNr,
|
||||||
|
IsActive = vm.IsActive,
|
||||||
|
IsVollLieferant = vm.IsVollLieferant,
|
||||||
|
IsFunktionär = vm.IsFunktionär,
|
||||||
|
ZwstId = vm.Branch?.ZwstId,
|
||||||
|
DefaultKgNr = vm.DefaultKg?.KgNr,
|
||||||
|
Comment = string.IsNullOrEmpty(vm.Comment) ? null : vm.Comment,
|
||||||
|
ContactViaPost = vm.ContactViaPost,
|
||||||
|
ContactViaEmail = vm.ContactViaEmail,
|
||||||
|
};
|
||||||
|
|
||||||
|
if (oldMgNr != null) {
|
||||||
|
ctx.Update(m);
|
||||||
|
} else {
|
||||||
|
ctx.Add(m);
|
||||||
|
}
|
||||||
|
|
||||||
|
ctx.RemoveRange(ctx.BillingAddresses.Where(a => a.MgNr == oldMgNr));
|
||||||
|
if (vm.BillingOrt != null && vm.BillingName != null) {
|
||||||
|
var p = vm.BillingOrt;
|
||||||
|
ctx.Add(new BillingAddr {
|
||||||
|
MgNr = m.MgNr,
|
||||||
|
Name = vm.BillingName,
|
||||||
|
Address = vm.BillingAddress ?? "",
|
||||||
|
CountryNum = p.CountryNum,
|
||||||
|
PostalDestId = p.Id,
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
ctx.RemoveRange(ctx.MemberTelephoneNrs.Where(t => t.MgNr == oldMgNr));
|
||||||
|
ctx.AddRange(vm.PhoneNrs
|
||||||
|
.Where(input => input.Number != null && input.Number != "")
|
||||||
|
.Select((input, i) => new MemberTelNr {
|
||||||
|
MgNr = m.MgNr,
|
||||||
|
Nr = i + 1,
|
||||||
|
Type = input.Type == -1 ? (input.Number!.StartsWith("+43 ") && input.Number![4] == '6' ? "mobile" : "landline") : vm.PhoneNrTypes[input.Type].Key,
|
||||||
|
Number = input.Number!,
|
||||||
|
Comment = input.Comment,
|
||||||
|
}));
|
||||||
|
|
||||||
|
ctx.RemoveRange(ctx.MemberEmailAddrs.Where(e => e.MgNr == oldMgNr));
|
||||||
|
ctx.AddRange(vm.EmailAddresses
|
||||||
|
.Where(input => input != null && input != "")
|
||||||
|
.Select((input, i) => new MemberEmailAddr {
|
||||||
|
MgNr = m.MgNr,
|
||||||
|
Nr = i + 1,
|
||||||
|
Address = input!,
|
||||||
|
Comment = null,
|
||||||
|
}));
|
||||||
|
|
||||||
|
await ctx.SaveChangesAsync();
|
||||||
|
|
||||||
|
if (vm.TransferPredecessorAreaComs is int year && m.PredecessorMgNr is int predecessor) {
|
||||||
|
var areaComs = await ctx.AreaCommitments
|
||||||
|
.Where(c => c.MgNr == predecessor && (c.YearTo == null || c.YearTo >= year))
|
||||||
|
.ToListAsync();
|
||||||
|
|
||||||
|
var fbNr = await ctx.NextFbNr();
|
||||||
|
ctx.AddRange(areaComs.Select((c, i) => new AreaCom {
|
||||||
|
FbNr = fbNr + i,
|
||||||
|
MgNr = m.MgNr,
|
||||||
|
VtrgId = c.VtrgId,
|
||||||
|
CultId = c.CultId,
|
||||||
|
Area = c.Area,
|
||||||
|
KgNr = c.KgNr,
|
||||||
|
GstNr = c.GstNr,
|
||||||
|
RdNr = c.RdNr,
|
||||||
|
YearFrom = year,
|
||||||
|
YearTo = c.YearTo,
|
||||||
|
}));
|
||||||
|
|
||||||
|
foreach (var ac in areaComs)
|
||||||
|
ac.YearTo = year - 1;
|
||||||
|
ctx.UpdateRange(areaComs);
|
||||||
|
await ctx.SaveChangesAsync();
|
||||||
|
}
|
||||||
|
vm.TransferPredecessorAreaComs = null;
|
||||||
|
|
||||||
|
if (vm.CancelAreaComs is int yearTo) {
|
||||||
|
var areaComs = await ctx.AreaCommitments
|
||||||
|
.Where(c => c.MgNr == m.MgNr && (c.YearTo == null || c.YearTo > yearTo))
|
||||||
|
.ToListAsync();
|
||||||
|
|
||||||
|
foreach (var ac in areaComs)
|
||||||
|
ac.YearTo = yearTo;
|
||||||
|
ctx.UpdateRange(areaComs);
|
||||||
|
await ctx.SaveChangesAsync();
|
||||||
|
}
|
||||||
|
vm.CancelAreaComs = null;
|
||||||
|
|
||||||
|
if (newMgNr != m.MgNr) {
|
||||||
|
await ctx.Database.ExecuteSqlAsync($"UPDATE member SET mgnr = {newMgNr} WHERE mgnr = {oldMgNr}");
|
||||||
|
}
|
||||||
|
|
||||||
|
await App.HintContextChange();
|
||||||
|
|
||||||
|
return newMgNr;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
@ -1,4 +1,4 @@
|
|||||||
<ResourceDictionary xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation">
|
<ResourceDictionary xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation">
|
||||||
<ResourceDictionary.MergedDictionaries>
|
<ResourceDictionary.MergedDictionaries>
|
||||||
<ResourceDictionary Source="/Elwig;component/Controls/UnitTextBox.xaml"/>
|
<ResourceDictionary Source="/Elwig;component/Controls/UnitTextBox.xaml"/>
|
||||||
<ResourceDictionary Source="/Elwig;component/Controls/IntegerUpDown.xaml"/>
|
<ResourceDictionary Source="/Elwig;component/Controls/IntegerUpDown.xaml"/>
|
||||||
|
95
Elwig/ViewModels/AreaComAdminViewModel.cs
Normal file
95
Elwig/ViewModels/AreaComAdminViewModel.cs
Normal file
@ -0,0 +1,95 @@
|
|||||||
|
using CommunityToolkit.Mvvm.ComponentModel;
|
||||||
|
using Elwig.Models.Entities;
|
||||||
|
using System.Collections.Generic;
|
||||||
|
using System.Linq;
|
||||||
|
using System.Windows.Controls;
|
||||||
|
|
||||||
|
namespace Elwig.ViewModels {
|
||||||
|
public partial class AreaComAdminViewModel : ObservableObject {
|
||||||
|
|
||||||
|
[ObservableProperty]
|
||||||
|
private string _title = "Flächenbindungen - Elwig";
|
||||||
|
|
||||||
|
public required Member FilterMember { get; set; }
|
||||||
|
|
||||||
|
[ObservableProperty]
|
||||||
|
private string? _searchQuery = "";
|
||||||
|
public List<string> TextFilter {
|
||||||
|
get => [.. SearchQuery?.ToLower().Split(' ').ToList().FindAll(e => e.Length > 0)];
|
||||||
|
set => SearchQuery = string.Join(' ', value.Where(e => e.Length > 0));
|
||||||
|
}
|
||||||
|
|
||||||
|
[ObservableProperty]
|
||||||
|
private bool _showOnlyActiveAreaComs;
|
||||||
|
|
||||||
|
[ObservableProperty]
|
||||||
|
private string? _fbNrString;
|
||||||
|
public int? FbNr {
|
||||||
|
get => int.TryParse(FbNrString, out var mgnr) ? mgnr : null;
|
||||||
|
set => FbNrString = $"{value}";
|
||||||
|
}
|
||||||
|
[ObservableProperty]
|
||||||
|
private string? _mgNrString;
|
||||||
|
public int? MgNr {
|
||||||
|
get => int.TryParse(MgNrString, out var mgnr) ? mgnr : null;
|
||||||
|
set => MgNrString = $"{value}";
|
||||||
|
}
|
||||||
|
[ObservableProperty]
|
||||||
|
private string? _yearFromString;
|
||||||
|
public int? YearFrom {
|
||||||
|
get => int.TryParse(YearFromString, out var year) ? year : null;
|
||||||
|
set => YearFromString = $"{value}";
|
||||||
|
}
|
||||||
|
[ObservableProperty]
|
||||||
|
private string? _yearToString;
|
||||||
|
public int? YearTo {
|
||||||
|
get => int.TryParse(YearToString, out var year) ? year : null;
|
||||||
|
set => YearToString = $"{value}";
|
||||||
|
}
|
||||||
|
|
||||||
|
[ObservableProperty]
|
||||||
|
private AreaComType? _areaComType;
|
||||||
|
[ObservableProperty]
|
||||||
|
private IEnumerable<AreaComType> _areaComTypeSource = [];
|
||||||
|
[ObservableProperty]
|
||||||
|
private object? _wineCultObj;
|
||||||
|
public WineCult? WineCult {
|
||||||
|
get => WineCultObj as WineCult;
|
||||||
|
set => WineCultObj = value ?? WineCultSource.FirstOrDefault();
|
||||||
|
}
|
||||||
|
[ObservableProperty]
|
||||||
|
private IEnumerable<object> _wineCultSource = [];
|
||||||
|
[ObservableProperty]
|
||||||
|
private string? _comment;
|
||||||
|
|
||||||
|
[ObservableProperty]
|
||||||
|
private AT_Kg? _kg;
|
||||||
|
[ObservableProperty]
|
||||||
|
private IEnumerable<AT_Kg> _kgSource = [];
|
||||||
|
[ObservableProperty]
|
||||||
|
private object? _rdObj;
|
||||||
|
public WbRd? Rd {
|
||||||
|
get => RdObj as WbRd;
|
||||||
|
set => RdObj = value ?? RdSource.FirstOrDefault();
|
||||||
|
}
|
||||||
|
[ObservableProperty]
|
||||||
|
private IEnumerable<object> _rdSource = [];
|
||||||
|
[ObservableProperty]
|
||||||
|
private string? _gstNr;
|
||||||
|
[ObservableProperty]
|
||||||
|
private string? _areaString;
|
||||||
|
public int? Area {
|
||||||
|
get => int.TryParse(AreaString, out var area) ? area : null;
|
||||||
|
set => AreaString = $"{value}";
|
||||||
|
}
|
||||||
|
|
||||||
|
[ObservableProperty]
|
||||||
|
private string _statusAreaCommitments = "-";
|
||||||
|
[ObservableProperty]
|
||||||
|
private string _statusContracts = "-";
|
||||||
|
[ObservableProperty]
|
||||||
|
private string _statusArea = "-";
|
||||||
|
[ObservableProperty]
|
||||||
|
private Grid? _statusAreaToolTip;
|
||||||
|
}
|
||||||
|
}
|
180
Elwig/ViewModels/DeliveryAdminViewModel.cs
Normal file
180
Elwig/ViewModels/DeliveryAdminViewModel.cs
Normal file
@ -0,0 +1,180 @@
|
|||||||
|
using CommunityToolkit.Mvvm.ComponentModel;
|
||||||
|
using Elwig.Helpers;
|
||||||
|
using Elwig.Models.Entities;
|
||||||
|
using System.Collections.Generic;
|
||||||
|
using System.Collections.ObjectModel;
|
||||||
|
using System.Linq;
|
||||||
|
using System.Windows.Controls;
|
||||||
|
|
||||||
|
namespace Elwig.ViewModels {
|
||||||
|
public partial class DeliveryAdminViewModel : ObservableObject {
|
||||||
|
|
||||||
|
public bool IsReceipt = false;
|
||||||
|
|
||||||
|
[ObservableProperty]
|
||||||
|
private string _title = "Lieferungen - Elwig";
|
||||||
|
|
||||||
|
public Member? FilterMember { get; set; }
|
||||||
|
|
||||||
|
[ObservableProperty]
|
||||||
|
private string? _searchQuery = "";
|
||||||
|
public List<string> TextFilter => [.. SearchQuery?.ToLower().Split(' ').ToList().FindAll(e => e.Length > 0)];
|
||||||
|
|
||||||
|
[ObservableProperty]
|
||||||
|
private string? _lastScaleError;
|
||||||
|
[ObservableProperty]
|
||||||
|
private string? _manualWeighingReason;
|
||||||
|
[ObservableProperty]
|
||||||
|
private string? _scaleId;
|
||||||
|
[ObservableProperty]
|
||||||
|
private string? _weighingData;
|
||||||
|
|
||||||
|
[ObservableProperty]
|
||||||
|
private bool _filterTodayOnly;
|
||||||
|
[ObservableProperty]
|
||||||
|
private bool _filterAllSeasons;
|
||||||
|
[ObservableProperty]
|
||||||
|
private bool _enableAllSeasons;
|
||||||
|
[ObservableProperty]
|
||||||
|
private string? _filterSeasonString;
|
||||||
|
public int? FilterSeason {
|
||||||
|
get => int.TryParse(FilterSeasonString, out var year) ? year : null;
|
||||||
|
set => FilterSeasonString = $"{value}";
|
||||||
|
}
|
||||||
|
|
||||||
|
[ObservableProperty]
|
||||||
|
private Delivery? _selectedDelivery;
|
||||||
|
[ObservableProperty]
|
||||||
|
private IEnumerable<Delivery> _deliveries = [];
|
||||||
|
|
||||||
|
[ObservableProperty]
|
||||||
|
private string? _mgNrString;
|
||||||
|
public int? MgNr {
|
||||||
|
get => int.TryParse(MgNrString, out var mgnr) ? mgnr : null;
|
||||||
|
set => MgNrString = $"{value}";
|
||||||
|
}
|
||||||
|
[ObservableProperty]
|
||||||
|
private Member? _member;
|
||||||
|
[ObservableProperty]
|
||||||
|
private IEnumerable<Member> _memberSource = [];
|
||||||
|
[ObservableProperty]
|
||||||
|
private string? _memberAddress;
|
||||||
|
[ObservableProperty]
|
||||||
|
private string? _lsNr;
|
||||||
|
[ObservableProperty]
|
||||||
|
private string? _date;
|
||||||
|
[ObservableProperty]
|
||||||
|
private string? _time;
|
||||||
|
[ObservableProperty]
|
||||||
|
private Branch? _branch;
|
||||||
|
[ObservableProperty]
|
||||||
|
private IEnumerable<Branch> _branchSource = [];
|
||||||
|
[ObservableProperty]
|
||||||
|
private string? _comment;
|
||||||
|
|
||||||
|
[ObservableProperty]
|
||||||
|
private string? _sortId;
|
||||||
|
[ObservableProperty]
|
||||||
|
private WineVar? _wineVar;
|
||||||
|
[ObservableProperty]
|
||||||
|
private IEnumerable<WineVar> _wineVarSource = [];
|
||||||
|
[ObservableProperty]
|
||||||
|
private object? _wineAttrObj;
|
||||||
|
public WineAttr? WineAttr {
|
||||||
|
get => WineAttrObj as WineAttr;
|
||||||
|
set => WineAttrObj = value ?? WineAttrSource.FirstOrDefault();
|
||||||
|
}
|
||||||
|
[ObservableProperty]
|
||||||
|
private IEnumerable<object> _wineAttrSource = [];
|
||||||
|
[ObservableProperty]
|
||||||
|
private object? _wineCultObj;
|
||||||
|
public WineCult? WineCult {
|
||||||
|
get => WineCultObj as WineCult;
|
||||||
|
set => WineCultObj = value ?? WineCultSource.FirstOrDefault();
|
||||||
|
}
|
||||||
|
[ObservableProperty]
|
||||||
|
private IEnumerable<object> _wineCultSource = [];
|
||||||
|
[ObservableProperty]
|
||||||
|
private string? _gradationOeString;
|
||||||
|
public double? GradationOe => double.TryParse(GradationOeString, out var oe) ? oe : null;
|
||||||
|
[ObservableProperty]
|
||||||
|
private string? _gradationKmwString;
|
||||||
|
public double? GradationKmw => double.TryParse(GradationKmwString, out var kmw) ? kmw : null;
|
||||||
|
[ObservableProperty]
|
||||||
|
private WineQualLevel? _wineQualityLevel;
|
||||||
|
[ObservableProperty]
|
||||||
|
private IEnumerable<WineQualLevel> _wineQualityLevelSource = [];
|
||||||
|
[ObservableProperty]
|
||||||
|
private bool _abgewertet;
|
||||||
|
|
||||||
|
[ObservableProperty]
|
||||||
|
private string? _weightString;
|
||||||
|
public int? Weight {
|
||||||
|
get => int.TryParse(WeightString?.Replace(Utils.GroupSeparator, ""), out var w) ? w : null;
|
||||||
|
set => WeightString = $"{value:N0}";
|
||||||
|
}
|
||||||
|
[ObservableProperty]
|
||||||
|
private bool _isManualWeighing;
|
||||||
|
[ObservableProperty]
|
||||||
|
private bool? _isNetWeightValue = false;
|
||||||
|
public bool IsNetWeight {
|
||||||
|
get => IsNetWeightValue ?? false;
|
||||||
|
set => IsNetWeightValue = value;
|
||||||
|
}
|
||||||
|
|
||||||
|
[ObservableProperty]
|
||||||
|
private WineOrigin? _wineOrigin;
|
||||||
|
[ObservableProperty]
|
||||||
|
private IEnumerable<WineOrigin> _wineOriginSource = [];
|
||||||
|
[ObservableProperty]
|
||||||
|
private object? _wineKgObj;
|
||||||
|
public AT_Kg? WineKg {
|
||||||
|
get => WineKgObj as AT_Kg;
|
||||||
|
set => WineKgObj = value ?? WineKgSource.FirstOrDefault();
|
||||||
|
}
|
||||||
|
[ObservableProperty]
|
||||||
|
private IEnumerable<object> _wineKgSource = [];
|
||||||
|
[ObservableProperty]
|
||||||
|
private object? _wineRdObj;
|
||||||
|
public WbRd? WineRd {
|
||||||
|
get => WineRdObj as WbRd;
|
||||||
|
set => WineRdObj = value ?? WineRdSource.FirstOrDefault();
|
||||||
|
}
|
||||||
|
[ObservableProperty]
|
||||||
|
private IEnumerable<object> _wineRdSource = [];
|
||||||
|
[ObservableProperty]
|
||||||
|
private bool? _isGebunden;
|
||||||
|
|
||||||
|
public ObservableCollection<Modifier> Modifiers { get; set; } = [];
|
||||||
|
[ObservableProperty]
|
||||||
|
private IEnumerable<Modifier> _modifiersSource = [];
|
||||||
|
[ObservableProperty]
|
||||||
|
private string? _partComment;
|
||||||
|
[ObservableProperty]
|
||||||
|
private string? _temperatureString;
|
||||||
|
public double? Temperature => double.TryParse(TemperatureString, out var t) ? t : null;
|
||||||
|
[ObservableProperty]
|
||||||
|
private string? _acidString;
|
||||||
|
public double? Acid => double.TryParse(AcidString, out var a) ? a : null;
|
||||||
|
[ObservableProperty]
|
||||||
|
private bool _isLesewagen;
|
||||||
|
[ObservableProperty]
|
||||||
|
private bool? _isHandPicked;
|
||||||
|
|
||||||
|
[ObservableProperty]
|
||||||
|
private string _statusMembers = "-";
|
||||||
|
[ObservableProperty]
|
||||||
|
private string _statusDeliveries = "-";
|
||||||
|
[ObservableProperty]
|
||||||
|
private string _statusVarieties = "-";
|
||||||
|
[ObservableProperty]
|
||||||
|
private string _statusWeight = "-";
|
||||||
|
[ObservableProperty]
|
||||||
|
private string _statusGradation = "-";
|
||||||
|
|
||||||
|
[ObservableProperty]
|
||||||
|
private Grid? _statusWeightToolTip;
|
||||||
|
[ObservableProperty]
|
||||||
|
private Grid? _statusGradationToolTip;
|
||||||
|
}
|
||||||
|
}
|
180
Elwig/ViewModels/MemberAdminViewModel.cs
Normal file
180
Elwig/ViewModels/MemberAdminViewModel.cs
Normal file
@ -0,0 +1,180 @@
|
|||||||
|
using CommunityToolkit.Mvvm.ComponentModel;
|
||||||
|
using Elwig.Helpers;
|
||||||
|
using Elwig.Models.Entities;
|
||||||
|
using System.Collections.Generic;
|
||||||
|
using System.Collections.ObjectModel;
|
||||||
|
using System.Linq;
|
||||||
|
using System.Windows;
|
||||||
|
using System.Windows.Controls;
|
||||||
|
|
||||||
|
namespace Elwig.ViewModels {
|
||||||
|
public partial class MemberAdminViewModel : ObservableObject {
|
||||||
|
|
||||||
|
public int? TransferPredecessorAreaComs = null;
|
||||||
|
public int? CancelAreaComs = null;
|
||||||
|
|
||||||
|
public ObservableCollection<KeyValuePair<string, string>> PhoneNrTypes { get; set; } = new(Utils.PhoneNrTypes);
|
||||||
|
|
||||||
|
[ObservableProperty]
|
||||||
|
private string? _searchQuery = "";
|
||||||
|
public List<string> TextFilter => [.. SearchQuery?.ToLower().Split(' ').ToList().FindAll(e => e.Length > 0)];
|
||||||
|
|
||||||
|
[ObservableProperty]
|
||||||
|
private bool _showOnlyActiveMembers;
|
||||||
|
|
||||||
|
[ObservableProperty]
|
||||||
|
private Member? _selectedMember;
|
||||||
|
[ObservableProperty]
|
||||||
|
private IEnumerable<Member> _members = [];
|
||||||
|
|
||||||
|
[ObservableProperty]
|
||||||
|
private bool _isMemberSelected;
|
||||||
|
[ObservableProperty]
|
||||||
|
private bool _memberHasEmail;
|
||||||
|
[ObservableProperty]
|
||||||
|
private bool _memberCanSendEmail;
|
||||||
|
[ObservableProperty]
|
||||||
|
private bool _enableMemberReferenceButton;
|
||||||
|
[ObservableProperty]
|
||||||
|
private bool _enableSearchInputs = true;
|
||||||
|
[ObservableProperty]
|
||||||
|
public IEnumerable<bool> _memberHasDeliveries = [ .. Enumerable.Range(0, 9999).Select(i => false) ];
|
||||||
|
|
||||||
|
[ObservableProperty]
|
||||||
|
private bool _memberListOrderByMgNr;
|
||||||
|
[ObservableProperty]
|
||||||
|
private bool _memberListOrderByName;
|
||||||
|
[ObservableProperty]
|
||||||
|
private bool _memberListOrderByOrt;
|
||||||
|
|
||||||
|
[ObservableProperty]
|
||||||
|
private string? _mgNrString;
|
||||||
|
public int? MgNr => int.TryParse(MgNrString, out var mgnr) ? mgnr : null;
|
||||||
|
[ObservableProperty]
|
||||||
|
private string? _predecessorMgNrString;
|
||||||
|
public int? PredecessorMgNr => int.TryParse(PredecessorMgNrString, out var mgnr) ? mgnr : null;
|
||||||
|
[ObservableProperty]
|
||||||
|
private string? _prefix;
|
||||||
|
[ObservableProperty]
|
||||||
|
private string? _givenName;
|
||||||
|
[ObservableProperty]
|
||||||
|
private string? _familyName;
|
||||||
|
[ObservableProperty]
|
||||||
|
private string? _suffix;
|
||||||
|
[ObservableProperty]
|
||||||
|
private string? _birthday;
|
||||||
|
[ObservableProperty]
|
||||||
|
private string? _age;
|
||||||
|
[ObservableProperty]
|
||||||
|
private bool _isDeceased;
|
||||||
|
[ObservableProperty]
|
||||||
|
private string? _address;
|
||||||
|
[ObservableProperty]
|
||||||
|
private string? _plzString;
|
||||||
|
public int? Plz => int.TryParse(PlzString, out var plz) ? plz : null;
|
||||||
|
[ObservableProperty]
|
||||||
|
private AT_PlzDest? _ort;
|
||||||
|
[ObservableProperty]
|
||||||
|
private IEnumerable<AT_PlzDest> _ortSource = [];
|
||||||
|
|
||||||
|
[ObservableProperty]
|
||||||
|
private string? _billingName;
|
||||||
|
[ObservableProperty]
|
||||||
|
private string? _billingAddress;
|
||||||
|
[ObservableProperty]
|
||||||
|
private string? _billingPlzString;
|
||||||
|
public int? BillingPlz => int.TryParse(BillingPlzString, out var plz) ? plz : null;
|
||||||
|
[ObservableProperty]
|
||||||
|
private AT_PlzDest? _billingOrt;
|
||||||
|
[ObservableProperty]
|
||||||
|
private IEnumerable<AT_PlzDest> _billingOrtSource = [];
|
||||||
|
|
||||||
|
[ObservableProperty]
|
||||||
|
private string? _iban;
|
||||||
|
[ObservableProperty]
|
||||||
|
private string? _bic;
|
||||||
|
|
||||||
|
[ObservableProperty]
|
||||||
|
private string? _ustIdNr;
|
||||||
|
[ObservableProperty]
|
||||||
|
private string? _lfbisNr;
|
||||||
|
[ObservableProperty]
|
||||||
|
private bool _isBuchführend;
|
||||||
|
[ObservableProperty]
|
||||||
|
private bool _isOrganic;
|
||||||
|
|
||||||
|
[ObservableProperty]
|
||||||
|
private string? _entryDate;
|
||||||
|
[ObservableProperty]
|
||||||
|
private string? _exitDate;
|
||||||
|
[ObservableProperty]
|
||||||
|
private string? _businessSharesString;
|
||||||
|
public int? BusinessShares => int.TryParse(BusinessSharesString, out var bs) ? bs : null;
|
||||||
|
[ObservableProperty]
|
||||||
|
private string? _accountingNr;
|
||||||
|
[ObservableProperty]
|
||||||
|
private bool _isActive;
|
||||||
|
[ObservableProperty]
|
||||||
|
private bool _isVollLieferant;
|
||||||
|
[ObservableProperty]
|
||||||
|
private bool _isFunktionär;
|
||||||
|
[ObservableProperty]
|
||||||
|
private Branch? _branch;
|
||||||
|
[ObservableProperty]
|
||||||
|
private IEnumerable<Branch> _branchSource = [];
|
||||||
|
[ObservableProperty]
|
||||||
|
private AT_Kg? _defaultKg;
|
||||||
|
[ObservableProperty]
|
||||||
|
private IEnumerable<AT_Kg> _defaultKgSource = [];
|
||||||
|
[ObservableProperty]
|
||||||
|
private string? _comment;
|
||||||
|
[ObservableProperty]
|
||||||
|
private bool _contactViaPost;
|
||||||
|
[ObservableProperty]
|
||||||
|
private bool _contactViaEmail;
|
||||||
|
|
||||||
|
public ObservableCollection<string?> EmailAddresses { get; private set; } = [null, null, null, null, null, null, null, null, null];
|
||||||
|
|
||||||
|
public partial class PhoneNr(int? type = null, string? number = null, string? comment = null) : ObservableObject {
|
||||||
|
[ObservableProperty]
|
||||||
|
public int _type = type ?? -1;
|
||||||
|
[ObservableProperty]
|
||||||
|
public string? _number = number;
|
||||||
|
[ObservableProperty]
|
||||||
|
public string? _comment = comment;
|
||||||
|
}
|
||||||
|
public ObservableCollection<PhoneNr> PhoneNrs { get; private set; } = [new(), new(), new(), new(), new(), new(), new(), new(), new()];
|
||||||
|
|
||||||
|
[ObservableProperty]
|
||||||
|
private string _statusMembers = "-";
|
||||||
|
[ObservableProperty]
|
||||||
|
private string? _statusMembersToolTip;
|
||||||
|
[ObservableProperty]
|
||||||
|
private string _statusBusinessShares = "-";
|
||||||
|
[ObservableProperty]
|
||||||
|
private string? _statusBusinessSharesToolTip;
|
||||||
|
[ObservableProperty]
|
||||||
|
private string _statusDeliveriesLastSeason = "-";
|
||||||
|
[ObservableProperty]
|
||||||
|
private string _statusDeliveriesLastSeasonInfo = "letzte Saison";
|
||||||
|
[ObservableProperty]
|
||||||
|
private Grid? _statusDeliveriesLastSeasonToolTip;
|
||||||
|
[ObservableProperty]
|
||||||
|
private string _statusDeliveriesThisSeason = "-";
|
||||||
|
[ObservableProperty]
|
||||||
|
private string _statusDeliveriesThisSeasonInfo = "aktuelle Saison";
|
||||||
|
[ObservableProperty]
|
||||||
|
private Grid? _statusDeliveriesThisSeasonToolTip;
|
||||||
|
[ObservableProperty]
|
||||||
|
private string _statusAreaCommitment = "-";
|
||||||
|
[ObservableProperty]
|
||||||
|
private Grid? _statusAreaCommitmentToolTip;
|
||||||
|
[ObservableProperty]
|
||||||
|
private string _statusAreaCommitmentInfo = "aktuelle Saison";
|
||||||
|
|
||||||
|
[ObservableProperty]
|
||||||
|
private Visibility _controlButtonsVisibility = Visibility.Visible;
|
||||||
|
[ObservableProperty]
|
||||||
|
private Visibility _editingButtonsVisibility = Visibility.Hidden;
|
||||||
|
}
|
||||||
|
}
|
@ -109,7 +109,7 @@ namespace Elwig.Windows {
|
|||||||
|
|
||||||
private void OnClosing(object? sender, CancelEventArgs evt) {
|
private void OnClosing(object? sender, CancelEventArgs evt) {
|
||||||
if ((IsCreating || IsEditing) && HasChanged) {
|
if ((IsCreating || IsEditing) && HasChanged) {
|
||||||
var r = System.Windows.MessageBox.Show("Soll das Fenster wirklich geschlossen werden?", "Schließen bestätigen",
|
var r = MessageBox.Show("Soll das Fenster wirklich geschlossen werden?", "Schließen bestätigen",
|
||||||
MessageBoxButton.YesNo, MessageBoxImage.Warning, MessageBoxResult.No);
|
MessageBoxButton.YesNo, MessageBoxImage.Warning, MessageBoxResult.No);
|
||||||
if (r != MessageBoxResult.Yes) {
|
if (r != MessageBoxResult.Yes) {
|
||||||
evt.Cancel = true;
|
evt.Cancel = true;
|
||||||
@ -162,11 +162,11 @@ namespace Elwig.Windows {
|
|||||||
if (input is TextBox tb && tb.Text.Length == 0) {
|
if (input is TextBox tb && tb.Text.Length == 0) {
|
||||||
ControlUtils.SetInputInvalid(input);
|
ControlUtils.SetInputInvalid(input);
|
||||||
Valid[input] = false;
|
Valid[input] = false;
|
||||||
} else if (input is ComboBox cb && cb.SelectedItem == null && cb.ItemsSource != null) {
|
} else if (input is ComboBox cb && cb.SelectedItem == null && cb.ItemsSource != null && cb.ItemsSource.Cast<object>().Any()) {
|
||||||
ControlUtils.SetInputInvalid(input);
|
ControlUtils.SetInputInvalid(input);
|
||||||
} else if (input is ListBox lb && lb.SelectedItem == null && lb.ItemsSource != null) {
|
} else if (input is ListBox lb && lb.SelectedItem == null && lb.ItemsSource != null && lb.ItemsSource.Cast<object>().Any()) {
|
||||||
ControlUtils.SetInputInvalid(input);
|
ControlUtils.SetInputInvalid(input);
|
||||||
} else if (input is CheckBox ckb && ckb.IsChecked != true) {
|
} else if (input is CheckBox ckb && ((ckb.IsThreeState && ckb.IsChecked == null) || (!ckb.IsThreeState && ckb.IsChecked != true))) {
|
||||||
ControlUtils.SetInputInvalid(input);
|
ControlUtils.SetInputInvalid(input);
|
||||||
Valid[input] = false;
|
Valid[input] = false;
|
||||||
} else if (input is RadioButton rb && rb.IsChecked != true) {
|
} else if (input is RadioButton rb && rb.IsChecked != true) {
|
||||||
@ -271,16 +271,28 @@ namespace Elwig.Windows {
|
|||||||
}
|
}
|
||||||
|
|
||||||
protected void ClearInputs(bool validate = true) {
|
protected void ClearInputs(bool validate = true) {
|
||||||
foreach (var tb in TextBoxInputs)
|
foreach (var tb in TextBoxInputs) {
|
||||||
tb.Text = "";
|
tb.Text = "";
|
||||||
foreach (var cb in ComboBoxInputs)
|
var binding = tb.GetBindingExpression(TextBox.TextProperty);
|
||||||
|
binding?.UpdateSource();
|
||||||
|
}
|
||||||
|
foreach (var cb in ComboBoxInputs) {
|
||||||
cb.SelectedItem = null;
|
cb.SelectedItem = null;
|
||||||
|
var binding = cb.GetBindingExpression(ComboBox.SelectedItemProperty);
|
||||||
|
binding?.UpdateSource();
|
||||||
|
}
|
||||||
foreach (var lb in ListBoxInputs)
|
foreach (var lb in ListBoxInputs)
|
||||||
lb.SelectedItems.Clear();
|
lb.SelectedItems.Clear();
|
||||||
foreach (var cb in CheckBoxInputs)
|
foreach (var cb in CheckBoxInputs) {
|
||||||
cb.IsChecked = cb.IsThreeState ? null : false;
|
cb.IsChecked = cb.IsThreeState ? null : false;
|
||||||
foreach (var rb in RadioButtonInputs)
|
var binding = cb.GetBindingExpression(CheckBox.IsCheckedProperty);
|
||||||
|
binding?.UpdateSource();
|
||||||
|
}
|
||||||
|
foreach (var rb in RadioButtonInputs) {
|
||||||
rb.IsChecked = rb.IsThreeState ? null : false;
|
rb.IsChecked = rb.IsThreeState ? null : false;
|
||||||
|
var binding = rb.GetBindingExpression(RadioButton.IsCheckedProperty);
|
||||||
|
binding?.UpdateSource();
|
||||||
|
}
|
||||||
if (validate) ValidateRequiredInputs();
|
if (validate) ValidateRequiredInputs();
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -327,7 +339,7 @@ namespace Elwig.Windows {
|
|||||||
protected async Task UpdatePlz(TextBox plzInput, ComboBox ortInput) {
|
protected async Task UpdatePlz(TextBox plzInput, ComboBox ortInput) {
|
||||||
var plzInputValid = Validator.CheckPlz(plzInput, RequiredInputs.Contains(plzInput)).IsValid;
|
var plzInputValid = Validator.CheckPlz(plzInput, RequiredInputs.Contains(plzInput)).IsValid;
|
||||||
|
|
||||||
List<AT_PlzDest>? list = null;
|
List<AT_PlzDest> list = [];
|
||||||
if (plzInputValid && plzInput.Text.Length == 4) {
|
if (plzInputValid && plzInput.Text.Length == 4) {
|
||||||
var plz = int.Parse(plzInput.Text);
|
var plz = int.Parse(plzInput.Text);
|
||||||
using var ctx = new AppDbContext();
|
using var ctx = new AppDbContext();
|
||||||
@ -338,7 +350,7 @@ namespace Elwig.Windows {
|
|||||||
}
|
}
|
||||||
|
|
||||||
ControlUtils.RenewItemsSource(ortInput, list);
|
ControlUtils.RenewItemsSource(ortInput, list);
|
||||||
if (list != null && ortInput.SelectedItem == null && list.Count == 1)
|
if (ortInput.SelectedItem == null && list.Count == 1)
|
||||||
ortInput.SelectedItem = list[0];
|
ortInput.SelectedItem = list[0];
|
||||||
UpdateComboBox(ortInput);
|
UpdateComboBox(ortInput);
|
||||||
}
|
}
|
||||||
@ -390,20 +402,24 @@ namespace Elwig.Windows {
|
|||||||
|
|
||||||
protected bool InputLostFocus(TextBox input, ValidationResult res, string? msg = null) {
|
protected bool InputLostFocus(TextBox input, ValidationResult res, string? msg = null) {
|
||||||
if (DoShowWarningWindows && !res.IsValid && !IsClosing && (IsEditing || IsCreating))
|
if (DoShowWarningWindows && !res.IsValid && !IsClosing && (IsEditing || IsCreating))
|
||||||
System.Windows.MessageBox.Show(res.ErrorContent.ToString(), msg ?? res.ErrorContent.ToString(), MessageBoxButton.OK, MessageBoxImage.Warning);
|
MessageBox.Show(res.ErrorContent?.ToString(), msg ?? res.ErrorContent?.ToString(), MessageBoxButton.OK, MessageBoxImage.Warning);
|
||||||
return res.IsValid;
|
return res.IsValid;
|
||||||
}
|
}
|
||||||
|
|
||||||
protected void CheckBox_Changed(object sender, RoutedEventArgs evt) {
|
protected void CheckBox_Changed(object sender, RoutedEventArgs evt) {
|
||||||
var input = (CheckBox)sender;
|
var input = (CheckBox)sender;
|
||||||
if (SenderIsRequired(input) && input.IsChecked != true) {
|
if (SenderIsRequired(input) && ((input.IsThreeState && input.IsChecked == null) || (!input.IsThreeState && input.IsChecked != true))) {
|
||||||
|
ValidateInput(input, false);
|
||||||
ControlUtils.SetInputInvalid(input);
|
ControlUtils.SetInputInvalid(input);
|
||||||
} else if (InputHasChanged(input)) {
|
|
||||||
ControlUtils.SetInputChanged(input);
|
|
||||||
} else if (InputIsNotDefault(input)) {
|
|
||||||
ControlUtils.SetInputNotDefault(input);
|
|
||||||
} else {
|
} else {
|
||||||
ControlUtils.ClearInputState(input);
|
ValidateInput(input, true);
|
||||||
|
if (InputHasChanged(input)) {
|
||||||
|
ControlUtils.SetInputChanged(input);
|
||||||
|
} else if (InputIsNotDefault(input)) {
|
||||||
|
ControlUtils.SetInputNotDefault(input);
|
||||||
|
} else {
|
||||||
|
ControlUtils.ClearInputState(input);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
UpdateButtons();
|
UpdateButtons();
|
||||||
}
|
}
|
||||||
@ -411,13 +427,17 @@ namespace Elwig.Windows {
|
|||||||
protected void RadioButton_Changed(object sender, RoutedEventArgs evt) {
|
protected void RadioButton_Changed(object sender, RoutedEventArgs evt) {
|
||||||
var input = (RadioButton)sender;
|
var input = (RadioButton)sender;
|
||||||
if (SenderIsRequired(input) && input.IsChecked != true) {
|
if (SenderIsRequired(input) && input.IsChecked != true) {
|
||||||
|
ValidateInput(input, false);
|
||||||
ControlUtils.SetInputInvalid(input);
|
ControlUtils.SetInputInvalid(input);
|
||||||
} else if (InputHasChanged(input)) {
|
|
||||||
ControlUtils.SetInputChanged(input);
|
|
||||||
} else if (InputIsNotDefault(input)) {
|
|
||||||
ControlUtils.SetInputNotDefault(input);
|
|
||||||
} else {
|
} else {
|
||||||
ControlUtils.ClearInputState(input);
|
ValidateInput(input, true);
|
||||||
|
if (InputHasChanged(input)) {
|
||||||
|
ControlUtils.SetInputChanged(input);
|
||||||
|
} else if (InputIsNotDefault(input)) {
|
||||||
|
ControlUtils.SetInputNotDefault(input);
|
||||||
|
} else {
|
||||||
|
ControlUtils.ClearInputState(input);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
UpdateButtons();
|
UpdateButtons();
|
||||||
}
|
}
|
||||||
@ -444,9 +464,9 @@ namespace Elwig.Windows {
|
|||||||
private void UpdateComboBox(Control input) {
|
private void UpdateComboBox(Control input) {
|
||||||
bool valid = false;
|
bool valid = false;
|
||||||
if (input is ComboBox cb) {
|
if (input is ComboBox cb) {
|
||||||
valid = cb.ItemsSource == null || cb.SelectedItem != null || !RequiredInputs.Contains(input);
|
valid = cb.ItemsSource == null || cb.SelectedItem != null || !RequiredInputs.Contains(input) || !cb.ItemsSource.Cast<object>().Any();
|
||||||
} else if (input is ListBox lb) {
|
} else if (input is ListBox lb) {
|
||||||
valid = lb.ItemsSource == null || lb.SelectedItem != null || !RequiredInputs.Contains(input);
|
valid = lb.ItemsSource == null || lb.SelectedItem != null || !RequiredInputs.Contains(input) || !lb.ItemsSource.Cast<object>().Any();
|
||||||
}
|
}
|
||||||
if (valid) {
|
if (valid) {
|
||||||
ValidateInput(input, true);
|
ValidateInput(input, true);
|
||||||
@ -464,115 +484,115 @@ namespace Elwig.Windows {
|
|||||||
UpdateButtons();
|
UpdateButtons();
|
||||||
}
|
}
|
||||||
|
|
||||||
protected void ComboBox_SelectionChanged(object sender, RoutedEventArgs evt) {
|
protected void ComboBox_SelectionChanged(object sender, RoutedEventArgs? evt) {
|
||||||
UpdateComboBox((Control)sender);
|
UpdateComboBox((Control)sender);
|
||||||
}
|
}
|
||||||
|
|
||||||
protected void IntegerInput_TextChanged(object sender, TextChangedEventArgs evt) {
|
protected void IntegerInput_TextChanged(object sender, TextChangedEventArgs? evt) {
|
||||||
// FIXME
|
// FIXME
|
||||||
InputTextChanged((TextBox)sender, Validator.CheckInteger);
|
InputTextChanged((TextBox)sender, Validator.CheckInteger);
|
||||||
}
|
}
|
||||||
|
|
||||||
protected void DecimalInput_TextChanged(object sender, TextChangedEventArgs evt) {
|
protected void DecimalInput_TextChanged(object sender, TextChangedEventArgs? evt) {
|
||||||
// FIXME
|
// FIXME
|
||||||
InputTextChanged((TextBox)sender, Validator.CheckDecimal);
|
InputTextChanged((TextBox)sender, Validator.CheckDecimal);
|
||||||
}
|
}
|
||||||
|
|
||||||
protected void PartialDateInput_TextChanged(object sender, TextChangedEventArgs evt) {
|
protected void PartialDateInput_TextChanged(object sender, TextChangedEventArgs? evt) {
|
||||||
InputTextChanged((TextBox)sender, Validator.CheckPartialDate);
|
InputTextChanged((TextBox)sender, Validator.CheckPartialDate);
|
||||||
}
|
}
|
||||||
|
|
||||||
protected void PartialDateInput_LostFocus(object sender, RoutedEventArgs evt) {
|
protected void PartialDateInput_LostFocus(object sender, RoutedEventArgs? evt) {
|
||||||
InputLostFocus((TextBox)sender, Validator.CheckPartialDate);
|
InputLostFocus((TextBox)sender, Validator.CheckPartialDate);
|
||||||
}
|
}
|
||||||
|
|
||||||
protected void DateInput_TextChanged(object sender, TextChangedEventArgs evt) {
|
protected void DateInput_TextChanged(object sender, TextChangedEventArgs? evt) {
|
||||||
InputTextChanged((TextBox)sender, Validator.CheckDate);
|
InputTextChanged((TextBox)sender, Validator.CheckDate);
|
||||||
}
|
}
|
||||||
|
|
||||||
protected void DateInput_LostFocus(object sender, RoutedEventArgs evt) {
|
protected void DateInput_LostFocus(object sender, RoutedEventArgs? evt) {
|
||||||
InputLostFocus((TextBox)sender, Validator.CheckDate);
|
InputLostFocus((TextBox)sender, Validator.CheckDate);
|
||||||
}
|
}
|
||||||
|
|
||||||
protected void TimeInput_TextChanged(object sender, TextChangedEventArgs evt) {
|
protected void TimeInput_TextChanged(object sender, TextChangedEventArgs? evt) {
|
||||||
InputTextChanged((TextBox)sender, Validator.CheckTime);
|
InputTextChanged((TextBox)sender, Validator.CheckTime);
|
||||||
}
|
}
|
||||||
|
|
||||||
protected void TimeInput_LostFocus(object sender, RoutedEventArgs evt) {
|
protected void TimeInput_LostFocus(object sender, RoutedEventArgs? evt) {
|
||||||
InputLostFocus((TextBox)sender, Validator.CheckTime);
|
InputLostFocus((TextBox)sender, Validator.CheckTime);
|
||||||
}
|
}
|
||||||
|
|
||||||
protected async void PlzInput_TextChanged(object sender, TextChangedEventArgs evt) {
|
protected async void PlzInput_TextChanged(object sender, TextChangedEventArgs? evt) {
|
||||||
var plz = (TextBox)sender;
|
var plz = (TextBox)sender;
|
||||||
InputTextChanged(plz, Validator.CheckPlz);
|
InputTextChanged(plz, Validator.CheckPlz);
|
||||||
if ("PLZ".Equals(plz.Tag))
|
if ("PLZ".Equals(plz.Tag))
|
||||||
await UpdatePlz(plz, GetPlzOrtInput(plz));
|
await UpdatePlz(plz, GetPlzOrtInput(plz));
|
||||||
}
|
}
|
||||||
|
|
||||||
protected async void PlzInput_LostFocus(object sender, RoutedEventArgs evt) {
|
protected async void PlzInput_LostFocus(object sender, RoutedEventArgs? evt) {
|
||||||
var plz = (TextBox)sender;
|
var plz = (TextBox)sender;
|
||||||
InputLostFocus(plz, Validator.CheckPlz);
|
InputLostFocus(plz, Validator.CheckPlz);
|
||||||
if ("PLZ".Equals(plz.Tag))
|
if ("PLZ".Equals(plz.Tag))
|
||||||
await UpdatePlz(plz, GetPlzOrtInput(plz));
|
await UpdatePlz(plz, GetPlzOrtInput(plz));
|
||||||
}
|
}
|
||||||
|
|
||||||
protected void EmailAddressInput_TextChanged(object sender, TextChangedEventArgs evt) {
|
protected void EmailAddressInput_TextChanged(object sender, TextChangedEventArgs? evt) {
|
||||||
InputTextChanged((TextBox)sender, Validator.CheckEmailAddress);
|
InputTextChanged((TextBox)sender, Validator.CheckEmailAddress);
|
||||||
}
|
}
|
||||||
|
|
||||||
protected void EmailAddressInput_LostFocus(object sender, RoutedEventArgs evt) {
|
protected void EmailAddressInput_LostFocus(object sender, RoutedEventArgs? evt) {
|
||||||
InputLostFocus((TextBox)sender, Validator.CheckEmailAddress);
|
InputLostFocus((TextBox)sender, Validator.CheckEmailAddress);
|
||||||
}
|
}
|
||||||
|
|
||||||
protected void PhoneNrInput_TextChanged(object sender, TextChangedEventArgs evt) {
|
protected void PhoneNrInput_TextChanged(object sender, TextChangedEventArgs? evt) {
|
||||||
InputTextChanged((TextBox)sender, Validator.CheckPhoneNumber);
|
InputTextChanged((TextBox)sender, Validator.CheckPhoneNumber);
|
||||||
}
|
}
|
||||||
|
|
||||||
protected void PhoneNrInput_LostFocus(object sender, RoutedEventArgs evt) {
|
protected void PhoneNrInput_LostFocus(object sender, RoutedEventArgs? evt) {
|
||||||
InputLostFocus((TextBox)sender, Validator.CheckPhoneNumber);
|
InputLostFocus((TextBox)sender, Validator.CheckPhoneNumber);
|
||||||
}
|
}
|
||||||
|
|
||||||
protected void IbanInput_TextChanged(object sender, TextChangedEventArgs evt) {
|
protected void IbanInput_TextChanged(object sender, TextChangedEventArgs? evt) {
|
||||||
InputTextChanged((TextBox)sender, Validator.CheckIban);
|
InputTextChanged((TextBox)sender, Validator.CheckIban);
|
||||||
}
|
}
|
||||||
|
|
||||||
protected void IbanInput_LostFocus(object sender, RoutedEventArgs evt) {
|
protected void IbanInput_LostFocus(object sender, RoutedEventArgs? evt) {
|
||||||
InputLostFocus((TextBox)sender, Validator.CheckIban);
|
InputLostFocus((TextBox)sender, Validator.CheckIban);
|
||||||
}
|
}
|
||||||
|
|
||||||
protected void BicInput_TextChanged(object sender, TextChangedEventArgs evt) {
|
protected void BicInput_TextChanged(object sender, TextChangedEventArgs? evt) {
|
||||||
InputTextChanged((TextBox)sender, Validator.CheckBic);
|
InputTextChanged((TextBox)sender, Validator.CheckBic);
|
||||||
}
|
}
|
||||||
|
|
||||||
protected void BicInput_LostFocus(object sender, RoutedEventArgs evt) {
|
protected void BicInput_LostFocus(object sender, RoutedEventArgs? evt) {
|
||||||
InputLostFocus((TextBox)sender, Validator.CheckBic);
|
InputLostFocus((TextBox)sender, Validator.CheckBic);
|
||||||
}
|
}
|
||||||
|
|
||||||
protected void UstIdNrInput_TextChanged(object sender, TextChangedEventArgs evt) {
|
protected void UstIdNrInput_TextChanged(object sender, TextChangedEventArgs? evt) {
|
||||||
InputTextChanged((TextBox)sender, Validator.CheckUstIdNr);
|
InputTextChanged((TextBox)sender, Validator.CheckUstIdNr);
|
||||||
}
|
}
|
||||||
|
|
||||||
protected void UstIdNrInput_LostFocus(object sender, RoutedEventArgs evt) {
|
protected void UstIdNrInput_LostFocus(object sender, RoutedEventArgs? evt) {
|
||||||
InputLostFocus((TextBox)sender, Validator.CheckUstIdNr);
|
InputLostFocus((TextBox)sender, Validator.CheckUstIdNr);
|
||||||
}
|
}
|
||||||
|
|
||||||
protected void LfbisNrInput_TextChanged(object sender, TextChangedEventArgs evt) {
|
protected void LfbisNrInput_TextChanged(object sender, TextChangedEventArgs? evt) {
|
||||||
InputTextChanged((TextBox)sender, Validator.CheckLfbisNr);
|
InputTextChanged((TextBox)sender, Validator.CheckLfbisNr);
|
||||||
}
|
}
|
||||||
|
|
||||||
protected void LfbisNrInput_LostFocus(object sender, RoutedEventArgs evt) {
|
protected void LfbisNrInput_LostFocus(object sender, RoutedEventArgs? evt) {
|
||||||
InputLostFocus((TextBox)sender, Validator.CheckLfbisNr);
|
InputLostFocus((TextBox)sender, Validator.CheckLfbisNr);
|
||||||
}
|
}
|
||||||
|
|
||||||
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);
|
||||||
}
|
}
|
||||||
|
|
||||||
protected void UpperCaseInput_LostFocus(object sender, RoutedEventArgs evt) {
|
protected void UpperCaseInput_LostFocus(object sender, RoutedEventArgs? evt) {
|
||||||
InputLostFocus((TextBox)sender, Validator.CheckUpperCase);
|
InputLostFocus((TextBox)sender, Validator.CheckUpperCase);
|
||||||
}
|
}
|
||||||
|
|
||||||
protected void AreaComTypeDetailsButton_Click(object sender, RoutedEventArgs evt) {
|
protected void AreaComTypeDetailsButton_Click(object sender, RoutedEventArgs? evt) {
|
||||||
App.FocusBaseDataAreaComType();
|
App.FocusBaseDataAreaComType();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -5,9 +5,12 @@
|
|||||||
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
|
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
|
||||||
xmlns:local="clr-namespace:Elwig.Windows"
|
xmlns:local="clr-namespace:Elwig.Windows"
|
||||||
xmlns:ctrl="clr-namespace:Elwig.Controls"
|
xmlns:ctrl="clr-namespace:Elwig.Controls"
|
||||||
mc:Ignorable="d"
|
xmlns:vm="clr-namespace:Elwig.ViewModels"
|
||||||
Title="Flächenbindungen - Elwig" Height="500" MinHeight="440" Width="920" MinWidth="860"
|
Title="{Binding Title}" Height="550" MinHeight="450" Width="920" MinWidth="860"
|
||||||
Loaded="Window_Loaded">
|
Loaded="Window_Loaded">
|
||||||
|
<Window.DataContext>
|
||||||
|
<vm:AreaComAdminViewModel/>
|
||||||
|
</Window.DataContext>
|
||||||
<Window.Resources>
|
<Window.Resources>
|
||||||
<Style TargetType="Label">
|
<Style TargetType="Label">
|
||||||
<Setter Property="HorizontalAlignment" Value="Left"/>
|
<Setter Property="HorizontalAlignment" Value="Left"/>
|
||||||
@ -48,6 +51,7 @@
|
|||||||
</Window.Resources>
|
</Window.Resources>
|
||||||
<Grid>
|
<Grid>
|
||||||
<Grid.RowDefinitions>
|
<Grid.RowDefinitions>
|
||||||
|
<RowDefinition Height="19"/>
|
||||||
<RowDefinition Height="*"/>
|
<RowDefinition Height="*"/>
|
||||||
<RowDefinition Height="24"/>
|
<RowDefinition Height="24"/>
|
||||||
</Grid.RowDefinitions>
|
</Grid.RowDefinitions>
|
||||||
@ -57,9 +61,12 @@
|
|||||||
<ColumnDefinition Width="*" MinWidth="280"/>
|
<ColumnDefinition Width="*" MinWidth="280"/>
|
||||||
</Grid.ColumnDefinitions>
|
</Grid.ColumnDefinitions>
|
||||||
|
|
||||||
<Grid Grid.Row="0" Grid.Column="0">
|
<Menu Grid.ColumnSpan="3" BorderThickness="0,0,0,1" BorderBrush="LightGray" Background="White">
|
||||||
|
</Menu>
|
||||||
|
|
||||||
|
<Grid Grid.Row="1" Grid.Column="0" Margin="5,0,0,0">
|
||||||
<Grid.RowDefinitions>
|
<Grid.RowDefinitions>
|
||||||
<RowDefinition Height="37"/>
|
<RowDefinition Height="35"/>
|
||||||
<RowDefinition Height="*"/>
|
<RowDefinition Height="*"/>
|
||||||
<RowDefinition Height="42"/>
|
<RowDefinition Height="42"/>
|
||||||
</Grid.RowDefinitions>
|
</Grid.RowDefinitions>
|
||||||
@ -69,11 +76,25 @@
|
|||||||
<ColumnDefinition Width="*"/>
|
<ColumnDefinition Width="*"/>
|
||||||
</Grid.ColumnDefinitions>
|
</Grid.ColumnDefinitions>
|
||||||
|
|
||||||
<TextBox x:Name="SearchInput" Grid.ColumnSpan="3" Margin="5,7,145,0" IsReadOnly="False"
|
<TextBox x:Name="SearchInput" Text="{Binding SearchQuery, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"
|
||||||
TextChanged="SearchInput_TextChanged"/>
|
Grid.ColumnSpan="3" Margin="5,5,190,0" IsReadOnly="False"
|
||||||
<CheckBox x:Name="ActiveAreaCommitmentInput" Content="Nur aktive anzeigen"
|
TextChanged="SearchInput_TextChanged">
|
||||||
|
<TextBox.ToolTip>
|
||||||
|
<TextBlock>
|
||||||
|
<Bold>Strg+F</Bold><LineBreak/><LineBreak/>
|
||||||
|
Flächenbindungen filtern und durchsuchen. Die Filter sind beliebig kombinierbar.<LineBreak/>
|
||||||
|
Groß- und Kleinschreibung ist in den meisten Fällen egal.<LineBreak/>
|
||||||
|
<LineBreak/>
|
||||||
|
Filtern nach:<LineBreak/>
|
||||||
|
<Bold>Sorte</Bold>: z.B. GV, zw, RR, ...<LineBreak/>
|
||||||
|
<Bold>Attribut</Bold>: z.B. Kabinett, dac, ... <LineBreak/>
|
||||||
|
<Bold>Flächenbindung</Bold>: z.B. GVK, GVD, ...
|
||||||
|
</TextBlock>
|
||||||
|
</TextBox.ToolTip>
|
||||||
|
</TextBox>
|
||||||
|
<CheckBox x:Name="ActiveAreaCommitmentInput" Content="Nur laufende anzeigen (2020)" IsChecked="{Binding ShowOnlyActiveAreaComs}"
|
||||||
Checked="ActiveAreaCommitmentInput_Changed" Unchecked="ActiveAreaCommitmentInput_Changed"
|
Checked="ActiveAreaCommitmentInput_Changed" Unchecked="ActiveAreaCommitmentInput_Changed"
|
||||||
HorizontalAlignment="Right" Margin="0,12,10,0" VerticalAlignment="Top" Grid.Column="1" Grid.ColumnSpan="2"/>
|
HorizontalAlignment="Right" Margin="0,10,10,0" VerticalAlignment="Top" Grid.Column="1" Grid.ColumnSpan="2"/>
|
||||||
|
|
||||||
<DataGrid x:Name="AreaCommitmentList" AutoGenerateColumns="False" HeadersVisibility="Column" IsReadOnly="True" GridLinesVisibility="None" SelectionMode="Single"
|
<DataGrid x:Name="AreaCommitmentList" AutoGenerateColumns="False" HeadersVisibility="Column" IsReadOnly="True" GridLinesVisibility="None" SelectionMode="Single"
|
||||||
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"
|
||||||
@ -90,7 +111,13 @@
|
|||||||
</Style>
|
</Style>
|
||||||
</DataGridTextColumn.CellStyle>
|
</DataGridTextColumn.CellStyle>
|
||||||
</DataGridTextColumn>
|
</DataGridTextColumn>
|
||||||
<DataGridTextColumn Header="Sorte" Binding="{Binding AreaComType.WineVar.SortId}" Width="70"/>
|
<DataGridTextColumn Header="Sorte" Binding="{Binding AreaComType.WineVar.SortId}" Width="70">
|
||||||
|
<DataGridTextColumn.CellStyle>
|
||||||
|
<Style>
|
||||||
|
<Setter Property="TextBlock.TextAlignment" Value="Center"/>
|
||||||
|
</Style>
|
||||||
|
</DataGridTextColumn.CellStyle>
|
||||||
|
</DataGridTextColumn>
|
||||||
<DataGridTextColumn Header="Attribut" Binding="{Binding AreaComType.WineAttr.Name}" Width="120"/>
|
<DataGridTextColumn Header="Attribut" Binding="{Binding AreaComType.WineAttr.Name}" Width="120"/>
|
||||||
</DataGrid.Columns>
|
</DataGrid.Columns>
|
||||||
</DataGrid>
|
</DataGrid>
|
||||||
@ -134,12 +161,12 @@
|
|||||||
</Button>
|
</Button>
|
||||||
</Grid>
|
</Grid>
|
||||||
|
|
||||||
<GridSplitter Grid.Column="1" Grid.Row="0" HorizontalAlignment="Stretch" VerticalAlignment="Stretch"/>
|
<GridSplitter Grid.Column="1" Grid.Row="1" HorizontalAlignment="Stretch" VerticalAlignment="Stretch"/>
|
||||||
|
|
||||||
<Grid Grid.Column="2" Grid.Row="0">
|
<Grid Grid.Column="2" Grid.Row="1">
|
||||||
<Grid.RowDefinitions>
|
<Grid.RowDefinitions>
|
||||||
<RowDefinition Height="*"/>
|
<RowDefinition Height="1.125*"/>
|
||||||
<RowDefinition Height="*"/>
|
<RowDefinition Height="1*"/>
|
||||||
</Grid.RowDefinitions>
|
</Grid.RowDefinitions>
|
||||||
|
|
||||||
<GroupBox Header="Vertrag" Grid.Column="2" Grid.Row="0" Grid.RowSpan="1" Margin="5,5,5,5">
|
<GroupBox Header="Vertrag" Grid.Column="2" Grid.Row="0" Grid.RowSpan="1" Margin="5,5,5,5">
|
||||||
@ -152,34 +179,40 @@
|
|||||||
</Grid.ColumnDefinitions>
|
</Grid.ColumnDefinitions>
|
||||||
|
|
||||||
<Label Content="FbNr.:" Margin="10,10,0,0" Grid.Column="0"/>
|
<Label Content="FbNr.:" Margin="10,10,0,0" Grid.Column="0"/>
|
||||||
<TextBox x:Name="FbNrInput" Margin="0,10,10,0" Grid.Column="1" TextAlignment="Right"
|
<TextBox x:Name="FbNrInput" Text="{Binding FbNrString, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"
|
||||||
|
Margin="0,10,10,0" Grid.Column="1" 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="MgNr.:" Margin="10,40,0,0" Grid.Column="0"/>
|
||||||
<TextBox x:Name="MgNrInput" IsEnabled="False"
|
<TextBox x:Name="MgNrInput" Text="{Binding MgNrString, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}" IsEnabled="False"
|
||||||
Margin="0,40,10,0" Grid.Column="1" TextAlignment="Right"/>
|
Margin="0,40,10,0" Grid.Column="1" TextAlignment="Right"/>
|
||||||
|
|
||||||
<Label Content="Von:" Margin="10,10,0,0" Grid.Column="2"/>
|
<Label Content="Von:" Margin="10,10,0,0" Grid.Column="2"/>
|
||||||
<TextBox x:Name="YearFromInput" Margin="0,10,10,0" Grid.Column="3" TextAlignment="Right"
|
<TextBox x:Name="YearFromInput" Text="{Binding YearFromString, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"
|
||||||
|
Margin="0,10,10,0" Grid.Column="3" TextAlignment="Right"
|
||||||
TextChanged="IntegerInput_TextChanged"/>
|
TextChanged="IntegerInput_TextChanged"/>
|
||||||
|
|
||||||
<Label Content="Bis:" Margin="10,40,0,0" Grid.Column="2"/>
|
<Label Content="Bis:" Margin="10,40,0,0" Grid.Column="2"/>
|
||||||
<TextBox x:Name="YearToInput" Margin="0,40,10,0" Grid.Column="3" TextAlignment="Right"
|
<TextBox x:Name="YearToInput" Text="{Binding YearToString, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"
|
||||||
|
Margin="0,40,10,0" Grid.Column="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" DisplayMemberPath="DisplayName" TextSearch.TextPath="DisplayName"
|
<ComboBox x:Name="AreaComTypeInput" SelectedItem="{Binding AreaComType, Mode=TwoWay}" ItemsSource="{Binding AreaComTypeSource, Mode=TwoWay}"
|
||||||
|
DisplayMemberPath="DisplayName" 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"
|
||||||
Grid.Column="3" VerticalAlignment="Top" HorizontalAlignment="Right" Width="25" Height="25" Margin="10,70,10,10"/>
|
Grid.Column="3" VerticalAlignment="Top" HorizontalAlignment="Right" Width="25" Height="25" Margin="10,70,10,10"/>
|
||||||
|
|
||||||
<Label Content="Bewirt.-Art:" Margin="10,100,0,0" Grid.Column="0" Grid.ColumnSpan="2"/>
|
<Label Content="Bewirt.-Art:" Margin="10,100,0,0" Grid.Column="0" Grid.ColumnSpan="2"/>
|
||||||
<ComboBox x:Name="WineCultivationInput" DisplayMemberPath="Name" TextSearch.TextPath="Name"
|
<ComboBox x:Name="WineCultivationInput" SelectedItem="{Binding WineCultObj, Mode=TwoWay}" ItemsSource="{Binding WineCultSource, Mode=TwoWay}"
|
||||||
|
DisplayMemberPath="Name" TextSearch.TextPath="Name"
|
||||||
HorizontalAlignment="Stretch" Margin="0,100,10,0" Grid.Column="1" Grid.ColumnSpan="3"/>
|
HorizontalAlignment="Stretch" Margin="0,100,10,0" Grid.Column="1" Grid.ColumnSpan="3"/>
|
||||||
|
|
||||||
<Label Content="Anmerkung:" Margin="10,130,0,0" Grid.Column="0" Grid.ColumnSpan="2"/>
|
<Label Content="Anmerkung:" Margin="10,130,0,0" Grid.Column="0" Grid.ColumnSpan="2"/>
|
||||||
<TextBox x:Name="CommentInput" TextChanged="TextBox_TextChanged"
|
<TextBox x:Name="CommentInput" Text="{Binding Comment, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"
|
||||||
|
TextChanged="TextBox_TextChanged"
|
||||||
HorizontalAlignment="Stretch" Margin="0,130,10,0" Grid.Column="1" Grid.ColumnSpan="3"/>
|
HorizontalAlignment="Stretch" Margin="0,130,10,0" Grid.Column="1" Grid.ColumnSpan="3"/>
|
||||||
</Grid>
|
</Grid>
|
||||||
</GroupBox>
|
</GroupBox>
|
||||||
@ -192,7 +225,8 @@
|
|||||||
</Grid.ColumnDefinitions>
|
</Grid.ColumnDefinitions>
|
||||||
|
|
||||||
<Label Content="KG:" Margin="10,10,0,0" Grid.Column="0"/>
|
<Label Content="KG:" Margin="10,10,0,0" Grid.Column="0"/>
|
||||||
<ComboBox x:Name="KgInput" ItemTemplate="{StaticResource KgNrTemplate}" TextSearch.TextPath="Name"
|
<ComboBox x:Name="KgInput" SelectedItem="{Binding Kg, Mode=TwoWay}" ItemsSource="{Binding KgSource, Mode=TwoWay}"
|
||||||
|
ItemTemplate="{StaticResource KgNrTemplate}" TextSearch.TextPath="Name"
|
||||||
HorizontalAlignment="Stretch" Margin="0,10,40,10" Grid.Column="1"
|
HorizontalAlignment="Stretch" Margin="0,10,40,10" Grid.Column="1"
|
||||||
SelectionChanged="KgInput_SelectionChanged"/>
|
SelectionChanged="KgInput_SelectionChanged"/>
|
||||||
<Button x:Name="KgDetailsButton" Content="" FontFamily="Segoe MDL2 Assets" FontSize="14" Padding="0,1,0,0"
|
<Button x:Name="KgDetailsButton" Content="" FontFamily="Segoe MDL2 Assets" FontSize="14" Padding="0,1,0,0"
|
||||||
@ -200,7 +234,8 @@
|
|||||||
Grid.Column="1" VerticalAlignment="Top" HorizontalAlignment="Right" Width="25" Height="25" Margin="10,10,10,10"/>
|
Grid.Column="1" VerticalAlignment="Top" HorizontalAlignment="Right" Width="25" Height="25" Margin="10,10,10,10"/>
|
||||||
|
|
||||||
<Label Content="Ried:" Margin="10,40,0,0" Grid.Column="0"/>
|
<Label Content="Ried:" Margin="10,40,0,0" Grid.Column="0"/>
|
||||||
<ComboBox x:Name="RdInput" DisplayMemberPath="Name" TextSearch.TextPath="Name" IsEditable="True"
|
<ComboBox x:Name="RdInput" SelectedItem="{Binding RdObj, Mode=TwoWay}" ItemsSource="{Binding RdSource, Mode=TwoWay}"
|
||||||
|
DisplayMemberPath="Name" TextSearch.TextPath="Name" IsEditable="True"
|
||||||
HorizontalAlignment="Stretch" Margin="0,40,40,10" Grid.Column="1"
|
HorizontalAlignment="Stretch" Margin="0,40,40,10" Grid.Column="1"
|
||||||
SelectionChanged="RdInput_SelectionChanged"/>
|
SelectionChanged="RdInput_SelectionChanged"/>
|
||||||
<Button x:Name="RdAddButton" Content="" FontFamily="Segoe MDL2 Assets" FontSize="16" Padding="0,0,0,0" IsEnabled="False"
|
<Button x:Name="RdAddButton" Content="" FontFamily="Segoe MDL2 Assets" FontSize="16" Padding="0,0,0,0" IsEnabled="False"
|
||||||
@ -208,11 +243,13 @@
|
|||||||
Grid.Column="1" VerticalAlignment="Top" HorizontalAlignment="Right" Width="25" Height="25" Margin="10,40,10,10"/>
|
Grid.Column="1" VerticalAlignment="Top" HorizontalAlignment="Right" Width="25" Height="25" Margin="10,40,10,10"/>
|
||||||
|
|
||||||
<Label Content="Parzelle(n):" Margin="10,70,0,0" Grid.Column="0"/>
|
<Label Content="Parzelle(n):" Margin="10,70,0,0" Grid.Column="0"/>
|
||||||
<TextBox x:Name="GstNrInput" Margin="0,70,10,0" Grid.Column="1" HorizontalAlignment="Stretch"
|
<TextBox x:Name="GstNrInput" Text="{Binding GstNr, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"
|
||||||
|
Margin="0,70,10,0" Grid.Column="1" HorizontalAlignment="Stretch"
|
||||||
TextChanged="TextBox_TextChanged"/>
|
TextChanged="TextBox_TextChanged"/>
|
||||||
|
|
||||||
<Label Content="Fläche:" Margin="10,100,0,0" Grid.Column="0"/>
|
<Label Content="Fläche:" Margin="10,100,0,0" Grid.Column="0"/>
|
||||||
<ctrl:UnitTextBox x:Name="AreaInput" Unit="m²" TextChanged="IntegerInput_TextChanged"
|
<ctrl:UnitTextBox x:Name="AreaInput" Unit="m²" Text="{Binding AreaString, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"
|
||||||
|
TextChanged="IntegerInput_TextChanged"
|
||||||
Grid.Column="1" Width="70" Margin="0,100,10,10" VerticalAlignment="Top" HorizontalAlignment="Left"/>
|
Grid.Column="1" Width="70" Margin="0,100,10,10" VerticalAlignment="Top" HorizontalAlignment="Left"/>
|
||||||
</Grid>
|
</Grid>
|
||||||
</GroupBox>
|
</GroupBox>
|
||||||
@ -223,9 +260,9 @@
|
|||||||
<ItemsPanelTemplate>
|
<ItemsPanelTemplate>
|
||||||
<Grid>
|
<Grid>
|
||||||
<Grid.ColumnDefinitions>
|
<Grid.ColumnDefinitions>
|
||||||
<ColumnDefinition Width="160"/>
|
<ColumnDefinition Width="180"/>
|
||||||
<ColumnDefinition Width="Auto"/>
|
<ColumnDefinition Width="Auto"/>
|
||||||
<ColumnDefinition Width="150"/>
|
<ColumnDefinition Width="180"/>
|
||||||
<ColumnDefinition Width="Auto"/>
|
<ColumnDefinition Width="Auto"/>
|
||||||
<ColumnDefinition Width="*"/>
|
<ColumnDefinition Width="*"/>
|
||||||
</Grid.ColumnDefinitions>
|
</Grid.ColumnDefinitions>
|
||||||
@ -233,15 +270,21 @@
|
|||||||
</ItemsPanelTemplate>
|
</ItemsPanelTemplate>
|
||||||
</StatusBar.ItemsPanel>
|
</StatusBar.ItemsPanel>
|
||||||
<StatusBarItem>
|
<StatusBarItem>
|
||||||
<TextBlock Name="StatusAreaCommitments" Text="Flächenbindungen: -"/>
|
<TextBlock>
|
||||||
|
Flächenbindungen: <Run Text="{Binding StatusAreaCommitments}"/>
|
||||||
|
</TextBlock>
|
||||||
</StatusBarItem>
|
</StatusBarItem>
|
||||||
<Separator Grid.Column="1"/>
|
<Separator Grid.Column="1"/>
|
||||||
<StatusBarItem Grid.Column="2">
|
<StatusBarItem Grid.Column="2">
|
||||||
<TextBlock Name="StatusArea" Text="Fläche: -"/>
|
<TextBlock ToolTip="{Binding StatusAreaToolTip}">
|
||||||
|
Fläche: <Run Text="{Binding StatusArea}"/>
|
||||||
|
</TextBlock>
|
||||||
</StatusBarItem>
|
</StatusBarItem>
|
||||||
<Separator Grid.Column="3"/>
|
<Separator Grid.Column="3"/>
|
||||||
<StatusBarItem Grid.Column="4">
|
<StatusBarItem Grid.Column="4">
|
||||||
<TextBlock Name="StatusContracts" Text="Vertragsarten: -"/>
|
<TextBlock>
|
||||||
|
Vertragsarten: <Run Text="{Binding StatusContracts}"/>
|
||||||
|
</TextBlock>
|
||||||
</StatusBarItem>
|
</StatusBarItem>
|
||||||
</StatusBar>
|
</StatusBar>
|
||||||
</Grid>
|
</Grid>
|
||||||
|
@ -6,21 +6,23 @@ using Elwig.Helpers;
|
|||||||
using Elwig.Models.Entities;
|
using Elwig.Models.Entities;
|
||||||
using System;
|
using System;
|
||||||
using System.Threading.Tasks;
|
using System.Threading.Tasks;
|
||||||
using System.Collections.Generic;
|
using Elwig.ViewModels;
|
||||||
|
using Elwig.Services;
|
||||||
|
using System.Windows.Input;
|
||||||
|
|
||||||
namespace Elwig.Windows {
|
namespace Elwig.Windows {
|
||||||
public partial class AreaComAdminWindow : AdministrationWindow {
|
public partial class AreaComAdminWindow : AdministrationWindow {
|
||||||
|
|
||||||
public int MgNr => Member.MgNr;
|
public AreaComAdminViewModel ViewModel => (AreaComAdminViewModel)DataContext;
|
||||||
|
|
||||||
private readonly Member Member;
|
private readonly RoutedCommand CtrlF = new("CtrlF", typeof(AreaComAdminWindow), [new KeyGesture(Key.F, ModifierKeys.Control)]);
|
||||||
private List<string> TextFilter = [];
|
|
||||||
|
|
||||||
public AreaComAdminWindow(int mgnr) {
|
public AreaComAdminWindow(int mgnr) {
|
||||||
InitializeComponent();
|
InitializeComponent();
|
||||||
|
CommandBindings.Add(new CommandBinding(CtrlF, FocusSearchInput));
|
||||||
using var ctx = new AppDbContext();
|
using var ctx = new AppDbContext();
|
||||||
Member = ctx.Members.Find(mgnr) ?? throw new ArgumentException("MgNr argument has invalid value");
|
ViewModel.FilterMember = ctx.Members.Find(mgnr) ?? throw new ArgumentException("MgNr argument has invalid value");
|
||||||
Title = $"Flächenbindungen - {Member.AdministrativeName} - Elwig";
|
ViewModel.Title = $"Flächenbindungen - {ViewModel.FilterMember.AdministrativeName} - Elwig";
|
||||||
ExemptInputs = [
|
ExemptInputs = [
|
||||||
MgNrInput, AreaCommitmentList, NewAreaCommitmentButton,
|
MgNrInput, AreaCommitmentList, NewAreaCommitmentButton,
|
||||||
EditAreaCommitmentButton, DeleteAreaCommitmentButton, AreaCommitmentSaveButton,
|
EditAreaCommitmentButton, DeleteAreaCommitmentButton, AreaCommitmentSaveButton,
|
||||||
@ -30,6 +32,10 @@ namespace Elwig.Windows {
|
|||||||
FbNrInput, YearFromInput, KgInput, RdInput,
|
FbNrInput, YearFromInput, KgInput, RdInput,
|
||||||
GstNrInput, AreaInput, AreaComTypeInput, WineCultivationInput
|
GstNrInput, AreaInput, AreaComTypeInput, WineCultivationInput
|
||||||
];
|
];
|
||||||
|
|
||||||
|
InitializeDelayTimer(SearchInput, SearchInput_TextChanged);
|
||||||
|
SearchInput.TextChanged -= SearchInput_TextChanged;
|
||||||
|
ActiveAreaCommitmentInput.Content = ((string)ActiveAreaCommitmentInput.Content).Replace("2020", $"{Utils.CurrentLastSeason}");
|
||||||
}
|
}
|
||||||
|
|
||||||
private void Window_Loaded(object sender, RoutedEventArgs e) {
|
private void Window_Loaded(object sender, RoutedEventArgs e) {
|
||||||
@ -37,21 +43,27 @@ namespace Elwig.Windows {
|
|||||||
LockInputs();
|
LockInputs();
|
||||||
}
|
}
|
||||||
|
|
||||||
private async Task RefreshAreaCommitmentList() {
|
private void FocusSearchInput(object sender, RoutedEventArgs evt) {
|
||||||
await RefreshAreaCommitmentListQuery();
|
if (!IsEditing && !IsCreating) {
|
||||||
|
SearchInput.Focus();
|
||||||
|
SearchInput.SelectAll();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private async Task RefreshAreaCommitmentListQuery(bool updateSort = false) {
|
private async Task RefreshList(bool updateSort = false) {
|
||||||
using var ctx = new AppDbContext();
|
using var ctx = new AppDbContext();
|
||||||
var (_, areaComQuery, filter) = await GetFilters(ctx);
|
var (_, areaComQuery, filter) = await ViewModel.GetFilters(ctx);
|
||||||
var areaComs = await areaComQuery
|
var areaComs = await areaComQuery
|
||||||
.Include(a => a.Kg.AtKg)
|
.Include(a => a.Kg.AtKg)
|
||||||
.Include(a => a.Rd!.Kg.AtKg)
|
.Include(a => a.Rd!.Kg.AtKg)
|
||||||
|
.Include(a => a.WineCult)
|
||||||
|
.Include(a => a.AreaComType.WineAttr)
|
||||||
|
.Include(a => a.AreaComType.WineVar)
|
||||||
.ToListAsync();
|
.ToListAsync();
|
||||||
|
|
||||||
if (filter.Count > 0 && areaComs.Count > 0) {
|
if (filter.Count > 0 && areaComs.Count > 0) {
|
||||||
var dict = areaComs.AsParallel()
|
var dict = areaComs.AsParallel()
|
||||||
.ToDictionary(d => d, d => d.SearchScore(TextFilter))
|
.ToDictionary(d => d, d => d.SearchScore(ViewModel.TextFilter))
|
||||||
.OrderByDescending(c => c.Value);
|
.OrderByDescending(c => c.Value);
|
||||||
var threshold = dict.Select(a => a.Value).Max() * 3 / 4;
|
var threshold = dict.Select(a => a.Value).Max() * 3 / 4;
|
||||||
areaComs = dict
|
areaComs = dict
|
||||||
@ -64,66 +76,21 @@ namespace Elwig.Windows {
|
|||||||
AreaCommitmentList_SelectionChanged, filter.Count > 0 ? ControlUtils.RenewSourceDefault.IfOnly : ControlUtils.RenewSourceDefault.None, !updateSort);
|
AreaCommitmentList_SelectionChanged, filter.Count > 0 ? ControlUtils.RenewSourceDefault.IfOnly : ControlUtils.RenewSourceDefault.None, !updateSort);
|
||||||
RefreshInputs();
|
RefreshInputs();
|
||||||
|
|
||||||
if(filter.Count == 0) {
|
if (filter.Count == 0) {
|
||||||
StatusAreaCommitments.Text = $"Flächenbindungen: {await areaComQuery.CountAsync()}";
|
ViewModel.StatusAreaCommitments = $"{await areaComQuery.CountAsync():N0}";
|
||||||
StatusArea.Text = $"Fläche: {await areaComQuery.Select(a => a.Area).SumAsync():N0} m²";
|
var s = await ctx.Seasons.FindAsync(await ctx.Seasons.MaxAsync(s => s.Year));
|
||||||
|
var (text, grid) = await AreaComService.GenerateToolTip(areaComQuery, s?.MaxKgPerHa ?? 10_000);
|
||||||
|
ViewModel.StatusArea = text;
|
||||||
|
ViewModel.StatusAreaToolTip = grid;
|
||||||
} else {
|
} else {
|
||||||
StatusAreaCommitments.Text = $"Flächenbindungen: {areaComs.Count}";
|
ViewModel.StatusAreaCommitments = $"{areaComs.Count:N0}";
|
||||||
StatusArea.Text = $"Fläche: {areaComs.Select(a => a.Area).Sum():N0} m²";
|
ViewModel.StatusArea = $"{areaComs.Select(a => a.Area).Sum():N0} m²";
|
||||||
|
ViewModel.StatusAreaToolTip = null;
|
||||||
}
|
}
|
||||||
var groups = areaComs.GroupBy(a => $"{a.AreaComType.SortId}{a.AreaComType.AttrId}").Select(a => (a.Key, a.Sum(b => b.Area))).OrderByDescending(a => a.Item2).ToList();
|
var groups = areaComs.GroupBy(a => $"{a.AreaComType.SortId}{a.AreaComType.AttrId}").Select(a => (a.Key, a.Sum(b => b.Area))).OrderByDescending(a => a.Item2).ToList();
|
||||||
StatusContracts.Text = $"Vertragsarten: {groups.Count} (" + string.Join(", ", groups.Select(g => $"{g.Key}: {g.Item2:N0} m²")) + ")";
|
ViewModel.StatusContracts = $"{groups.Count:N0}";
|
||||||
groups = areaComs.GroupBy(a => a.AreaComType.DisplayName).Select(a => (a.Key, a.Sum(b => b.Area))).OrderByDescending(a => a.Item2).ToList();
|
if (groups.Count > 0)
|
||||||
StatusContracts.ToolTip = $"Vertragsarten: {groups.Count}\n" + string.Join($"\n", groups.Select(g => $"{g.Key}: {g.Item2:N0} m²"));
|
ViewModel.StatusContracts += $" ({string.Join(", ", groups.Select(g => g.Key))})";
|
||||||
}
|
|
||||||
|
|
||||||
private async Task<(List<string>, IQueryable<AreaCom>, List<string>)> GetFilters(AppDbContext ctx) {
|
|
||||||
List<string> filterNames = [];
|
|
||||||
IQueryable<AreaCom> areaComQuery = ctx.AreaCommitments.Where(a => a.MgNr == Member.MgNr).OrderBy(a => a.FbNr);
|
|
||||||
if (ActiveAreaCommitmentInput.IsChecked == true) {
|
|
||||||
areaComQuery = Utils.ActiveAreaCommitments(areaComQuery);
|
|
||||||
filterNames.Add("aktiv");
|
|
||||||
}
|
|
||||||
|
|
||||||
var filterVar = new List<string>();
|
|
||||||
var filterNotVar = new List<string>();
|
|
||||||
var filterAttr = new List<string>();
|
|
||||||
var filterNotAttr = new List<string>();
|
|
||||||
|
|
||||||
var filter = TextFilter.ToList();
|
|
||||||
if (filter.Count > 0) {
|
|
||||||
var var = await ctx.WineVarieties.ToDictionaryAsync(v => v.SortId, v => v);
|
|
||||||
var attr = await ctx.WineAttributes.ToDictionaryAsync(a => a.Name.ToLower().Split(" ")[0], a => a);
|
|
||||||
|
|
||||||
for (int i = 0; i < filter.Count; i++) {
|
|
||||||
var e = filter[i];
|
|
||||||
if (e.Length == 2 && var.ContainsKey(e.ToUpper())) {
|
|
||||||
filterVar.Add(e.ToUpper());
|
|
||||||
filter.RemoveAt(i--);
|
|
||||||
filterNames.Add(var[e.ToUpper()].Name);
|
|
||||||
} else if (e.Length == 3 && e[0] == '!' && var.ContainsKey(e[1..].ToUpper())) {
|
|
||||||
filterNotVar.Add(e[1..].ToUpper());
|
|
||||||
filter.RemoveAt(i--);
|
|
||||||
} else if (attr.ContainsKey(e.ToLower())) {
|
|
||||||
var a = attr[e.ToLower()];
|
|
||||||
filterAttr.Add(a.AttrId);
|
|
||||||
filter.RemoveAt(i--);
|
|
||||||
filterNames.Add($"Attribut {a.Name}");
|
|
||||||
} else if (e[0] == '!' && attr.ContainsKey(e[1..].ToLower())) {
|
|
||||||
var a = attr[e[1..].ToLower()];
|
|
||||||
filterNotAttr.Add(a.AttrId);
|
|
||||||
filter.RemoveAt(i--);
|
|
||||||
filterNames.Add($"ohne Attribut {a.Name}");
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if (filterVar.Count > 0) areaComQuery = areaComQuery.Where(a => filterVar.Contains(a.AreaComType.WineVar.SortId));
|
|
||||||
if (filterNotVar.Count > 0) areaComQuery = areaComQuery.Where(a => !filterNotVar.Contains(a.AreaComType.WineVar.SortId));
|
|
||||||
if (filterAttr.Count > 0) areaComQuery = areaComQuery.Where(a => a.AreaComType.WineAttr != null && a.AreaComType.WineAttr.AttrId != null && filterAttr.Contains(a.AreaComType.WineAttr.AttrId));
|
|
||||||
if (filterNotAttr.Count > 0) areaComQuery = areaComQuery.Where(a => a.AreaComType.WineAttr == null || a.AreaComType.WineAttr.AttrId == null || !filterAttr.Contains(a.AreaComType.WineAttr.AttrId));
|
|
||||||
}
|
|
||||||
|
|
||||||
return (filterNames, areaComQuery, filter);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
private void RefreshInputs(bool validate = false) {
|
private void RefreshInputs(bool validate = false) {
|
||||||
@ -146,50 +113,28 @@ namespace Elwig.Windows {
|
|||||||
private void FillInputs(AreaCom a) {
|
private void FillInputs(AreaCom a) {
|
||||||
ClearOriginalValues();
|
ClearOriginalValues();
|
||||||
ClearDefaultValues();
|
ClearDefaultValues();
|
||||||
|
ViewModel.FillInputs(a);
|
||||||
FbNrInput.Text = a.FbNr.ToString();
|
|
||||||
MgNrInput.Text = a.MgNr.ToString();
|
|
||||||
YearFromInput.Text = a.YearFrom.ToString();
|
|
||||||
YearToInput.Text = a.YearTo.ToString();
|
|
||||||
|
|
||||||
ControlUtils.SelectItemWithPk(KgInput, a.KgNr);
|
|
||||||
if (a.RdNr != null) {
|
|
||||||
ControlUtils.SelectItemWithPk(RdInput, a.KgNr, a.RdNr);
|
|
||||||
} else {
|
|
||||||
RdInput.SelectedIndex = 0;
|
|
||||||
}
|
|
||||||
GstNrInput.Text = a.GstNr;
|
|
||||||
AreaInput.Text = a.Area.ToString();
|
|
||||||
|
|
||||||
ControlUtils.SelectItemWithPk(AreaComTypeInput, a.VtrgId);
|
|
||||||
if (a.CultId != null) {
|
|
||||||
ControlUtils.SelectItemWithPk(WineCultivationInput, a.CultId);
|
|
||||||
} else {
|
|
||||||
WineCultivationInput.SelectedIndex = 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
CommentInput.Text = a.Comment;
|
|
||||||
|
|
||||||
FinishInputFilling();
|
FinishInputFilling();
|
||||||
}
|
}
|
||||||
|
|
||||||
private async void InitInputs() {
|
private async void InitInputs() {
|
||||||
ClearOriginalValues();
|
ClearOriginalValues();
|
||||||
ClearDefaultValues();
|
ClearDefaultValues();
|
||||||
|
await ViewModel.InitInputs();
|
||||||
using (var ctx = new AppDbContext()) {
|
|
||||||
FbNrInput.Text = (await ctx.NextFbNr()).ToString();
|
|
||||||
MgNrInput.Text = Member.MgNr.ToString();
|
|
||||||
YearFromInput.Text = DateTime.Now.Year.ToString();
|
|
||||||
WineCultivationInput.SelectedIndex = 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
SetDefaultValue(FbNrInput);
|
SetDefaultValue(FbNrInput);
|
||||||
ValidateRequiredInputs();
|
ValidateRequiredInputs();
|
||||||
}
|
}
|
||||||
|
|
||||||
protected override async Task OnRenewContext(AppDbContext ctx) {
|
protected override async Task OnRenewContext(AppDbContext ctx) {
|
||||||
await base.OnRenewContext(ctx);
|
await base.OnRenewContext(ctx);
|
||||||
|
|
||||||
|
if (await ctx.Members.FindAsync(ViewModel.FilterMember.MgNr) is not Member m) {
|
||||||
|
Close();
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
ViewModel.FilterMember = m;
|
||||||
|
ViewModel.Title = $"Lieferungen - {ViewModel.FilterMember.AdministrativeName} - Elwig";
|
||||||
|
|
||||||
ControlUtils.RenewItemsSource(KgInput, await ctx.WbKgs
|
ControlUtils.RenewItemsSource(KgInput, await ctx.WbKgs
|
||||||
.Include(k => k.AtKg.WbKg!.Rds)
|
.Include(k => k.AtKg.WbKg!.Rds)
|
||||||
.Select(k => k.AtKg)
|
.Select(k => k.AtKg)
|
||||||
@ -205,7 +150,7 @@ namespace Elwig.Windows {
|
|||||||
.Cast<object>().ToListAsync();
|
.Cast<object>().ToListAsync();
|
||||||
cultList.Insert(0, new NullItem());
|
cultList.Insert(0, new NullItem());
|
||||||
ControlUtils.RenewItemsSource(WineCultivationInput, cultList, null, ControlUtils.RenewSourceDefault.First);
|
ControlUtils.RenewItemsSource(WineCultivationInput, cultList, null, ControlUtils.RenewSourceDefault.First);
|
||||||
await RefreshAreaCommitmentList();
|
await RefreshList();
|
||||||
}
|
}
|
||||||
|
|
||||||
protected override void ShortcutNew() {
|
protected override void ShortcutNew() {
|
||||||
@ -262,53 +207,10 @@ namespace Elwig.Windows {
|
|||||||
using var ctx = new AppDbContext();
|
using var ctx = new AppDbContext();
|
||||||
ctx.Remove(a);
|
ctx.Remove(a);
|
||||||
await ctx.SaveChangesAsync();
|
await ctx.SaveChangesAsync();
|
||||||
await RefreshAreaCommitmentList();
|
await RefreshList();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private async Task<int> UpdateAreaCom(int? oldFbNr) {
|
|
||||||
using var ctx = new AppDbContext();
|
|
||||||
int newFbNr = int.Parse(FbNrInput.Text);
|
|
||||||
|
|
||||||
var a = new AreaCom {
|
|
||||||
FbNr = oldFbNr ?? newFbNr,
|
|
||||||
MgNr = int.Parse(MgNrInput.Text),
|
|
||||||
YearFrom = int.Parse(YearFromInput.Text),
|
|
||||||
YearTo = (YearToInput.Text == "") ? null : int.Parse(YearToInput.Text),
|
|
||||||
KgNr = ((AT_Kg)KgInput.SelectedItem).KgNr,
|
|
||||||
RdNr = (RdInput.SelectedItem as WbRd)?.RdNr,
|
|
||||||
GstNr = GstNrInput.Text.Trim(),
|
|
||||||
Area = int.Parse(AreaInput.Text),
|
|
||||||
VtrgId = (AreaComTypeInput.SelectedItem as AreaComType)!.VtrgId,
|
|
||||||
CultId = (WineCultivationInput.SelectedItem as WineCult)?.CultId,
|
|
||||||
Comment = (CommentInput.Text == "") ? null : CommentInput.Text.Trim(),
|
|
||||||
};
|
|
||||||
|
|
||||||
if (RdInput.SelectedItem is WbRd rd) {
|
|
||||||
if (rd.RdNr == 0) {
|
|
||||||
rd.RdNr = await ctx.NextRdNr(a.KgNr);
|
|
||||||
a.RdNr = rd.RdNr;
|
|
||||||
ctx.Add(rd);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if (oldFbNr != null) {
|
|
||||||
ctx.Update(a);
|
|
||||||
} else {
|
|
||||||
ctx.Add(a);
|
|
||||||
}
|
|
||||||
|
|
||||||
await ctx.SaveChangesAsync();
|
|
||||||
|
|
||||||
if (newFbNr != a.FbNr) {
|
|
||||||
await ctx.Database.ExecuteSqlAsync($"UPDATE area_commitment SET fbnr = {newFbNr} WHERE fbnr = {oldFbNr}");
|
|
||||||
}
|
|
||||||
|
|
||||||
await App.HintContextChange();
|
|
||||||
|
|
||||||
return newFbNr;
|
|
||||||
}
|
|
||||||
|
|
||||||
protected override void ShortcutSave() {
|
protected override void ShortcutSave() {
|
||||||
if (!AreaCommitmentSaveButton.IsEnabled || AreaCommitmentSaveButton.Visibility != Visibility.Visible)
|
if (!AreaCommitmentSaveButton.IsEnabled || AreaCommitmentSaveButton.Visibility != Visibility.Visible)
|
||||||
return;
|
return;
|
||||||
@ -318,7 +220,7 @@ namespace Elwig.Windows {
|
|||||||
private async void AreaCommitmentSaveButton_Click(object? sender, RoutedEventArgs? evt) {
|
private async void AreaCommitmentSaveButton_Click(object? sender, RoutedEventArgs? evt) {
|
||||||
int? fbnr = null;
|
int? fbnr = null;
|
||||||
try {
|
try {
|
||||||
fbnr = await UpdateAreaCom((AreaCommitmentList.SelectedItem as AreaCom)?.FbNr);
|
fbnr = await ViewModel.UpdateAreaCommitment((AreaCommitmentList.SelectedItem as AreaCom)?.FbNr);
|
||||||
} 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;
|
||||||
@ -332,9 +234,9 @@ namespace Elwig.Windows {
|
|||||||
LockInputs();
|
LockInputs();
|
||||||
UnlockSearchInputs();
|
UnlockSearchInputs();
|
||||||
FinishInputFilling();
|
FinishInputFilling();
|
||||||
await RefreshAreaCommitmentList();
|
await RefreshList();
|
||||||
RefreshInputs();
|
RefreshInputs();
|
||||||
SearchInput.Text = "";
|
ViewModel.SearchQuery = "";
|
||||||
ControlUtils.SelectItem(AreaCommitmentList, AreaCommitmentList.ItemsSource.Cast<AreaCom>().Where(a => a.FbNr == fbnr).FirstOrDefault());
|
ControlUtils.SelectItem(AreaCommitmentList, AreaCommitmentList.ItemsSource.Cast<AreaCom>().Where(a => a.FbNr == fbnr).FirstOrDefault());
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -435,12 +337,13 @@ namespace Elwig.Windows {
|
|||||||
}
|
}
|
||||||
|
|
||||||
private async void ActiveAreaCommitmentInput_Changed(object sender, RoutedEventArgs evt) {
|
private async void ActiveAreaCommitmentInput_Changed(object sender, RoutedEventArgs evt) {
|
||||||
await RefreshAreaCommitmentListQuery();
|
await RefreshList();
|
||||||
}
|
}
|
||||||
|
|
||||||
private async void SearchInput_TextChanged(object sender, RoutedEventArgs evt) {
|
private async void SearchInput_TextChanged(object sender, RoutedEventArgs evt) {
|
||||||
TextFilter = SearchInput.Text.ToLower().Split(" ").ToList().FindAll(e => e.Length > 0);
|
var binding = ((TextBox)sender).GetBindingExpression(TextBox.TextProperty);
|
||||||
await RefreshAreaCommitmentListQuery(true);
|
binding?.UpdateSource();
|
||||||
|
await RefreshList(true);
|
||||||
}
|
}
|
||||||
|
|
||||||
private void KgInput_SelectionChanged(object sender, SelectionChangedEventArgs evt) {
|
private void KgInput_SelectionChanged(object sender, SelectionChangedEventArgs evt) {
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
using Elwig.Helpers;
|
using Elwig.Helpers;
|
||||||
using Elwig.Models.Entities;
|
using Elwig.Models.Entities;
|
||||||
using Microsoft.EntityFrameworkCore;
|
using Microsoft.EntityFrameworkCore;
|
||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
using Elwig.Models.Entities;
|
using Elwig.Models.Entities;
|
||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
using System.Collections.ObjectModel;
|
using System.Collections.ObjectModel;
|
||||||
using System.Windows.Controls;
|
using System.Windows.Controls;
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
using Elwig.Helpers;
|
using Elwig.Helpers;
|
||||||
using Elwig.Models.Entities;
|
using Elwig.Models.Entities;
|
||||||
using LinqKit;
|
using LinqKit;
|
||||||
using Microsoft.EntityFrameworkCore;
|
using Microsoft.EntityFrameworkCore;
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
using Elwig.Dialogs;
|
using Elwig.Dialogs;
|
||||||
using Elwig.Helpers;
|
using Elwig.Helpers;
|
||||||
using Elwig.Models.Entities;
|
using Elwig.Models.Entities;
|
||||||
using Microsoft.EntityFrameworkCore;
|
using Microsoft.EntityFrameworkCore;
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
using Elwig.Helpers;
|
using Elwig.Helpers;
|
||||||
using Elwig.Models.Entities;
|
using Elwig.Models.Entities;
|
||||||
using Microsoft.EntityFrameworkCore;
|
using Microsoft.EntityFrameworkCore;
|
||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
using Elwig.Helpers;
|
using Elwig.Helpers;
|
||||||
using Elwig.Models.Entities;
|
using Elwig.Models.Entities;
|
||||||
using Microsoft.EntityFrameworkCore;
|
using Microsoft.EntityFrameworkCore;
|
||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
<local:ContextWindow
|
<local:ContextWindow
|
||||||
x:Class="Elwig.Windows.ChartWindow"
|
x:Class="Elwig.Windows.ChartWindow"
|
||||||
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"
|
||||||
|
@ -4,9 +4,13 @@
|
|||||||
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:local="clr-namespace:Elwig.Windows"
|
xmlns:local="clr-namespace:Elwig.Windows"
|
||||||
|
xmlns:vm="clr-namespace:Elwig.ViewModels"
|
||||||
xmlns:ctrl="clr-namespace:Elwig.Controls"
|
xmlns:ctrl="clr-namespace:Elwig.Controls"
|
||||||
Title="Lieferungen - Elwig" Height="720" Width="1100" MinHeight="720" MinWidth="1000"
|
Title="{Binding Title}" Height="720" Width="1100" MinHeight="720" MinWidth="1000"
|
||||||
Loaded="Window_Loaded">
|
Loaded="Window_Loaded">
|
||||||
|
<Window.DataContext>
|
||||||
|
<vm:DeliveryAdminViewModel/>
|
||||||
|
</Window.DataContext>
|
||||||
<Window.Resources>
|
<Window.Resources>
|
||||||
<Style TargetType="Label">
|
<Style TargetType="Label">
|
||||||
<Setter Property="HorizontalAlignment" Value="Left"/>
|
<Setter Property="HorizontalAlignment" Value="Left"/>
|
||||||
@ -120,15 +124,20 @@
|
|||||||
<MenuItem x:Name="Menu_Bki_SaveList" Header="Traubentransportscheinliste speichern..."/>
|
<MenuItem x:Name="Menu_Bki_SaveList" Header="Traubentransportscheinliste speichern..."/>
|
||||||
</MenuItem>
|
</MenuItem>
|
||||||
<MenuItem Header="Export">
|
<MenuItem Header="Export">
|
||||||
|
<MenuItem x:Name="Menu_Export_ExportSelected" Header="...von ausgewählter Lieferung speichern..." IsEnabled="False"
|
||||||
|
Click="Menu_Export_ExportSelected_Click"/>
|
||||||
|
<MenuItem x:Name="Menu_Export_UploadSelected" Header="...von ausgewählter Lieferung hochladen" IsEnabled="False"
|
||||||
|
Click="Menu_Export_UploadSelected_Click"/>
|
||||||
|
<Separator/>
|
||||||
<MenuItem x:Name="Menu_Export_ExportFilters" Header="...aus Filtern speichern..."
|
<MenuItem x:Name="Menu_Export_ExportFilters" Header="...aus Filtern speichern..."
|
||||||
Click="Menu_Export_ExportFilters_Click"/>
|
Click="Menu_Export_ExportFilters_Click"/>
|
||||||
<MenuItem x:Name="Menu_Export_UploadFilters" Header="...aus Filtern hochladen"
|
<MenuItem x:Name="Menu_Export_UploadFilters" Header="...aus Filtern hochladen"
|
||||||
Click="Menu_Export_UploadFilters_Click"/>
|
Click="Menu_Export_UploadFilters_Click"/>
|
||||||
<Separator/>
|
<Separator/>
|
||||||
<MenuItem x:Name="Menu_Export_ExportToday" Header="...von heute speichern..."
|
<MenuItem x:Name="Menu_Export_ExportSeason" Header="...von Saison/Zweigstelle speichern..."
|
||||||
Click="Menu_Export_ExportToday_Click"/>
|
Click="Menu_Export_ExportSeason_Click"/>
|
||||||
<MenuItem x:Name="Menu_Export_UploadToday" Header="...von heute hochladen"
|
<MenuItem x:Name="Menu_Export_UploadSeason" Header="...von Saison/Zweigstelle hochladen"
|
||||||
Click="Menu_Export_UploadToday_Click" InputGestureText="Strg+H"/>
|
Click="Menu_Export_UploadSeason_Click"/>
|
||||||
</MenuItem>
|
</MenuItem>
|
||||||
<MenuItem Header="Einstellungen">
|
<MenuItem Header="Einstellungen">
|
||||||
<MenuItem x:Name="Menu_Settings_EnableFreeEditing" Header="Freie Bearbeitung aktivieren"
|
<MenuItem x:Name="Menu_Settings_EnableFreeEditing" Header="Freie Bearbeitung aktivieren"
|
||||||
@ -148,7 +157,8 @@
|
|||||||
<ColumnDefinition Width="*"/>
|
<ColumnDefinition Width="*"/>
|
||||||
</Grid.ColumnDefinitions>
|
</Grid.ColumnDefinitions>
|
||||||
|
|
||||||
<TextBox x:Name="SearchInput" Grid.ColumnSpan="3" Margin="5,10,161,0" IsReadOnly="False"
|
<TextBox x:Name="SearchInput" Text="{Binding SearchQuery, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"
|
||||||
|
Grid.ColumnSpan="3" Margin="5,10,156,0" IsReadOnly="False"
|
||||||
TextChanged="SearchInput_TextChanged">
|
TextChanged="SearchInput_TextChanged">
|
||||||
<TextBox.ToolTip>
|
<TextBox.ToolTip>
|
||||||
<TextBlock>
|
<TextBlock>
|
||||||
@ -171,21 +181,23 @@
|
|||||||
<Bold>Handwiegung</Bold>: handw[iegung], !Handw[iegung] (alle ohne Handwiegung)<LineBreak/>
|
<Bold>Handwiegung</Bold>: handw[iegung], !Handw[iegung] (alle ohne Handwiegung)<LineBreak/>
|
||||||
<Bold>Handlese</Bold>: Handl[ese], !handl[ese] (alle ohne Handlese)<LineBreak/>
|
<Bold>Handlese</Bold>: Handl[ese], !handl[ese] (alle ohne Handlese)<LineBreak/>
|
||||||
<Bold>Gebunden</Bold>: geb[unden], ungeb[unden], !geb[unden], !ungeb[unden]<LineBreak/>
|
<Bold>Gebunden</Bold>: geb[unden], ungeb[unden], !geb[unden], !ungeb[unden]<LineBreak/>
|
||||||
<Bold>Brutto/Netto Wiegung</Bold>: bto, Brut[to], nto, Net[to], gerebelt, !Gerebelt<LineBreak/>
|
<Bold>Gerebelt</Bold>: gerebelt, !Gerebelt (nicht gerebelt gewogen)<LineBreak/>
|
||||||
<Bold>Freitext</Bold>: z.B. Lieferscheinnummern, Anmerkung, "quw" (sucht nach dem Text "quw")
|
<Bold>Freitext</Bold>: z.B. Lieferscheinnummern, Anmerkung, "quw" (sucht nach dem Text "quw")
|
||||||
</TextBlock>
|
</TextBlock>
|
||||||
</TextBox.ToolTip>
|
</TextBox.ToolTip>
|
||||||
</TextBox>
|
</TextBox>
|
||||||
<ctrl:IntegerUpDown x:Name="SeasonInput" Grid.ColumnSpan="3" Height="25" Width="56" FontSize="14" Minimum="1900" Maximum="9999"
|
<ctrl:IntegerUpDown x:Name="SeasonInput" Text="{Binding FilterSeasonString, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"
|
||||||
Margin="0,10,100,0" VerticalAlignment="Top" HorizontalAlignment="Right" Text="2020"
|
Grid.ColumnSpan="3" Height="25" Width="56" FontSize="14" Minimum="1900" Maximum="9999"
|
||||||
|
Margin="0,10,95,0" VerticalAlignment="Top" HorizontalAlignment="Right"
|
||||||
TextChanged="SeasonInput_TextChanged"/>
|
TextChanged="SeasonInput_TextChanged"/>
|
||||||
<CheckBox x:Name="TodayOnlyInput" Content="Nur heute"
|
<CheckBox x:Name="TodayOnlyInput" Content="Nur heute" IsChecked="{Binding FilterTodayOnly, Mode=TwoWay}"
|
||||||
HorizontalAlignment="Right" Margin="0,7,18,0" VerticalAlignment="Top" Grid.Column="1" Grid.ColumnSpan="2"
|
HorizontalAlignment="Right" Margin="0,7,18,0" VerticalAlignment="Top" Grid.Column="1" Grid.ColumnSpan="2"
|
||||||
Checked="TodayOnlyInput_Changed" Unchecked="TodayOnlyInput_Changed"/>
|
Checked="TodayOnlyInput_Changed" Unchecked="TodayOnlyInput_Changed"/>
|
||||||
<CheckBox x:Name="AllSeasonsInput" Content="Jede Saison" IsEnabled="False"
|
<CheckBox x:Name="AllSeasonsInput" Content="Jede Saison" IsEnabled="{Binding EnableAllSeasons, Mode=TwoWay}" IsChecked="{Binding FilterAllSeasons, Mode=TwoWay}"
|
||||||
HorizontalAlignment="Right" Margin="0,24,10,0" VerticalAlignment="Top" Grid.Column="1" Grid.ColumnSpan="2"
|
HorizontalAlignment="Right" Margin="0,24,10,0" VerticalAlignment="Top" Grid.Column="1" Grid.ColumnSpan="2"
|
||||||
Checked="AllSeasonsInput_Changed" Unchecked="AllSeasonsInput_Changed"/>
|
Checked="AllSeasonsInput_Changed" Unchecked="AllSeasonsInput_Changed"/>
|
||||||
<DataGrid x:Name="DeliveryList" AutoGenerateColumns="False" HeadersVisibility="Column" IsReadOnly="True" GridLinesVisibility="None" SelectionMode="Single"
|
<DataGrid x:Name="DeliveryList" AutoGenerateColumns="False" HeadersVisibility="Column" IsReadOnly="True" GridLinesVisibility="None" SelectionMode="Single"
|
||||||
|
ItemsSource="{Binding Deliveries, Mode=TwoWay}" SelectedItem="{Binding SelectedDelivery, Mode=TwoWay}"
|
||||||
SelectionChanged="DeliveryList_SelectionChanged"
|
SelectionChanged="DeliveryList_SelectionChanged"
|
||||||
CanUserDeleteRows="False" CanUserResizeRows="False" CanUserAddRows="False"
|
CanUserDeleteRows="False" CanUserResizeRows="False" CanUserAddRows="False"
|
||||||
Margin="5,0,5,0" Grid.Row="1" FontSize="14" Grid.ColumnSpan="3">
|
Margin="5,0,5,0" Grid.Row="1" FontSize="14" Grid.ColumnSpan="3">
|
||||||
@ -325,9 +337,11 @@
|
|||||||
</Grid.ColumnDefinitions>
|
</Grid.ColumnDefinitions>
|
||||||
|
|
||||||
<Label Content="Mitglied:" Margin="10,10,0,0" Grid.Column="0"/>
|
<Label Content="Mitglied:" Margin="10,10,0,0" Grid.Column="0"/>
|
||||||
<TextBox x:Name="MgNrInput" Width="48" Grid.Row="1" Grid.Column="1" Margin="0,10,0,0" HorizontalAlignment="Left" TextAlignment="Right"
|
<TextBox x:Name="MgNrInput" Text="{Binding MgNrString, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"
|
||||||
|
Width="48" Grid.Row="1" Grid.Column="1" Margin="0,10,0,0" HorizontalAlignment="Left" TextAlignment="Right"
|
||||||
TextChanged="MgNrInput_TextChanged" LostFocus="MgNrInput_LostFocus" KeyUp="Input_KeyUp"/>
|
TextChanged="MgNrInput_TextChanged" LostFocus="MgNrInput_LostFocus" KeyUp="Input_KeyUp"/>
|
||||||
<ComboBox x:Name="MemberInput" Grid.Column="1" Margin="53,10,40,10" IsEditable="True"
|
<ComboBox x:Name="MemberInput" SelectedItem="{Binding Member, Mode=TwoWay}" ItemsSource="{Binding MemberSource, Mode=TwoWay}"
|
||||||
|
Grid.Column="1" Margin="53,10,40,10" IsEditable="True"
|
||||||
ItemTemplate="{StaticResource MemberAdminNameTemplate}" TextSearch.TextPath="AdministrativeName"
|
ItemTemplate="{StaticResource MemberAdminNameTemplate}" TextSearch.TextPath="AdministrativeName"
|
||||||
SelectionChanged="MemberInput_SelectionChanged" KeyUp="Input_KeyUp"/>
|
SelectionChanged="MemberInput_SelectionChanged" KeyUp="Input_KeyUp"/>
|
||||||
<Button x:Name="MemberReferenceButton" Grid.Column="1" Height="25" Width="25" FontFamily="Segoe MDL2 Assets" Content="" Padding="0,0,0,0"
|
<Button x:Name="MemberReferenceButton" Grid.Column="1" Height="25" Width="25" FontFamily="Segoe MDL2 Assets" Content="" Padding="0,0,0,0"
|
||||||
@ -335,7 +349,8 @@
|
|||||||
Click="MemberReferenceButton_Click"/>
|
Click="MemberReferenceButton_Click"/>
|
||||||
|
|
||||||
<Label Content="Wohnort:" Margin="10,38,0,0" Grid.Column="0"/>
|
<Label Content="Wohnort:" Margin="10,38,0,0" Grid.Column="0"/>
|
||||||
<TextBox x:Name="MemberAddressField" Grid.Column="1" Margin="0,40,10,10" FontSize="12" Height="22"
|
<TextBox x:Name="MemberAddressField" Text="{Binding MemberAddress}"
|
||||||
|
Grid.Column="1" Margin="0,40,10,10" FontSize="12" Height="22"
|
||||||
IsReadOnly="True" IsTabStop="False"/>
|
IsReadOnly="True" IsTabStop="False"/>
|
||||||
</Grid>
|
</Grid>
|
||||||
</GroupBox>
|
</GroupBox>
|
||||||
@ -348,26 +363,31 @@
|
|||||||
</Grid.ColumnDefinitions>
|
</Grid.ColumnDefinitions>
|
||||||
|
|
||||||
<Label Content="LieferscheinNr.:" Margin="10,10,0,0" Grid.Column="0"/>
|
<Label Content="LieferscheinNr.:" Margin="10,10,0,0" Grid.Column="0"/>
|
||||||
<TextBox x:Name="LsNrInput" Width="126" Grid.Column="1" HorizontalAlignment="Left" Margin="0,10,0,0"
|
<TextBox x:Name="LsNrInput" Text="{Binding LsNr, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"
|
||||||
|
Width="126" Grid.Column="1" HorizontalAlignment="Left" Margin="0,10,0,0"
|
||||||
IsReadOnly="True" IsTabStop="False"
|
IsReadOnly="True" IsTabStop="False"
|
||||||
TextChanged="TextBox_TextChanged"/>
|
TextChanged="TextBox_TextChanged"/>
|
||||||
|
|
||||||
<Label Content="Datum/Uhrzeit:" Margin="10,40,0,0" Grid.Column="0"/>
|
<Label Content="Datum/Uhrzeit:" Margin="10,40,0,0" Grid.Column="0"/>
|
||||||
<TextBox x:Name="DateInput" Width="77" Grid.Column="1" HorizontalAlignment="Left" Margin="0,40,0,0"
|
<TextBox x:Name="DateInput" Text="{Binding Date, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"
|
||||||
|
Width="77" Grid.Column="1" HorizontalAlignment="Left" Margin="0,40,0,0"
|
||||||
IsReadOnly="True"
|
IsReadOnly="True"
|
||||||
TextChanged="DateInput_TextChanged" LostFocus="DateInput_LostFocus"/>
|
TextChanged="DateInput_TextChanged" LostFocus="DateInput_LostFocus"/>
|
||||||
<TextBox x:Name="TimeInput" Width="44" Grid.Column="1" HorizontalAlignment="Left" Margin="82,40,0,0"
|
<TextBox x:Name="TimeInput" Text="{Binding Time, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"
|
||||||
|
Width="44" Grid.Column="1" HorizontalAlignment="Left" Margin="82,40,0,0"
|
||||||
IsReadOnly="True"
|
IsReadOnly="True"
|
||||||
TextChanged="TimeInput_TextChanged" LostFocus="TimeInput_LostFocus"/>
|
TextChanged="TimeInput_TextChanged" LostFocus="TimeInput_LostFocus"/>
|
||||||
|
|
||||||
<Label Content="Zweigstelle:" Margin="10,70,0,0" Grid.Column="0"/>
|
<Label Content="Zweigstelle:" Margin="10,70,0,0" Grid.Column="0"/>
|
||||||
<ComboBox x:Name="BranchInput" Width="126" Margin="0,70,10,0" Grid.Column="1" HorizontalAlignment="Left"
|
<ComboBox x:Name="BranchInput" SelectedItem="{Binding Branch, Mode=TwoWay}" ItemsSource="{Binding BranchSource, Mode=TwoWay}"
|
||||||
|
Width="126" Margin="0,70,10,0" Grid.Column="1" HorizontalAlignment="Left"
|
||||||
IsEnabled="False"
|
IsEnabled="False"
|
||||||
SelectionChanged="BranchInput_SelectionChanged"
|
SelectionChanged="BranchInput_SelectionChanged"
|
||||||
DisplayMemberPath="Name" TextSearch.TextPath="Name"/>
|
DisplayMemberPath="Name" TextSearch.TextPath="Name"/>
|
||||||
|
|
||||||
<Label Content="Anmerkung:" Margin="10,100,0,10"/>
|
<Label Content="Anmerkung:" Margin="10,100,0,10"/>
|
||||||
<TextBox x:Name="CommentInput" Grid.Column="1" Margin="0,100,10,10"
|
<TextBox x:Name="CommentInput" Text="{Binding Comment, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"
|
||||||
|
Grid.Column="1" Margin="0,100,10,10"
|
||||||
TextChanged="TextBox_TextChanged"/>
|
TextChanged="TextBox_TextChanged"/>
|
||||||
</Grid>
|
</Grid>
|
||||||
</GroupBox>
|
</GroupBox>
|
||||||
@ -381,9 +401,11 @@
|
|||||||
</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" Width="36" Grid.Row="1" Grid.Column="1" Margin="0,10,0,0" HorizontalAlignment="Left"
|
<TextBox x:Name="SortIdInput" Text="{Binding SortId, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"
|
||||||
|
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" Grid.Row="1" Grid.Column="1" Grid.ColumnSpan="2" Margin="41,10,10,10"
|
<ComboBox x:Name="WineVarietyInput" SelectedItem="{Binding WineVar, Mode=TwoWay}" ItemsSource="{Binding WineVarSource, Mode=TwoWay}"
|
||||||
|
Grid.Row="1" Grid.Column="1" Grid.ColumnSpan="2" Margin="41,10,10,10"
|
||||||
TextSearch.TextPath="Name"
|
TextSearch.TextPath="Name"
|
||||||
SelectionChanged="WineVarietyInput_SelectionChanged" KeyUp="Input_KeyUp">
|
SelectionChanged="WineVarietyInput_SelectionChanged" KeyUp="Input_KeyUp">
|
||||||
<ComboBox.ItemTemplateSelector>
|
<ComboBox.ItemTemplateSelector>
|
||||||
@ -392,12 +414,14 @@
|
|||||||
</ComboBox>
|
</ComboBox>
|
||||||
|
|
||||||
<Label Content="Attr./Bewirt.:" Margin="10,40,0,0" Grid.Column="0"/>
|
<Label Content="Attr./Bewirt.:" Margin="10,40,0,0" Grid.Column="0"/>
|
||||||
<ComboBox x:Name="AttributeInput" Grid.Row="1" Grid.Column="1" Margin="0,40,5,10"
|
<ComboBox x:Name="AttributeInput" SelectedItem="{Binding WineAttrObj, Mode=TwoWay}" ItemsSource="{Binding WineAttrSource, Mode=TwoWay}"
|
||||||
|
Grid.Row="1" Grid.Column="1" Margin="0,40,5,10"
|
||||||
DisplayMemberPath="Name"
|
DisplayMemberPath="Name"
|
||||||
SelectionChanged="AttributeInput_SelectionChanged" KeyUp="Input_KeyUp"/>
|
KeyUp="Input_KeyUp"/>
|
||||||
<ComboBox x:Name="CultivationInput" Grid.Row="1" Grid.Column="2" Margin="0,40,10,10"
|
<ComboBox x:Name="CultivationInput" SelectedItem="{Binding WineCultObj, Mode=TwoWay}" ItemsSource="{Binding WineCultSource, Mode=TwoWay}"
|
||||||
|
Grid.Row="1" Grid.Column="2" Margin="0,40,10,10"
|
||||||
DisplayMemberPath="Name"
|
DisplayMemberPath="Name"
|
||||||
SelectionChanged="CultivationInput_SelectionChanged" KeyUp="Input_KeyUp"/>
|
KeyUp="Input_KeyUp"/>
|
||||||
</Grid>
|
</Grid>
|
||||||
</GroupBox>
|
</GroupBox>
|
||||||
|
|
||||||
@ -408,15 +432,18 @@
|
|||||||
<ColumnDefinition/>
|
<ColumnDefinition/>
|
||||||
</Grid.ColumnDefinitions>
|
</Grid.ColumnDefinitions>
|
||||||
<Label Content="Gradation:" Margin="10,10,10,10"/>
|
<Label Content="Gradation:" Margin="10,10,10,10"/>
|
||||||
<ctrl:UnitTextBox x:Name="GradationOeInput" Unit="°Oe" TextChanged="GradationOeInput_TextChanged" KeyUp="Input_KeyUp"
|
<ctrl:UnitTextBox x:Name="GradationOeInput" Unit="°Oe" Text="{Binding GradationOeString, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"
|
||||||
|
TextChanged="GradationOeInput_TextChanged" KeyUp="Input_KeyUp"
|
||||||
Grid.Column="1" Width="54" Margin="0,10,10,10" HorizontalAlignment="Left" VerticalAlignment="Top"/>
|
Grid.Column="1" Width="54" Margin="0,10,10,10" HorizontalAlignment="Left" VerticalAlignment="Top"/>
|
||||||
|
|
||||||
<Label Content="=" Margin="60,10,10,10" Grid.Column="1"/>
|
<Label Content="=" Margin="60,10,10,10" Grid.Column="1"/>
|
||||||
<ctrl:UnitTextBox x:Name="GradationKmwInput" Unit="°KMW" TextChanged="GradationKmwInput_TextChanged" KeyUp="Input_KeyUp"
|
<ctrl:UnitTextBox x:Name="GradationKmwInput" Unit="°KMW" Text="{Binding GradationKmwString, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"
|
||||||
|
TextChanged="GradationKmwInput_TextChanged" KeyUp="Input_KeyUp"
|
||||||
Grid.Column="1" Width="68" Margin="78,10,10,10" HorizontalAlignment="Left" VerticalAlignment="Top"/>
|
Grid.Column="1" Width="68" Margin="78,10,10,10" HorizontalAlignment="Left" VerticalAlignment="Top"/>
|
||||||
|
|
||||||
<Label Content="Qualitätsstufe:" Margin="10,40,10,10"/>
|
<Label Content="Qualitätsstufe:" Margin="10,40,10,10"/>
|
||||||
<ComboBox x:Name="WineQualityLevelInput" Width="146" Margin="0,40,10,10" Grid.Column="1" HorizontalAlignment="Left"
|
<ComboBox x:Name="WineQualityLevelInput" SelectedItem="{Binding WineQualityLevel, Mode=TwoWay}" ItemsSource="{Binding WineQualityLevelSource, Mode=TwoWay}"
|
||||||
|
Width="146" Margin="0,40,10,10" Grid.Column="1" HorizontalAlignment="Left"
|
||||||
TextSearch.TextPath="Name"
|
TextSearch.TextPath="Name"
|
||||||
SelectionChanged="WineQualityLevelInput_SelectionChanged" KeyUp="Input_KeyUp">
|
SelectionChanged="WineQualityLevelInput_SelectionChanged" KeyUp="Input_KeyUp">
|
||||||
<ComboBox.ItemTemplateSelector>
|
<ComboBox.ItemTemplateSelector>
|
||||||
@ -424,7 +451,8 @@
|
|||||||
</ComboBox.ItemTemplateSelector>
|
</ComboBox.ItemTemplateSelector>
|
||||||
</ComboBox>
|
</ComboBox>
|
||||||
|
|
||||||
<CheckBox x:Name="AbgewertetInput" Content="Abgewertet" IsEnabled="False"
|
<CheckBox x:Name="AbgewertetInput" IsChecked="{Binding Abgewertet, Mode=TwoWay}"
|
||||||
|
Content="Abgewertet" IsEnabled="False"
|
||||||
VerticalAlignment="Top" HorizontalAlignment="Left" Margin="10,75,10,10" Grid.Column="0" Grid.ColumnSpan="2"/>
|
VerticalAlignment="Top" HorizontalAlignment="Left" Margin="10,75,10,10" Grid.Column="0" Grid.ColumnSpan="2"/>
|
||||||
</Grid>
|
</Grid>
|
||||||
</GroupBox>
|
</GroupBox>
|
||||||
@ -437,16 +465,19 @@
|
|||||||
</Grid.ColumnDefinitions>
|
</Grid.ColumnDefinitions>
|
||||||
|
|
||||||
<Label Content="Gewicht:" Margin="10,10,10,10"/>
|
<Label Content="Gewicht:" Margin="10,10,10,10"/>
|
||||||
<ctrl:UnitTextBox x:Name="WeightInput" Unit="kg" TextChanged="WeightInput_TextChanged"
|
<ctrl:UnitTextBox x:Name="WeightInput" Unit="kg" Text="{Binding WeightString, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"
|
||||||
|
TextChanged="WeightInput_TextChanged"
|
||||||
Grid.Column="1" Width="70" Margin="0,10,10,10" HorizontalAlignment="Left" VerticalAlignment="Top"/>
|
Grid.Column="1" Width="70" Margin="0,10,10,10" HorizontalAlignment="Left" VerticalAlignment="Top"/>
|
||||||
|
|
||||||
<CheckBox x:Name="ManualWeighingInput" Content="Handwiegung" IsEnabled="False"
|
<CheckBox x:Name="ManualWeighingInput" IsChecked="{Binding IsManualWeighing, Mode=TwoWay}"
|
||||||
|
Content="Handwiegung" IsEnabled="False"
|
||||||
VerticalAlignment="Top" HorizontalAlignment="Left" Margin="10,45,10,10" Grid.Column="0" Grid.ColumnSpan="2"
|
VerticalAlignment="Top" HorizontalAlignment="Left" Margin="10,45,10,10" Grid.Column="0" Grid.ColumnSpan="2"
|
||||||
Checked="CheckBox_Changed" Unchecked="CheckBox_Changed"/>
|
Checked="CheckBox_Changed" Unchecked="CheckBox_Changed"/>
|
||||||
|
|
||||||
<CheckBox x:Name="GerebeltGewogenInput" Content="Netto (gerebelt gewogen)"
|
<CheckBox x:Name="GerebeltGewogenInput" IsChecked="{Binding IsNetWeightValue, Mode=TwoWay}"
|
||||||
|
Content="Gerebelt gewogen" IsThreeState="True"
|
||||||
VerticalAlignment="Top" HorizontalAlignment="Left" Margin="10,75,10,10" Grid.Column="0" Grid.ColumnSpan="2"
|
VerticalAlignment="Top" HorizontalAlignment="Left" Margin="10,75,10,10" Grid.Column="0" Grid.ColumnSpan="2"
|
||||||
Checked="GerebeltGewogenInput_Changed" Unchecked="GerebeltGewogenInput_Changed"/>
|
Checked="GerebeltGewogenInput_Changed" Unchecked="GerebeltGewogenInput_Changed" Indeterminate="GerebeltGewogenInput_Changed"/>
|
||||||
|
|
||||||
<Button x:Name="WeighingAButton" Content="Wiegen A" Width="120"
|
<Button x:Name="WeighingAButton" Content="Wiegen A" Width="120"
|
||||||
Click="WeighingButton_Click"
|
Click="WeighingButton_Click"
|
||||||
@ -475,30 +506,34 @@
|
|||||||
</Grid.ColumnDefinitions>
|
</Grid.ColumnDefinitions>
|
||||||
|
|
||||||
<Label Content="Zu-/Abschläge:" Margin="10,10,0,10"/>
|
<Label Content="Zu-/Abschläge:" Margin="10,10,0,10"/>
|
||||||
<ctrl:CheckComboBox x:Name="ModifiersInput" Margin="0,10,10,10" Grid.Column="1" Grid.ColumnSpan="2"
|
<ctrl:CheckComboBox x:Name="ModifiersInput" SelectedItems="{Binding Modifiers}" ItemsSource="{Binding ModifiersSource, Mode=TwoWay}"
|
||||||
|
Margin="0,10,10,10" Grid.Column="1" Grid.ColumnSpan="2"
|
||||||
ItemTemplate="{StaticResource ModifierTemplate}" Delimiter=", " AllItemsSelectedContent="Alle"
|
ItemTemplate="{StaticResource ModifierTemplate}" Delimiter=", " AllItemsSelectedContent="Alle"
|
||||||
SelectionChanged="ModifiersInput_SelectionChanged"/>
|
SelectionChanged="ModifiersInput_SelectionChanged"/>
|
||||||
|
|
||||||
<Label Content="Anmerkung:" Margin="10,40,0,10"/>
|
<Label Content="Anmerkung:" Margin="10,40,0,10"/>
|
||||||
<TextBox x:Name="PartCommentInput" Grid.Column="1" Margin="0,40,10,10" Grid.ColumnSpan="2"
|
<TextBox x:Name="PartCommentInput" Text="{Binding PartComment, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"
|
||||||
|
Grid.Column="1" Margin="0,40,10,10" Grid.ColumnSpan="2"
|
||||||
TextChanged="TextBox_TextChanged"/>
|
TextChanged="TextBox_TextChanged"/>
|
||||||
|
|
||||||
<Label Content="Temperatur:" Margin="10,70,0,10"/>
|
<Label Content="Temperatur:" Margin="10,70,0,10"/>
|
||||||
<ctrl:UnitTextBox x:Name="TemperatureInput" Unit="°C"
|
<ctrl:UnitTextBox x:Name="TemperatureInput" Unit="°C" Text="{Binding TemperatureString, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"
|
||||||
TextChanged="TemperatureAcidInput_TextChanged" LostFocus="TemperatureAcidInput_LostFocus"
|
TextChanged="TemperatureAcidInput_TextChanged" LostFocus="TemperatureAcidInput_LostFocus"
|
||||||
Grid.Column="1" Margin="0,70,10,10" VerticalAlignment="Top"/>
|
Grid.Column="1" Margin="0,70,10,10" VerticalAlignment="Top"/>
|
||||||
|
|
||||||
<Label Content="Säure:" Margin="10,100,0,10"/>
|
<Label Content="Säure:" Margin="10,100,0,10"/>
|
||||||
<ctrl:UnitTextBox x:Name="AcidInput" Unit="g/l"
|
<ctrl:UnitTextBox x:Name="AcidInput" Unit="g/l" Text="{Binding AcidString, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"
|
||||||
TextChanged="TemperatureAcidInput_TextChanged" LostFocus="TemperatureAcidInput_LostFocus"
|
TextChanged="TemperatureAcidInput_TextChanged" LostFocus="TemperatureAcidInput_LostFocus"
|
||||||
Grid.Column="1" Margin="0,100,10,10" VerticalAlignment="Top"/>
|
Grid.Column="1" Margin="0,100,10,10" VerticalAlignment="Top"/>
|
||||||
|
|
||||||
<CheckBox x:Name="LesewagenInput" Content="Lesewagen" Margin="10,75,0,0" Grid.Column="2"
|
<CheckBox x:Name="LesewagenInput" IsChecked="{Binding IsLesewagen, Mode=TwoWay}"
|
||||||
|
Content="Lesewagen" Margin="10,75,0,0" Grid.Column="2"
|
||||||
VerticalAlignment="Top" HorizontalAlignment="Left"
|
VerticalAlignment="Top" HorizontalAlignment="Left"
|
||||||
Checked="LesewagenInput_Changed" Unchecked="LesewagenInput_Changed" Click="HandPickedInput_Changed"/>
|
Checked="LesewagenInput_Changed" Unchecked="LesewagenInput_Changed"/>
|
||||||
<CheckBox x:Name="HandPickedInput" Content="Handlese" Margin="10,105,0,0" Grid.Column="2" IsThreeState="True"
|
<CheckBox x:Name="HandPickedInput" IsChecked="{Binding IsHandPicked, Mode=TwoWay}"
|
||||||
|
Content="Handlese" Margin="10,105,0,0" Grid.Column="2" IsThreeState="True"
|
||||||
VerticalAlignment="Top" HorizontalAlignment="Left"
|
VerticalAlignment="Top" HorizontalAlignment="Left"
|
||||||
Checked="HandPickedInput_Changed" Unchecked="HandPickedInput_Changed" Click="HandPickedInput_Changed"/>
|
Checked="HandPickedInput_Changed" Unchecked="HandPickedInput_Changed" Indeterminate="HandPickedInput_Changed"/>
|
||||||
</Grid>
|
</Grid>
|
||||||
</GroupBox>
|
</GroupBox>
|
||||||
|
|
||||||
@ -543,7 +578,8 @@
|
|||||||
</Grid.ColumnDefinitions>
|
</Grid.ColumnDefinitions>
|
||||||
|
|
||||||
<Label Content="Weinbaugebiet:" Margin="10,10,0,10" Grid.Column="0"/>
|
<Label Content="Weinbaugebiet:" Margin="10,10,0,10" Grid.Column="0"/>
|
||||||
<ComboBox x:Name="WineOriginInput" Margin="0,10,10,10" Grid.Column="1"
|
<ComboBox x:Name="WineOriginInput" SelectedItem="{Binding WineOrigin, Mode=TwoWay}" ItemsSource="{Binding WineOriginSource, Mode=TwoWay}"
|
||||||
|
Margin="0,10,10,10" Grid.Column="1"
|
||||||
TextSearch.TextPath="Name">
|
TextSearch.TextPath="Name">
|
||||||
<ComboBox.ItemTemplateSelector>
|
<ComboBox.ItemTemplateSelector>
|
||||||
<ctrl:WineOriginTemplateSelector/>
|
<ctrl:WineOriginTemplateSelector/>
|
||||||
@ -551,17 +587,20 @@
|
|||||||
</ComboBox>
|
</ComboBox>
|
||||||
|
|
||||||
<Label Content="Weinbau-KG:" Margin="10,40,0,10" Grid.Column="0"/>
|
<Label Content="Weinbau-KG:" Margin="10,40,0,10" Grid.Column="0"/>
|
||||||
<ComboBox x:Name="WineKgInput" Margin="0,40,10,10" Grid.Column="1"
|
<ComboBox x:Name="WineKgInput" SelectedItem="{Binding WineKgObj, Mode=TwoWay}" ItemsSource="{Binding WineKgSource, Mode=TwoWay}"
|
||||||
|
Margin="0,40,10,10" Grid.Column="1"
|
||||||
DisplayMemberPath="Name"
|
DisplayMemberPath="Name"
|
||||||
SelectionChanged="WineKgInput_SelectionChanged"/>
|
SelectionChanged="WineKgInput_SelectionChanged"/>
|
||||||
|
|
||||||
<Label Content="Ried:" Margin="10,70,0,10" Grid.Column="0"/>
|
<Label Content="Ried:" Margin="10,70,0,10" Grid.Column="0"/>
|
||||||
<ComboBox x:Name="WineRdInput" Margin="0,70,10,10" Grid.Column="1"
|
<ComboBox x:Name="WineRdInput" SelectedItem="{Binding WineRdObj, Mode=TwoWay}" ItemsSource="{Binding WineRdSource, Mode=TwoWay}"
|
||||||
|
Margin="0,70,10,10" Grid.Column="1"
|
||||||
DisplayMemberPath="Name"/>
|
DisplayMemberPath="Name"/>
|
||||||
|
|
||||||
<CheckBox x:Name="GebundenInput" Content="Gebunden" Margin="10,105,0,0" Grid.Column="0" Grid.ColumnSpan="2" IsThreeState="True"
|
<CheckBox x:Name="GebundenInput" IsChecked="{Binding IsGebunden, Mode=TwoWay}"
|
||||||
|
Content="Gebunden" Margin="10,105,0,0" Grid.Column="0" Grid.ColumnSpan="2" IsThreeState="True"
|
||||||
VerticalAlignment="Top" HorizontalAlignment="Left"
|
VerticalAlignment="Top" HorizontalAlignment="Left"
|
||||||
Checked="CheckBox_Changed" Unchecked="CheckBox_Changed"/>
|
Checked="CheckBox_Changed" Unchecked="CheckBox_Changed" Indeterminate="CheckBox_Changed"/>
|
||||||
</Grid>
|
</Grid>
|
||||||
</GroupBox>
|
</GroupBox>
|
||||||
</Grid>
|
</Grid>
|
||||||
@ -571,11 +610,11 @@
|
|||||||
<ItemsPanelTemplate>
|
<ItemsPanelTemplate>
|
||||||
<Grid>
|
<Grid>
|
||||||
<Grid.ColumnDefinitions>
|
<Grid.ColumnDefinitions>
|
||||||
<ColumnDefinition Width="2*"/>
|
<ColumnDefinition Width="2*" MaxWidth="250"/>
|
||||||
<ColumnDefinition Width="Auto"/>
|
<ColumnDefinition Width="Auto"/>
|
||||||
<ColumnDefinition Width="150"/>
|
<ColumnDefinition Width="150"/>
|
||||||
<ColumnDefinition Width="Auto"/>
|
<ColumnDefinition Width="Auto"/>
|
||||||
<ColumnDefinition Width="2*"/>
|
<ColumnDefinition Width="2*" MaxWidth="180"/>
|
||||||
<ColumnDefinition Width="Auto"/>
|
<ColumnDefinition Width="Auto"/>
|
||||||
<ColumnDefinition Width="3*"/>
|
<ColumnDefinition Width="3*"/>
|
||||||
<ColumnDefinition Width="Auto"/>
|
<ColumnDefinition Width="Auto"/>
|
||||||
@ -585,46 +624,32 @@
|
|||||||
</ItemsPanelTemplate>
|
</ItemsPanelTemplate>
|
||||||
</StatusBar.ItemsPanel>
|
</StatusBar.ItemsPanel>
|
||||||
<StatusBarItem>
|
<StatusBarItem>
|
||||||
<TextBlock x:Name="StatusMembers" Text="Mitglieder: -"/>
|
<TextBlock ToolTip="{Binding StatusMembers}">
|
||||||
|
Mitglieder: <Run Text="{Binding StatusMembers}"/>
|
||||||
|
</TextBlock>
|
||||||
</StatusBarItem>
|
</StatusBarItem>
|
||||||
<Separator Grid.Column="1"/>
|
<Separator Grid.Column="1"/>
|
||||||
<StatusBarItem Grid.Column="2">
|
<StatusBarItem Grid.Column="2">
|
||||||
<TextBlock x:Name="StatusDeliveries" Text="Lieferungen: -"/>
|
<TextBlock>
|
||||||
|
Lieferungen: <Run Text="{Binding StatusDeliveries}"/>
|
||||||
|
</TextBlock>
|
||||||
</StatusBarItem>
|
</StatusBarItem>
|
||||||
<Separator Grid.Column="3"/>
|
<Separator Grid.Column="3"/>
|
||||||
<StatusBarItem Grid.Column="4">
|
<StatusBarItem Grid.Column="4">
|
||||||
<TextBlock x:Name="StatusVarieties" Text="Sorten: -"/>
|
<TextBlock ToolTip="{Binding StatusVarieties}">
|
||||||
|
Sorten: <Run Text="{Binding StatusVarieties}"/>
|
||||||
|
</TextBlock>
|
||||||
</StatusBarItem>
|
</StatusBarItem>
|
||||||
<Separator Grid.Column="5"/>
|
<Separator Grid.Column="5"/>
|
||||||
<StatusBarItem Grid.Column="6">
|
<StatusBarItem Grid.Column="6">
|
||||||
<TextBlock x:Name="StatusWeight" Text="Gewicht: -">
|
<TextBlock ToolTip="{Binding StatusWeightToolTip}">
|
||||||
<TextBlock.ToolTip>
|
Gewicht: <Run Text="{Binding StatusWeight}"/>
|
||||||
<Grid x:Name="StatusWeightToolTip">
|
|
||||||
<Grid.ColumnDefinitions>
|
|
||||||
<ColumnDefinition Width="10"/>
|
|
||||||
<ColumnDefinition Width="60"/>
|
|
||||||
<ColumnDefinition Width="80"/>
|
|
||||||
<ColumnDefinition Width="50"/>
|
|
||||||
<ColumnDefinition Width="50"/>
|
|
||||||
</Grid.ColumnDefinitions>
|
|
||||||
</Grid>
|
|
||||||
</TextBlock.ToolTip>
|
|
||||||
</TextBlock>
|
</TextBlock>
|
||||||
</StatusBarItem>
|
</StatusBarItem>
|
||||||
<Separator Grid.Column="7"/>
|
<Separator Grid.Column="7"/>
|
||||||
<StatusBarItem Grid.Column="8">
|
<StatusBarItem Grid.Column="8">
|
||||||
<TextBlock x:Name="StatusGradation" Text="Gradation: -">
|
<TextBlock ToolTip="{Binding StatusGradationToolTip}">
|
||||||
<TextBlock.ToolTip>
|
Gradation: <Run Text="{Binding StatusGradation}"/>
|
||||||
<Grid x:Name="StatusGradationToolTip">
|
|
||||||
<Grid.ColumnDefinitions>
|
|
||||||
<ColumnDefinition Width="10"/>
|
|
||||||
<ColumnDefinition Width="60"/>
|
|
||||||
<ColumnDefinition Width="35"/>
|
|
||||||
<ColumnDefinition Width="35"/>
|
|
||||||
<ColumnDefinition Width="35"/>
|
|
||||||
</Grid.ColumnDefinitions>
|
|
||||||
</Grid>
|
|
||||||
</TextBlock.ToolTip>
|
|
||||||
</TextBlock>
|
</TextBlock>
|
||||||
</StatusBarItem>
|
</StatusBarItem>
|
||||||
</StatusBar>
|
</StatusBar>
|
||||||
|
File diff suppressed because it is too large
Load Diff
@ -1,5 +1,6 @@
|
|||||||
<local:ContextWindow
|
<local:ContextWindow
|
||||||
x:Class="Elwig.Windows.MailWindow"
|
x:Class="Elwig.Windows.MailWindow"
|
||||||
|
AutomationProperties.AutomationId="MailWindow"
|
||||||
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"
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
using Elwig.Documents;
|
using Elwig.Documents;
|
||||||
using Elwig.Helpers;
|
using Elwig.Helpers;
|
||||||
using Elwig.Helpers.Billing;
|
using Elwig.Helpers.Billing;
|
||||||
using Elwig.Models.Dtos;
|
using Elwig.Models.Dtos;
|
||||||
@ -103,7 +103,7 @@ namespace Elwig.Windows {
|
|||||||
public MailWindow(int? year = null) {
|
public MailWindow(int? year = null) {
|
||||||
InitializeComponent();
|
InitializeComponent();
|
||||||
using (var ctx = new AppDbContext()) {
|
using (var ctx = new AppDbContext()) {
|
||||||
Year = year ?? ctx.Seasons.OrderBy(s => s.Year).LastOrDefault()!.Year;
|
Year = year ?? ctx.Seasons.OrderBy(s => s.Year).LastOrDefault()?.Year ?? Utils.Today.Year;
|
||||||
Title = $"Rundschreiben - Lese {Year} - Elwig";
|
Title = $"Rundschreiben - Lese {Year} - Elwig";
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -139,7 +139,7 @@ namespace Elwig.Windows {
|
|||||||
AvaiableDocumentsList.ItemsSource = l;
|
AvaiableDocumentsList.ItemsSource = l;
|
||||||
|
|
||||||
ControlUtils.RenewItemsSource(MemberBranchInput, await ctx.Branches
|
ControlUtils.RenewItemsSource(MemberBranchInput, await ctx.Branches
|
||||||
.Where(b => b.Members.Any())
|
.Where(b => b.Members.Count != 0)
|
||||||
.OrderBy(b => b.Name)
|
.OrderBy(b => b.Name)
|
||||||
.ToListAsync(), MemberInput_SelectionChanged);
|
.ToListAsync(), MemberInput_SelectionChanged);
|
||||||
if (MemberBranchInput.SelectedItems.Count == 0) {
|
if (MemberBranchInput.SelectedItems.Count == 0) {
|
||||||
@ -148,7 +148,7 @@ namespace Elwig.Windows {
|
|||||||
MemberBranchInput.SelectionChanged += MemberInput_SelectionChanged;
|
MemberBranchInput.SelectionChanged += MemberInput_SelectionChanged;
|
||||||
}
|
}
|
||||||
ControlUtils.RenewItemsSource(MemberKgInput, await ctx.Katastralgemeinden
|
ControlUtils.RenewItemsSource(MemberKgInput, await ctx.Katastralgemeinden
|
||||||
.Where(k => k.WbKg!.Members.Any())
|
.Where(k => k.WbKg!.Members.Count != 0)
|
||||||
.OrderBy(k => k.Name)
|
.OrderBy(k => k.Name)
|
||||||
.ToListAsync(), MemberInput_SelectionChanged);
|
.ToListAsync(), MemberInput_SelectionChanged);
|
||||||
if (MemberKgInput.SelectedItems.Count == 0) {
|
if (MemberKgInput.SelectedItems.Count == 0) {
|
||||||
@ -272,7 +272,7 @@ namespace Elwig.Windows {
|
|||||||
private void SelectDocumentButton_Click(object sender, RoutedEventArgs evt) {
|
private void SelectDocumentButton_Click(object sender, RoutedEventArgs evt) {
|
||||||
var d = new OpenFileDialog() {
|
var d = new OpenFileDialog() {
|
||||||
Title = "Dokument auswählen - Elwig",
|
Title = "Dokument auswählen - Elwig",
|
||||||
DefaultExt = ".pdf",
|
DefaultExt = "pdf",
|
||||||
Filter = "PDF-Dokument (*.pdf)|*.pdf",
|
Filter = "PDF-Dokument (*.pdf)|*.pdf",
|
||||||
Multiselect = true,
|
Multiselect = true,
|
||||||
};
|
};
|
||||||
@ -561,7 +561,7 @@ namespace Elwig.Windows {
|
|||||||
double totalNum = printNum + emailNum;
|
double totalNum = printNum + emailNum;
|
||||||
|
|
||||||
var email = memberDocs
|
var email = memberDocs
|
||||||
.Where(d => d.Docs.Count > 0 && d.Member.EmailAddresses.Any() && (emailMode == 2 || (emailMode == 1 && d.Member.ContactViaEmail)))
|
.Where(d => d.Member.EmailAddresses.Count > 0 && (emailMode == 2 || (emailMode == 1 && d.Member.ContactViaEmail)))
|
||||||
.ToDictionary(d => d.Member, m => {
|
.ToDictionary(d => d.Member, m => {
|
||||||
var docs = m.Docs.Select(d => d.Doc).ToList();
|
var docs = m.Docs.Select(d => d.Doc).ToList();
|
||||||
foreach (var doc in docs) {
|
foreach (var doc in docs) {
|
||||||
|
@ -19,9 +19,8 @@
|
|||||||
<Grid>
|
<Grid>
|
||||||
<Menu BorderThickness="0,0,0,1" VerticalAlignment="Top" Height="19" BorderBrush="LightGray" Background="White">
|
<Menu BorderThickness="0,0,0,1" VerticalAlignment="Top" Height="19" BorderBrush="LightGray" Background="White">
|
||||||
<MenuItem Header="Datenbank">
|
<MenuItem Header="Datenbank">
|
||||||
<MenuItem Header="Daten exportieren..." Click="Menu_Database_Export_Click"/>
|
<MenuItem Header="Daten exportieren..." Click="Menu_Database_Export_Click" IsEnabled="False"/>
|
||||||
<MenuItem Header="Daten importieren..." Click="Menu_Database_Import_Click"/>
|
<MenuItem Header="Daten importieren..." Click="Menu_Database_Import_Click"/>
|
||||||
<MenuItem x:Name="Menu_Database_Sync" Header="Daten synchronisieren" Click="Menu_Database_Sync_Click"/>
|
|
||||||
<Separator/>
|
<Separator/>
|
||||||
<MenuItem Header="Abfragen stellen" Click="Menu_Database_Query_Click"/>
|
<MenuItem Header="Abfragen stellen" Click="Menu_Database_Query_Click"/>
|
||||||
<MenuItem Header="Speicherort öffnen..." Click="Menu_Database_Open_Click"/>
|
<MenuItem Header="Speicherort öffnen..." Click="Menu_Database_Open_Click"/>
|
||||||
@ -30,7 +29,9 @@
|
|||||||
<MenuItem Header="Über"/>
|
<MenuItem Header="Über"/>
|
||||||
<MenuItem x:Name="Menu_Help_Update" Header="Nach Updates suchen" Click="Menu_Help_Update_Click"/>
|
<MenuItem x:Name="Menu_Help_Update" Header="Nach Updates suchen" Click="Menu_Help_Update_Click"/>
|
||||||
<MenuItem x:Name="Menu_Help_Smtp" Header="E-Mail-Einstellungen testen" Click="Menu_Help_Smtp_Click"/>
|
<MenuItem x:Name="Menu_Help_Smtp" Header="E-Mail-Einstellungen testen" Click="Menu_Help_Smtp_Click"/>
|
||||||
<MenuItem x:Name="Menu_Help_Config" Header="Konfigurationsspeicherort öffnen..." Click="Menu_Help_Config_Click"/>
|
<Separator/>
|
||||||
|
<MenuItem x:Name="Menu_Help_Config" Header="Konfigurationsdatei öffnen..." Click="Menu_Help_Config_Click"/>
|
||||||
|
<MenuItem x:Name="Menu_Help_Directory" Header="Konfigurationsspeicherort öffnen..." Click="Menu_Help_Directory_Click"/>
|
||||||
</MenuItem>
|
</MenuItem>
|
||||||
</Menu>
|
</Menu>
|
||||||
|
|
||||||
@ -66,6 +67,15 @@
|
|||||||
<Button x:Name="RegistrationButton" Content="Anmeldungen" IsEnabled="False"
|
<Button x:Name="RegistrationButton" Content="Anmeldungen" IsEnabled="False"
|
||||||
Margin="205,250,0,0"/>
|
Margin="205,250,0,0"/>
|
||||||
|
|
||||||
|
<Button x:Name="DownloadButton" Click="DownloadButton_Click"
|
||||||
|
Margin="310,135,0,0" Padding="1.5,0,0,0" Height="30" Width="30"
|
||||||
|
Content="" FontFamily="Segoe MDL2 Assets" FontSize="16"
|
||||||
|
ToolTip="Lieferungen und Mitgliederdaten anderer Zweigstellen herunterladen"/>
|
||||||
|
<Button x:Name="UploadButton" Click="UploadButton_Click"
|
||||||
|
Margin="375,135,0,0" Padding="1.5,0,0,0" Height="30" Width="30"
|
||||||
|
Content="" FontFamily="Segoe MDL2 Assets" FontSize="16"
|
||||||
|
ToolTip="Lieferungen dieser Zweigstelle hochladen"/>
|
||||||
|
|
||||||
<Expander x:Name="SeasonFinish" Header="Leseabschluss" SnapsToDevicePixels="True"
|
<Expander x:Name="SeasonFinish" Header="Leseabschluss" SnapsToDevicePixels="True"
|
||||||
Expanded="SeasonFinish_Expanded" Collapsed="SeasonFinish_Collapsed"
|
Expanded="SeasonFinish_Expanded" Collapsed="SeasonFinish_Collapsed"
|
||||||
HorizontalAlignment="Center" Width="407" Margin="0,290,0,0" VerticalAlignment="Top">
|
HorizontalAlignment="Center" Width="407" Margin="0,290,0,0" VerticalAlignment="Top">
|
||||||
|
@ -11,7 +11,9 @@ using System.Diagnostics;
|
|||||||
using System.Globalization;
|
using System.Globalization;
|
||||||
using System.IO;
|
using System.IO;
|
||||||
using System.Linq;
|
using System.Linq;
|
||||||
|
using System.Net.Http;
|
||||||
using System.Reflection;
|
using System.Reflection;
|
||||||
|
using System.Threading;
|
||||||
using System.Threading.Tasks;
|
using System.Threading.Tasks;
|
||||||
using System.Windows;
|
using System.Windows;
|
||||||
using System.Windows.Controls;
|
using System.Windows.Controls;
|
||||||
@ -27,7 +29,8 @@ namespace Elwig.Windows {
|
|||||||
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;
|
||||||
Menu_Database_Sync.IsEnabled = App.Config.SyncUrl != null;
|
DownloadButton.Visibility = App.Config.SyncUrl != null ? Visibility.Visible : Visibility.Hidden;
|
||||||
|
UploadButton.Visibility = App.Config.SyncUrl != null ? Visibility.Visible : Visibility.Hidden;
|
||||||
}
|
}
|
||||||
|
|
||||||
private void Window_Loaded(object sender, RoutedEventArgs evt) {
|
private void Window_Loaded(object sender, RoutedEventArgs evt) {
|
||||||
@ -35,13 +38,21 @@ namespace Elwig.Windows {
|
|||||||
}
|
}
|
||||||
|
|
||||||
private void Window_Closing(object sender, CancelEventArgs evt) {
|
private void Window_Closing(object sender, CancelEventArgs evt) {
|
||||||
if (App.NumWindows > 1 && !App.ForceShutdown && !App.Current.Windows.Cast<Window>().Any(w => ((w as AdministrationWindow)?.IsEditing ?? false) || ((w as AdministrationWindow)?.IsCreating ?? false))) {
|
if (App.NumWindows > 1 && !App.ForceShutdown) {
|
||||||
var res = MessageBox.Show("Es sind noch weitere Fenster geöffnet.\nSollen alle Fenster geschlossen werden?",
|
foreach (var w in App.Current.Windows.Cast<Window>().Where(w => ((w as AdministrationWindow)?.IsEditing ?? false) || ((w as AdministrationWindow)?.IsCreating ?? false))) {
|
||||||
"Elwig beenden", MessageBoxButton.YesNo, MessageBoxImage.Warning, MessageBoxResult.No);
|
try {
|
||||||
if (res != MessageBoxResult.Yes) {
|
w.Close();
|
||||||
evt.Cancel = true;
|
} catch { }
|
||||||
} else {
|
}
|
||||||
Application.Current.Shutdown();
|
Thread.Sleep(100);
|
||||||
|
if (App.NumWindows > 1 && !App.Current.Windows.Cast<Window>().Any(w => ((w as AdministrationWindow)?.IsEditing ?? false) || ((w as AdministrationWindow)?.IsCreating ?? false))) {
|
||||||
|
var res = MessageBox.Show("Es sind noch weitere Fenster geöffnet.\nSollen alle Fenster geschlossen werden?",
|
||||||
|
"Elwig beenden", MessageBoxButton.YesNo, MessageBoxImage.Warning, MessageBoxResult.No);
|
||||||
|
if (res != MessageBoxResult.Yes) {
|
||||||
|
evt.Cancel = true;
|
||||||
|
} else {
|
||||||
|
Application.Current.Shutdown();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -62,8 +73,21 @@ namespace Elwig.Windows {
|
|||||||
Mouse.OverrideCursor = null;
|
Mouse.OverrideCursor = null;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private void Menu_Help_Directory_Click(object sender, RoutedEventArgs evt) {
|
||||||
|
try {
|
||||||
|
Process.Start("explorer.exe", App.DataPath);
|
||||||
|
} catch { }
|
||||||
|
}
|
||||||
|
|
||||||
private void Menu_Help_Config_Click(object sender, RoutedEventArgs evt) {
|
private void Menu_Help_Config_Click(object sender, RoutedEventArgs evt) {
|
||||||
Process.Start("explorer.exe", App.DataPath);
|
try {
|
||||||
|
Process.Start(new ProcessStartInfo {
|
||||||
|
FileName = "notepad.exe",
|
||||||
|
Arguments = App.ConfigPath,
|
||||||
|
Verb = "runas",
|
||||||
|
UseShellExecute = true,
|
||||||
|
});
|
||||||
|
} catch { }
|
||||||
}
|
}
|
||||||
|
|
||||||
private void Menu_Database_Query_Click(object sender, RoutedEventArgs evt) {
|
private void Menu_Database_Query_Click(object sender, RoutedEventArgs evt) {
|
||||||
@ -80,11 +104,25 @@ namespace Elwig.Windows {
|
|||||||
// TODO Menu_Database_Export_Click
|
// TODO Menu_Database_Export_Click
|
||||||
}
|
}
|
||||||
|
|
||||||
private void Menu_Database_Import_Click(object sender, RoutedEventArgs evt) {
|
private async void Menu_Database_Import_Click(object sender, RoutedEventArgs evt) {
|
||||||
// TODO Menu_Database_Import_Click
|
try {
|
||||||
|
var d = new OpenFileDialog() {
|
||||||
|
Title = "Export-Datei auswählen - Elwig",
|
||||||
|
DefaultExt = "elwig.zip",
|
||||||
|
Filter = "Elwig-Export-Datei (*.elwig.zip)|*.elwig.zip",
|
||||||
|
Multiselect = true,
|
||||||
|
};
|
||||||
|
if (d.ShowDialog() == true) {
|
||||||
|
Mouse.OverrideCursor = Cursors.AppStarting;
|
||||||
|
await ElwigData.Import(d.FileNames, ElwigData.ImportMode.Interactively);
|
||||||
|
}
|
||||||
|
} catch (Exception exc) {
|
||||||
|
MessageBox.Show(exc.Message, "Fehler", MessageBoxButton.OK, MessageBoxImage.Error);
|
||||||
|
}
|
||||||
|
Mouse.OverrideCursor = null;
|
||||||
}
|
}
|
||||||
|
|
||||||
private async void Menu_Database_Sync_Click(object sender, RoutedEventArgs evt) {
|
private async void DownloadButton_Click(object sender, RoutedEventArgs evt) {
|
||||||
if (App.Config.SyncUrl == null)
|
if (App.Config.SyncUrl == null)
|
||||||
return;
|
return;
|
||||||
Mouse.OverrideCursor = Cursors.AppStarting;
|
Mouse.OverrideCursor = Cursors.AppStarting;
|
||||||
@ -94,20 +132,17 @@ namespace Elwig.Windows {
|
|||||||
.Select(f => new {
|
.Select(f => new {
|
||||||
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!["zwstid"]?.AsValue().GetValue<string>(),
|
ZwstId = f!["meta"]?["zwstid"]?.AsValue().GetValue<string>() ?? f!["zwstid"]?.AsValue().GetValue<string>(),
|
||||||
DeliveryNum = f!["meta"]?["deliveries"]?["count"]!.AsValue().GetValue<int>(),
|
|
||||||
DeliveryPartNum = f!["meta"]?["deliveries"]?["parts"]!.AsValue().GetValue<int>(),
|
|
||||||
Filters = f!["meta"]?["deliveries"]?["filters"]!.AsArray().Select(i => i!.AsValue().GetValue<string>()).ToArray(),
|
|
||||||
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>(),
|
||||||
})
|
})
|
||||||
.Where(f => f.DeliveryNum > 0 && f.Timestamp >= new DateTime(Utils.CurrentLastSeason, 7, 1))
|
.Where(f => f.Timestamp >= new DateTime(Utils.CurrentLastSeason, 7, 1))
|
||||||
.ToList();
|
.ToList();
|
||||||
|
|
||||||
var imported = await ElwigData.GetImportedFiles();
|
var imported = await ElwigData.GetImportedFiles();
|
||||||
var import = files
|
var import = files
|
||||||
.Where(f => f.Filters != null && f.Filters.Length > 0 && f.Device != Environment.MachineName && !imported.Contains(f.Name))
|
.Where(f => f.Device != Environment.MachineName && !imported.Contains(f.Name))
|
||||||
.ToList();
|
.ToList();
|
||||||
var paths = new List<string>();
|
var paths = new List<string>();
|
||||||
using (var client = Utils.GetHttpClient(App.Config.SyncUsername, App.Config.SyncPassword)) {
|
using (var client = Utils.GetHttpClient(App.Config.SyncUsername, App.Config.SyncPassword)) {
|
||||||
@ -118,13 +153,52 @@ namespace Elwig.Windows {
|
|||||||
paths.Add(filename);
|
paths.Add(filename);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
await ElwigData.Import(paths, false);
|
await ElwigData.Import(paths, ElwigData.ImportMode.FromBranches);
|
||||||
|
} catch (HttpRequestException exc) {
|
||||||
|
MessageBox.Show("Eventuell Internetverbindung prüfen!\n\n" + exc.Message, "Fehler", MessageBoxButton.OK, MessageBoxImage.Error);
|
||||||
|
} catch (TaskCanceledException exc) {
|
||||||
|
MessageBox.Show("Eventuell Internetverbindung prüfen!\n\n" + exc.Message, "Fehler", MessageBoxButton.OK, MessageBoxImage.Error);
|
||||||
} catch (Exception exc) {
|
} catch (Exception exc) {
|
||||||
MessageBox.Show(exc.Message, "Fehler", MessageBoxButton.OK, MessageBoxImage.Error);
|
MessageBox.Show(exc.Message, "Fehler", MessageBoxButton.OK, MessageBoxImage.Error);
|
||||||
}
|
}
|
||||||
Mouse.OverrideCursor = null;
|
Mouse.OverrideCursor = null;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private async void UploadButton_Click(object sender, RoutedEventArgs evt) {
|
||||||
|
if (App.Config.SyncUrl == null)
|
||||||
|
return;
|
||||||
|
Mouse.OverrideCursor = Cursors.AppStarting;
|
||||||
|
try {
|
||||||
|
var path = Path.Combine(App.TempPath, $"{DateTime.Now:yyyy-MM-dd_HH-mm-ss}_{App.ZwstId}.elwig.zip");
|
||||||
|
using var ctx = new AppDbContext();
|
||||||
|
var deliveries = await ctx.Deliveries
|
||||||
|
.Where(d => d.Year == Utils.CurrentLastSeason && d.ZwstId == App.ZwstId)
|
||||||
|
.Include(d => d.Parts)
|
||||||
|
.ThenInclude(p => p.PartModifiers)
|
||||||
|
.OrderBy(d => d.DateString)
|
||||||
|
.ThenBy(d => d.TimeString)
|
||||||
|
.ThenBy(d => d.LsNr)
|
||||||
|
.AsSplitQuery()
|
||||||
|
.ToListAsync();
|
||||||
|
if (deliveries.Count == 0) {
|
||||||
|
MessageBox.Show("Es gibt keine Lieferungen, die hochgeladen werden können!", "Lieferungen hochladen",
|
||||||
|
MessageBoxButton.OK, MessageBoxImage.Error);
|
||||||
|
} else {
|
||||||
|
await ElwigData.Export(path, deliveries, [$"{Utils.CurrentLastSeason}", $"Zweigstelle {App.BranchName}"]);
|
||||||
|
await Utils.UploadExportData(path, App.Config.SyncUrl, App.Config.SyncUsername, App.Config.SyncPassword);
|
||||||
|
MessageBox.Show($"Hochladen von {deliveries.Count} Lieferungen erfolgreich!", "Lieferungen hochladen",
|
||||||
|
MessageBoxButton.OK, MessageBoxImage.Information);
|
||||||
|
}
|
||||||
|
} catch (HttpRequestException exc) {
|
||||||
|
MessageBox.Show("Eventuell Internetverbindung prüfen!\n\n" + exc.Message, "Lieferungen hochladen", MessageBoxButton.OK, MessageBoxImage.Error);
|
||||||
|
} catch (TaskCanceledException exc) {
|
||||||
|
MessageBox.Show("Eventuell Internetverbindung prüfen!\n\n" + exc.Message, "Fehler", MessageBoxButton.OK, MessageBoxImage.Error);
|
||||||
|
} catch (Exception exc) {
|
||||||
|
MessageBox.Show(exc.Message, "Lieferungen 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();
|
||||||
|
@ -4,8 +4,12 @@
|
|||||||
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:local="clr-namespace:Elwig.Windows"
|
xmlns:local="clr-namespace:Elwig.Windows"
|
||||||
|
xmlns:vm="clr-namespace:Elwig.ViewModels"
|
||||||
Title="Mitglieder - Elwig" Height="700" Width="1250" MinHeight="650" MinWidth="1150"
|
Title="Mitglieder - Elwig" Height="700" Width="1250" MinHeight="650" MinWidth="1150"
|
||||||
Loaded="Window_Loaded">
|
Loaded="Window_Loaded">
|
||||||
|
<Window.DataContext>
|
||||||
|
<vm:MemberAdminViewModel/>
|
||||||
|
</Window.DataContext>
|
||||||
<Window.Resources>
|
<Window.Resources>
|
||||||
<Style TargetType="Label">
|
<Style TargetType="Label">
|
||||||
<Setter Property="HorizontalAlignment" Value="Left"/>
|
<Setter Property="HorizontalAlignment" Value="Left"/>
|
||||||
@ -47,19 +51,19 @@
|
|||||||
|
|
||||||
<Menu Grid.ColumnSpan="3" BorderThickness="0,0,0,1" BorderBrush="LightGray" Background="White">
|
<Menu Grid.ColumnSpan="3" BorderThickness="0,0,0,1" BorderBrush="LightGray" Background="White">
|
||||||
<MenuItem Header="Kontaktieren">
|
<MenuItem Header="Kontaktieren">
|
||||||
<MenuItem x:Name="Menu_Contact_Email" Header="E-Mail senden..." IsEnabled="False"
|
<MenuItem x:Name="Menu_Contact_Email" Header="E-Mail senden..." IsEnabled="{Binding MemberHasEmail}"
|
||||||
Click="Menu_Contact_Email_Click"/>
|
Click="Menu_Contact_Email_Click"/>
|
||||||
<MenuItem x:Name="Menu_Contact_Letterhead" Header="Briefkopf drucken" IsEnabled="False"
|
<MenuItem x:Name="Menu_Contact_Letterhead" Header="Briefkopf drucken" IsEnabled="{Binding IsMemberSelected}"
|
||||||
Click="Menu_Contact_Letterhead_Click"/>
|
Click="Menu_Contact_Letterhead_Click"/>
|
||||||
</MenuItem>
|
</MenuItem>
|
||||||
<MenuItem Header="Stammdatenblatt">
|
<MenuItem Header="Stammdatenblatt">
|
||||||
<MenuItem x:Name="Menu_MemberDataSheet_Show" Header="...anzeigen (PDF)" IsEnabled="False"
|
<MenuItem x:Name="Menu_MemberDataSheet_Show" Header="...anzeigen (PDF)" IsEnabled="{Binding IsMemberSelected}"
|
||||||
Click="Menu_MemberDataSheet_Show_Click" InputGestureText="Strg+P"/>
|
Click="Menu_MemberDataSheet_Show_Click" InputGestureText="Strg+P"/>
|
||||||
<MenuItem x:Name="Menu_MemberDataSheet_SavePdf" Header="...speichern... (PDF)" IsEnabled="False"
|
<MenuItem x:Name="Menu_MemberDataSheet_SavePdf" Header="...speichern... (PDF)" IsEnabled="{Binding IsMemberSelected}"
|
||||||
Click="Menu_MemberDataSheet_SavePdf_Click"/>
|
Click="Menu_MemberDataSheet_SavePdf_Click"/>
|
||||||
<MenuItem x:Name="Menu_MemberDataSheet_Print" Header="...drucken" IsEnabled="False"
|
<MenuItem x:Name="Menu_MemberDataSheet_Print" Header="...drucken" IsEnabled="{Binding IsMemberSelected}"
|
||||||
Click="Menu_MemberDataSheet_Print_Click" InputGestureText="Strg+Shift+P"/>
|
Click="Menu_MemberDataSheet_Print_Click" InputGestureText="Strg+Shift+P"/>
|
||||||
<MenuItem x:Name="Menu_MemberDataSheet_Email" Header="...per E-Mail schicken" IsEnabled="False"
|
<MenuItem x:Name="Menu_MemberDataSheet_Email" Header="...per E-Mail schicken" IsEnabled="{Binding MemberCanSendEmail}"
|
||||||
Click="Menu_MemberDataSheet_Email_Click"/>
|
Click="Menu_MemberDataSheet_Email_Click"/>
|
||||||
</MenuItem>
|
</MenuItem>
|
||||||
<MenuItem Header="Anlieferungsbestätigung" x:Name="Menu_DeliveryConfirmation">
|
<MenuItem Header="Anlieferungsbestätigung" x:Name="Menu_DeliveryConfirmation">
|
||||||
@ -110,18 +114,37 @@
|
|||||||
<MenuItem x:Name="Menu_List_PrintAll" Header="...mit allen drucken"
|
<MenuItem x:Name="Menu_List_PrintAll" Header="...mit allen drucken"
|
||||||
Click="Menu_List_PrintAll_Click"/>
|
Click="Menu_List_PrintAll_Click"/>
|
||||||
<Separator/>
|
<Separator/>
|
||||||
<MenuItem x:Name="Menu_List_OrderMgNr" Header="...nach MgNr. sortieren" IsCheckable="True" IsChecked="True"
|
<MenuItem x:Name="Menu_List_OrderMgNr" Header="...nach MgNr. sortieren"
|
||||||
|
IsCheckable="True" IsChecked="{Binding MemberListOrderByMgNr, Mode=TwoWay}"
|
||||||
Click="Menu_List_Order_Click"/>
|
Click="Menu_List_Order_Click"/>
|
||||||
<MenuItem x:Name="Menu_List_OrderName" Header="...nach Nachname, Vorname sortieren" IsCheckable="True"
|
<MenuItem x:Name="Menu_List_OrderName" Header="...nach Nachname, Vorname sortieren"
|
||||||
|
IsCheckable="True" IsChecked="{Binding MemberListOrderByName, Mode=TwoWay}"
|
||||||
Click="Menu_List_Order_Click"/>
|
Click="Menu_List_Order_Click"/>
|
||||||
<MenuItem x:Name="Menu_List_OrderOrt" Header="...nach Stamm-KG, Name sortieren" IsCheckable="True"
|
<MenuItem x:Name="Menu_List_OrderOrt" Header="...nach Stamm-KG, Name sortieren"
|
||||||
|
IsCheckable="True" IsChecked="{Binding MemberListOrderByOrt, Mode=TwoWay}"
|
||||||
Click="Menu_List_Order_Click"/>
|
Click="Menu_List_Order_Click"/>
|
||||||
</MenuItem>
|
</MenuItem>
|
||||||
|
<MenuItem Header="Export">
|
||||||
|
<MenuItem x:Name="Menu_Export_ExportSelected" Header="...von ausgewähltem Mitglied speichern..." IsEnabled="False"
|
||||||
|
Click="Menu_Export_ExportSelected_Click"/>
|
||||||
|
<MenuItem x:Name="Menu_Export_UploadSelected" Header="...von ausgewähltem Mitglied hochladen" IsEnabled="False"
|
||||||
|
Click="Menu_Export_UploadSelected_Click"/>
|
||||||
|
<Separator/>
|
||||||
|
<MenuItem x:Name="Menu_Export_ExportFilters" Header="...aus Filtern speichern..."
|
||||||
|
Click="Menu_Export_ExportFilters_Click"/>
|
||||||
|
<MenuItem x:Name="Menu_Export_UploadFilters" Header="...aus Filtern hochladen"
|
||||||
|
Click="Menu_Export_UploadFilters_Click"/>
|
||||||
|
<Separator/>
|
||||||
|
<MenuItem x:Name="Menu_Export_ExportAll" Header="...von allen Mitgliedern speichern..."
|
||||||
|
Click="Menu_Export_ExportAll_Click"/>
|
||||||
|
<MenuItem x:Name="Menu_Export_UploadAll" Header="...von allen Mitgliedern hochladen"
|
||||||
|
Click="Menu_Export_UploadAll_Click"/>
|
||||||
|
</MenuItem>
|
||||||
</Menu>
|
</Menu>
|
||||||
|
|
||||||
<Grid Grid.Row="1" Margin="5,0,0,0">
|
<Grid Grid.Row="1" Margin="5,0,0,0">
|
||||||
<Grid.RowDefinitions>
|
<Grid.RowDefinitions>
|
||||||
<RowDefinition Height="39"/>
|
<RowDefinition Height="35"/>
|
||||||
<RowDefinition Height="*"/>
|
<RowDefinition Height="*"/>
|
||||||
<RowDefinition Height="42"/>
|
<RowDefinition Height="42"/>
|
||||||
</Grid.RowDefinitions>
|
</Grid.RowDefinitions>
|
||||||
@ -131,7 +154,8 @@
|
|||||||
<ColumnDefinition Width="*"/>
|
<ColumnDefinition Width="*"/>
|
||||||
</Grid.ColumnDefinitions>
|
</Grid.ColumnDefinitions>
|
||||||
|
|
||||||
<TextBox x:Name="SearchInput" Grid.ColumnSpan="3" Margin="5,7,145,0" IsReadOnly="False"
|
<TextBox x:Name="SearchInput" Text="{Binding SearchQuery, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}" IsEnabled="{Binding EnableSearchInputs}"
|
||||||
|
Grid.ColumnSpan="3" Margin="5,5,140,0"
|
||||||
TextChanged="SearchInput_TextChanged">
|
TextChanged="SearchInput_TextChanged">
|
||||||
<TextBox.ToolTip>
|
<TextBox.ToolTip>
|
||||||
<TextBlock>
|
<TextBlock>
|
||||||
@ -151,15 +175,19 @@
|
|||||||
<Bold>Volllieferant</Bold>: voll[lieferant], !Voll[lieferant] (nicht-Volllieferant)<LineBreak/>
|
<Bold>Volllieferant</Bold>: voll[lieferant], !Voll[lieferant] (nicht-Volllieferant)<LineBreak/>
|
||||||
<Bold>Funktionär</Bold>: Funkt[ionär], !funkt[ionär] (nicht-Funktionär)<LineBreak/>
|
<Bold>Funktionär</Bold>: Funkt[ionär], !funkt[ionär] (nicht-Funktionär)<LineBreak/>
|
||||||
<Bold>Telefon-Nr.</Bold>: z.B. +436641234, ....<LineBreak/>
|
<Bold>Telefon-Nr.</Bold>: z.B. +436641234, ....<LineBreak/>
|
||||||
|
<Bold>Kontaktdaten</Bold>: email (mind. 1 E-Mail-Adr.), telnr (mind. 1 Tel.-Nr.), !email (keine E-Mail-Adr.), !telnr (keine Tel.-Nr.)<LineBreak/>
|
||||||
|
<Bold>Kontaktart</Bold>: kontakt:email, kontakt:post, !kontakt:email, !kontakt:post<LineBreak/>
|
||||||
<Bold>Flächenbindungen</Bold>: z.B. zw, GVK, WRB, ... (Mitglieder mit aktiven Flächenbindungen)<LineBreak/>
|
<Bold>Flächenbindungen</Bold>: z.B. zw, GVK, WRB, ... (Mitglieder mit aktiven Flächenbindungen)<LineBreak/>
|
||||||
<Bold>Freitext</Bold>: z.B. Rechnungsaddresse, Anmerkung, "matzen" (sucht nach dem Text "matzen")
|
<Bold>Freitext</Bold>: z.B. Rechnungsaddresse, Anmerkung, "matzen" (sucht nach dem Text "matzen")
|
||||||
</TextBlock>
|
</TextBlock>
|
||||||
</TextBox.ToolTip>
|
</TextBox.ToolTip>
|
||||||
</TextBox>
|
</TextBox>
|
||||||
<CheckBox x:Name="ActiveMemberInput" Content="Nur aktive anzeigen"
|
<CheckBox x:Name="ActiveMemberInput" Content="Nur aktive anzeigen"
|
||||||
|
IsChecked="{Binding ShowOnlyActiveMembers, Mode=TwoWay}" IsEnabled="{Binding EnableSearchInputs}"
|
||||||
Checked="ActiveMemberInput_Changed" Unchecked="ActiveMemberInput_Changed"
|
Checked="ActiveMemberInput_Changed" Unchecked="ActiveMemberInput_Changed"
|
||||||
HorizontalAlignment="Right" Margin="0,12,10,0" VerticalAlignment="Top" Grid.Column="1" Grid.ColumnSpan="2"/>
|
HorizontalAlignment="Right" Margin="0,10,10,0" VerticalAlignment="Top" Grid.Column="1" Grid.ColumnSpan="2"/>
|
||||||
<DataGrid x:Name="MemberList" AutoGenerateColumns="False" HeadersVisibility="Column" IsReadOnly="True" GridLinesVisibility="None" SelectionMode="Single"
|
<DataGrid x:Name="MemberList" AutoGenerateColumns="False" HeadersVisibility="Column" IsReadOnly="True" GridLinesVisibility="None" SelectionMode="Single"
|
||||||
|
ItemsSource="{Binding Members, Mode=TwoWay}" SelectedItem="{Binding SelectedMember, Mode=TwoWay}"
|
||||||
CanUserDeleteRows="False" CanUserResizeRows="False" CanUserAddRows="False"
|
CanUserDeleteRows="False" CanUserResizeRows="False" CanUserAddRows="False"
|
||||||
SelectionChanged="MemberList_SelectionChanged"
|
SelectionChanged="MemberList_SelectionChanged"
|
||||||
Margin="5,0,5,0" Grid.Row="1" FontSize="14" Grid.ColumnSpan="3">
|
Margin="5,0,5,0" Grid.Row="1" FontSize="14" Grid.ColumnSpan="3">
|
||||||
@ -184,21 +212,21 @@
|
|||||||
</DataGrid.Columns>
|
</DataGrid.Columns>
|
||||||
</DataGrid>
|
</DataGrid>
|
||||||
|
|
||||||
<Button x:Name="NewMemberButton" Content="Neu"
|
<Button x:Name="NewMemberButton" Content="Neu" Visibility="{Binding ControlButtonsVisibility}"
|
||||||
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"
|
||||||
Click="NewMemberButton_Click">
|
Click="NewMemberButton_Click">
|
||||||
<Button.ToolTip>
|
<Button.ToolTip>
|
||||||
<TextBlock FontWeight="Bold">Alt+Einfg</TextBlock>
|
<TextBlock FontWeight="Bold">Alt+Einfg</TextBlock>
|
||||||
</Button.ToolTip>
|
</Button.ToolTip>
|
||||||
</Button>
|
</Button>
|
||||||
<Button x:Name="EditMemberButton" Content="Bearbeiten" IsEnabled="False"
|
<Button x:Name="EditMemberButton" Content="Bearbeiten" IsEnabled="False" Visibility="{Binding ControlButtonsVisibility}"
|
||||||
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"
|
||||||
Click="EditMemberButton_Click">
|
Click="EditMemberButton_Click">
|
||||||
<Button.ToolTip>
|
<Button.ToolTip>
|
||||||
<TextBlock FontWeight="Bold">Strg+B</TextBlock>
|
<TextBlock FontWeight="Bold">Strg+B</TextBlock>
|
||||||
</Button.ToolTip>
|
</Button.ToolTip>
|
||||||
</Button>
|
</Button>
|
||||||
<Button x:Name="DeleteMemberButton" Content="Löschen" IsEnabled="False"
|
<Button x:Name="DeleteMemberButton" Content="Löschen" IsEnabled="False" Visibility="{Binding ControlButtonsVisibility}"
|
||||||
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"
|
||||||
Click="DeleteMemberButton_Click">
|
Click="DeleteMemberButton_Click">
|
||||||
<Button.ToolTip>
|
<Button.ToolTip>
|
||||||
@ -206,21 +234,21 @@
|
|||||||
</Button.ToolTip>
|
</Button.ToolTip>
|
||||||
</Button>
|
</Button>
|
||||||
|
|
||||||
<Button x:Name="SaveButton" Content="Speichern" IsEnabled="False" Visibility="Hidden"
|
<Button x:Name="SaveButton" Content="Speichern" IsEnabled="False" Visibility="{Binding EditingButtonsVisibility}"
|
||||||
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"
|
||||||
Click="SaveButton_Click">
|
Click="SaveButton_Click">
|
||||||
<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="ResetButton" Content="Zurücksetzen" IsEnabled="False" Visibility="Hidden"
|
<Button x:Name="ResetButton" Content="Zurücksetzen" IsEnabled="False" Visibility="{Binding EditingButtonsVisibility}"
|
||||||
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"
|
||||||
Click="ResetButton_Click">
|
Click="ResetButton_Click">
|
||||||
<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="CancelButton" Content="Abbrechen" IsEnabled="False" Visibility="Hidden" IsCancel="True"
|
<Button x:Name="CancelButton" Content="Abbrechen" IsEnabled="False" Visibility="{Binding EditingButtonsVisibility}" 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"
|
||||||
Click="CancelButton_Click">
|
Click="CancelButton_Click">
|
||||||
<Button.ToolTip>
|
<Button.ToolTip>
|
||||||
@ -254,51 +282,62 @@
|
|||||||
</Grid.ColumnDefinitions>
|
</Grid.ColumnDefinitions>
|
||||||
|
|
||||||
<Label Content="MgNr.:" Margin="10,10,0,0" Grid.Column="0"/>
|
<Label Content="MgNr.:" Margin="10,10,0,0" Grid.Column="0"/>
|
||||||
<TextBox x:Name="MgNrInput" Margin="0,10,0,0" Width="48" Grid.Column="1" TextAlignment="Right" HorizontalAlignment="Left"
|
<TextBox x:Name="MgNrInput" Text="{Binding MgNrString, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"
|
||||||
|
Margin="0,10,0,0" Width="48" Grid.Column="1" TextAlignment="Right" HorizontalAlignment="Left"
|
||||||
TextChanged="MgNrInput_TextChanged" LostFocus="MgNrInput_LostFocus"/>
|
TextChanged="MgNrInput_TextChanged" LostFocus="MgNrInput_LostFocus"/>
|
||||||
|
|
||||||
<Label Content="Vorg.:" Margin="10,10,0,0" Grid.Column="2"/>
|
<Label Content="Vorg.:" Margin="10,10,0,0" Grid.Column="2"/>
|
||||||
<TextBox x:Name="PredecessorMgNrInput" Margin="0,10,10,0" Width="48" Grid.Column="3" TextAlignment="Right" HorizontalAlignment="Left"
|
<TextBox x:Name="PredecessorMgNrInput" Text="{Binding PredecessorMgNrString, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"
|
||||||
|
Margin="0,10,10,0" Width="48" Grid.Column="3" TextAlignment="Right" HorizontalAlignment="Left"
|
||||||
TextChanged="PredecessorMgNrInput_TextChanged" LostFocus="PredecessorMgNrInput_LostFocus"/>
|
TextChanged="PredecessorMgNrInput_TextChanged" LostFocus="PredecessorMgNrInput_LostFocus"/>
|
||||||
<Button x:Name="MemberReferenceButton" Grid.Column="3" Height="25" Width="25" FontFamily="Segoe MDL2 Assets" Content="" Padding="0,0,0,0"
|
<Button x:Name="MemberReferenceButton" Grid.Column="3" Height="25" Width="25" FontFamily="Segoe MDL2 Assets" Content="" Padding="0,0,0,0"
|
||||||
Margin="53,10,10,10" VerticalAlignment="Top" HorizontalAlignment="Left" IsEnabled="False" ToolTip="Zu Vorgänger springen"
|
Margin="53,10,10,10" VerticalAlignment="Top" HorizontalAlignment="Left" IsEnabled="{Binding EnableMemberReferenceButton}" ToolTip="Zu Vorgänger springen"
|
||||||
Click="MemberReferenceButton_Click"/>
|
Click="MemberReferenceButton_Click"/>
|
||||||
|
|
||||||
<Label Content="Präfix:" Margin="10,40,0,0" Grid.Column="2"/>
|
<Label Content="Präfix:" Margin="10,40,0,0" Grid.Column="2"/>
|
||||||
<TextBox x:Name="PrefixInput" Margin="0,40,10,0" Grid.Column="3"
|
<TextBox x:Name="PrefixInput" Text="{Binding Prefix, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"
|
||||||
|
Margin="0,40,10,0" Grid.Column="3"
|
||||||
TextChanged="TextBox_TextChanged"/>
|
TextChanged="TextBox_TextChanged"/>
|
||||||
|
|
||||||
<Label Content="Vorname:" Margin="10,40,0,0" Grid.Column="0"/>
|
<Label Content="Vorname:" Margin="10,40,0,0" Grid.Column="0"/>
|
||||||
<TextBox x:Name="GivenNameInput" Margin="0,40,0,0" Grid.Column="1"
|
<TextBox x:Name="GivenNameInput" Text="{Binding GivenName, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"
|
||||||
|
Margin="0,40,0,0" Grid.Column="1"
|
||||||
TextChanged="TextBox_TextChanged"/>
|
TextChanged="TextBox_TextChanged"/>
|
||||||
|
|
||||||
<Label Content="Nachname:" Margin="10,70,0,0" Grid.Column="0"/>
|
<Label Content="Nachname:" Margin="10,70,0,0" Grid.Column="0"/>
|
||||||
<TextBox x:Name="FamilyNameInput" Margin="0,70,0,0" Grid.Column="1"
|
<TextBox x:Name="FamilyNameInput" Text="{Binding FamilyName, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"
|
||||||
|
Margin="0,70,0,0" Grid.Column="1"
|
||||||
TextChanged="TextBox_TextChanged"/>
|
TextChanged="TextBox_TextChanged"/>
|
||||||
|
|
||||||
<Label Content="Suffix:" Margin="10,70,0,0" Grid.Column="2"/>
|
<Label Content="Suffix:" Margin="10,70,0,0" Grid.Column="2"/>
|
||||||
<TextBox x:Name="SuffixInput" Margin="0,70,10,0" Grid.Column="3"
|
<TextBox x:Name="SuffixInput" Text="{Binding Suffix, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"
|
||||||
|
Margin="0,70,10,0" Grid.Column="3"
|
||||||
TextChanged="TextBox_TextChanged"/>
|
TextChanged="TextBox_TextChanged"/>
|
||||||
|
|
||||||
<Label Content="Geburtstag:" Margin="10,100,0,0" Grid.Column="0"/>
|
<Label Content="Geburtstag:" Margin="10,100,0,0" Grid.Column="0"/>
|
||||||
<TextBox x:Name="BirthdayInput" Margin="0,100,0,0" Grid.Column="1" Width="78" TextAlignment="Right" HorizontalAlignment="Left"
|
<TextBox x:Name="BirthdayInput" Text="{Binding Birthday, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"
|
||||||
|
Margin="0,100,0,0" Grid.Column="1" Width="78" TextAlignment="Right" HorizontalAlignment="Left"
|
||||||
TextChanged="PartialDateInput_TextChanged" LostFocus="PartialDateInput_LostFocus"/>
|
TextChanged="PartialDateInput_TextChanged" LostFocus="PartialDateInput_LostFocus"/>
|
||||||
|
|
||||||
<Label Content="Alter:" Margin="85,100,0,0" Grid.Column="1" Grid.ColumnSpan="3"/>
|
<Label Content="Alter:" Margin="85,100,0,0" Grid.Column="1" Grid.ColumnSpan="3"/>
|
||||||
<TextBlock x:Name="Age" Text="-" Margin="119,104,0,0" Grid.Column="1" Grid.ColumnSpan="3" TextWrapping="NoWrap" VerticalAlignment="Top"/>
|
<TextBlock x:Name="Age" Text="{Binding Age, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"
|
||||||
|
Margin="119,104,0,0" Grid.Column="1" Grid.ColumnSpan="3" TextWrapping="NoWrap" VerticalAlignment="Top"/>
|
||||||
|
|
||||||
<CheckBox x:Name="DeceasedInput" Content="Verstorben" IsEnabled="False"
|
<CheckBox x:Name="DeceasedInput" Content="Verstorben" IsChecked="{Binding IsDeceased, Mode=TwoWay}"
|
||||||
Checked="CheckBox_Changed" Unchecked="CheckBox_Changed"
|
Checked="CheckBox_Changed" Unchecked="CheckBox_Changed"
|
||||||
Grid.Column="3" HorizontalAlignment="Left" Margin="0,105,0,0" VerticalAlignment="Top" IsChecked="False"/>
|
Grid.Column="3" HorizontalAlignment="Left" Margin="0,105,0,0" VerticalAlignment="Top"/>
|
||||||
|
|
||||||
<Label Content="Adresse:" Margin="10,130,0,0"/>
|
<Label Content="Adresse:" Margin="10,130,0,0"/>
|
||||||
<TextBox x:Name="AddressInput" Margin="0,130,10,0" Grid.Column="1" Grid.ColumnSpan="3"
|
<TextBox x:Name="AddressInput" Text="{Binding Address, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"
|
||||||
|
Margin="0,130,10,0" Grid.Column="1" Grid.ColumnSpan="3"
|
||||||
TextChanged="TextBox_TextChanged"/>
|
TextChanged="TextBox_TextChanged"/>
|
||||||
|
|
||||||
<Label Content="PLZ/Ort:" Margin="10,160,0,0" Grid.Column="0"/>
|
<Label Content="PLZ/Ort:" Margin="10,160,0,0" Grid.Column="0"/>
|
||||||
<TextBox x:Name="PlzInput" Margin="0,160,0,0" Width="42" Grid.Column="1" HorizontalAlignment="Left"
|
<TextBox x:Name="PlzInput" Margin="0,160,0,0" Text="{Binding PlzString, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"
|
||||||
|
Width="42" Grid.Column="1" HorizontalAlignment="Left"
|
||||||
TextChanged="PlzInput_TextChanged" LostFocus="PlzInput_LostFocus" Tag="PLZ"/>
|
TextChanged="PlzInput_TextChanged" LostFocus="PlzInput_LostFocus" Tag="PLZ"/>
|
||||||
<ComboBox x:Name="OrtInput" ItemTemplate="{StaticResource PostalDestTemplate}" TextSearch.TextPath="Ort.Name"
|
<ComboBox x:Name="OrtInput" SelectedItem="{Binding Ort, Mode=TwoWay}" ItemsSource="{Binding OrtSource, Mode=TwoWay}"
|
||||||
|
ItemTemplate="{StaticResource PostalDestTemplate}" TextSearch.TextPath="Ort.Name"
|
||||||
Margin="47,160,10,0" Grid.Column="1" Grid.ColumnSpan="3"/>
|
Margin="47,160,10,0" Grid.Column="1" Grid.ColumnSpan="3"/>
|
||||||
</Grid>
|
</Grid>
|
||||||
</GroupBox>
|
</GroupBox>
|
||||||
@ -311,93 +350,138 @@
|
|||||||
</Grid.ColumnDefinitions>
|
</Grid.ColumnDefinitions>
|
||||||
|
|
||||||
<Label x:Name="EmailAddress1Label" Content="E-Mail-Adresse:" Margin="10,10,0,0" Grid.Column="0"/>
|
<Label x:Name="EmailAddress1Label" Content="E-Mail-Adresse:" Margin="10,10,0,0" Grid.Column="0"/>
|
||||||
<TextBox x:Name="EmailAddress1Input" Margin="0,10,10,0" Grid.Column="1" Grid.ColumnSpan="2"
|
<TextBox x:Name="EmailAddress1Input" Text="{Binding EmailAddresses[0], Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"
|
||||||
|
Margin="0,10,10,0" Grid.Column="1" Grid.ColumnSpan="2"
|
||||||
TextChanged="EmailAddressInput_TextChanged" LostFocus="EmailAddressInput_LostFocus"/>
|
TextChanged="EmailAddressInput_TextChanged" LostFocus="EmailAddressInput_LostFocus"/>
|
||||||
|
|
||||||
<Label x:Name="EmailAddress2Label" Content="E-Mail-Adresse:" Margin="10,40,0,0" Grid.Column="0"/>
|
<Label x:Name="EmailAddress2Label" Content="E-Mail-Adresse:" Margin="10,40,0,0" Grid.Column="0"/>
|
||||||
<TextBox x:Name="EmailAddress2Input" Margin="0,40,10,0" Grid.Column="1" Grid.ColumnSpan="2"
|
<TextBox x:Name="EmailAddress2Input" Text="{Binding EmailAddresses[1], Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"
|
||||||
|
Margin="0,40,10,0" Grid.Column="1" Grid.ColumnSpan="2"
|
||||||
TextChanged="EmailAddressInput_TextChanged" LostFocus="EmailAddressInput_LostFocus"/>
|
TextChanged="EmailAddressInput_TextChanged" LostFocus="EmailAddressInput_LostFocus"/>
|
||||||
|
|
||||||
<Label x:Name="EmailAddress3Label" Content="E-Mail-Adresse:" Margin="10,70,0,0" Grid.Column="0"/>
|
<Label x:Name="EmailAddress3Label" Content="E-Mail-Adresse:" Margin="10,70,0,0" Grid.Column="0"/>
|
||||||
<TextBox x:Name="EmailAddress3Input" Margin="0,70,10,0" Grid.Column="1" Grid.ColumnSpan="2"
|
<TextBox x:Name="EmailAddress3Input" Text="{Binding EmailAddresses[2], Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"
|
||||||
|
Margin="0,70,10,0" Grid.Column="1" Grid.ColumnSpan="2"
|
||||||
TextChanged="EmailAddressInput_TextChanged" LostFocus="EmailAddressInput_LostFocus"/>
|
TextChanged="EmailAddressInput_TextChanged" LostFocus="EmailAddressInput_LostFocus"/>
|
||||||
|
|
||||||
<Label x:Name="EmailAddress4Label" Content="E-Mail-Adresse:" Margin="10,100,0,0" Grid.Column="0"/>
|
<Label x:Name="EmailAddress4Label" Content="E-Mail-Adresse:" Margin="10,100,0,0" Grid.Column="0"/>
|
||||||
<TextBox x:Name="EmailAddress4Input" Margin="0,100,10,0" Grid.Column="1" Grid.ColumnSpan="2"
|
<TextBox x:Name="EmailAddress4Input" Text="{Binding EmailAddresses[3], Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"
|
||||||
|
Margin="0,100,10,0" Grid.Column="1" Grid.ColumnSpan="2"
|
||||||
TextChanged="EmailAddressInput_TextChanged" LostFocus="EmailAddressInput_LostFocus"/>
|
TextChanged="EmailAddressInput_TextChanged" LostFocus="EmailAddressInput_LostFocus"/>
|
||||||
|
|
||||||
<Label x:Name="EmailAddress5Label" Content="E-Mail-Adresse:" Margin="10,130,0,0" Grid.Column="0"/>
|
<Label x:Name="EmailAddress5Label" Content="E-Mail-Adresse:" Margin="10,130,0,0" Grid.Column="0"/>
|
||||||
<TextBox x:Name="EmailAddress5Input" Margin="0,130,10,0" Grid.Column="1" Grid.ColumnSpan="2"
|
<TextBox x:Name="EmailAddress5Input" Text="{Binding EmailAddresses[4], Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"
|
||||||
|
Margin="0,130,10,0" Grid.Column="1" Grid.ColumnSpan="2"
|
||||||
TextChanged="EmailAddressInput_TextChanged" LostFocus="EmailAddressInput_LostFocus"/>
|
TextChanged="EmailAddressInput_TextChanged" LostFocus="EmailAddressInput_LostFocus"/>
|
||||||
|
|
||||||
<Label x:Name="EmailAddress6Label" Content="E-Mail-Adresse:" Margin="10,160,0,0" Grid.Column="0"/>
|
<Label x:Name="EmailAddress6Label" Content="E-Mail-Adresse:" Margin="10,160,0,0" Grid.Column="0"/>
|
||||||
<TextBox x:Name="EmailAddress6Input" Margin="0,160,10,0" Grid.Column="1" Grid.ColumnSpan="2"
|
<TextBox x:Name="EmailAddress6Input" Text="{Binding EmailAddresses[5], Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"
|
||||||
|
Margin="0,160,10,0" Grid.Column="1" Grid.ColumnSpan="2"
|
||||||
TextChanged="EmailAddressInput_TextChanged" LostFocus="EmailAddressInput_LostFocus"/>
|
TextChanged="EmailAddressInput_TextChanged" LostFocus="EmailAddressInput_LostFocus"/>
|
||||||
|
|
||||||
<Label x:Name="EmailAddress7Label" Content="E-Mail-Adresse:" Margin="10,190,0,0" Grid.Column="0"/>
|
<Label x:Name="EmailAddress7Label" Content="E-Mail-Adresse:" Margin="10,190,0,0" Grid.Column="0"/>
|
||||||
<TextBox x:Name="EmailAddress7Input" Margin="0,190,10,0" Grid.Column="1" Grid.ColumnSpan="2"
|
<TextBox x:Name="EmailAddress7Input" Text="{Binding EmailAddresses[6], Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"
|
||||||
|
Margin="0,190,10,0" Grid.Column="1" Grid.ColumnSpan="2"
|
||||||
TextChanged="EmailAddressInput_TextChanged" LostFocus="EmailAddressInput_LostFocus"/>
|
TextChanged="EmailAddressInput_TextChanged" LostFocus="EmailAddressInput_LostFocus"/>
|
||||||
|
|
||||||
<Label x:Name="EmailAddress8Label" Content="E-Mail-Adresse:" Margin="10,220,0,0" Grid.Column="0"/>
|
<Label x:Name="EmailAddress8Label" Content="E-Mail-Adresse:" Margin="10,220,0,0" Grid.Column="0"/>
|
||||||
<TextBox x:Name="EmailAddress8Input" Margin="0,220,10,0" Grid.Column="1" Grid.ColumnSpan="2"
|
<TextBox x:Name="EmailAddress8Input" Text="{Binding EmailAddresses[7], Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"
|
||||||
|
Margin="0,220,10,0" Grid.Column="1" Grid.ColumnSpan="2"
|
||||||
TextChanged="EmailAddressInput_TextChanged" LostFocus="EmailAddressInput_LostFocus"/>
|
TextChanged="EmailAddressInput_TextChanged" LostFocus="EmailAddressInput_LostFocus"/>
|
||||||
|
|
||||||
<Label x:Name="EmailAddress9Label" Content="E-Mail-Adresse:" Margin="10,250,0,0" Grid.Column="0"/>
|
<Label x:Name="EmailAddress9Label" Content="E-Mail-Adresse:" Margin="10,250,0,0" Grid.Column="0"/>
|
||||||
<TextBox x:Name="EmailAddress9Input" Margin="0,250,10,0" Grid.Column="1" Grid.ColumnSpan="2"
|
<TextBox x:Name="EmailAddress9Input" Text="{Binding EmailAddresses[8], Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"
|
||||||
|
Margin="0,250,10,0" Grid.Column="1" Grid.ColumnSpan="2"
|
||||||
TextChanged="EmailAddressInput_TextChanged" LostFocus="EmailAddressInput_LostFocus"/>
|
TextChanged="EmailAddressInput_TextChanged" LostFocus="EmailAddressInput_LostFocus"/>
|
||||||
|
|
||||||
<ComboBox x:Name="PhoneNr1TypeInput" DisplayMemberPath="Value" Margin="6,70,5,0" FontSize="12" Padding="6,4,4,4"/>
|
<ComboBox x:Name="PhoneNr1TypeInput" DisplayMemberPath="Value"
|
||||||
<TextBox x:Name="PhoneNr1Input" Margin="0,70,5,0" Grid.Column="1"
|
SelectedIndex="{Binding PhoneNrs[0].Type, Mode=TwoWay}" ItemsSource="{Binding PhoneNrTypes}"
|
||||||
|
Margin="6,70,5,0" FontSize="12" Padding="6,4,4,4"/>
|
||||||
|
<TextBox x:Name="PhoneNr1Input" Text="{Binding PhoneNrs[0].Number, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"
|
||||||
|
Margin="0,70,5,0" Grid.Column="1"
|
||||||
TextChanged="PhoneNrInput_TextChanged" LostFocus="PhoneNrInput_LostFocus"/>
|
TextChanged="PhoneNrInput_TextChanged" LostFocus="PhoneNrInput_LostFocus"/>
|
||||||
<TextBox x:Name="PhoneNr1CommentInput" Margin="0,70,10,0" Grid.Column="2"
|
<TextBox x:Name="PhoneNr1CommentInput" Text="{Binding PhoneNrs[0].Comment, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"
|
||||||
|
Margin="0,70,10,0" Grid.Column="2"
|
||||||
TextChanged="TextBox_TextChanged"/>
|
TextChanged="TextBox_TextChanged"/>
|
||||||
|
|
||||||
<ComboBox x:Name="PhoneNr2TypeInput" DisplayMemberPath="Value" Margin="6,100,5,0" FontSize="12" Padding="6,4,4,4"/>
|
<ComboBox x:Name="PhoneNr2TypeInput" DisplayMemberPath="Value"
|
||||||
<TextBox x:Name="PhoneNr2Input" Margin="0,100,5,0" Grid.Column="1"
|
SelectedIndex="{Binding PhoneNrs[1].Type, Mode=TwoWay}" ItemsSource="{Binding PhoneNrTypes}"
|
||||||
|
Margin="6,100,5,0" FontSize="12" Padding="6,4,4,4"/>
|
||||||
|
<TextBox x:Name="PhoneNr2Input" Text="{Binding PhoneNrs[1].Number, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"
|
||||||
|
Margin="0,100,5,0" Grid.Column="1"
|
||||||
TextChanged="PhoneNrInput_TextChanged" LostFocus="PhoneNrInput_LostFocus"/>
|
TextChanged="PhoneNrInput_TextChanged" LostFocus="PhoneNrInput_LostFocus"/>
|
||||||
<TextBox x:Name="PhoneNr2CommentInput" Margin="0,100,10,0" Grid.Column="2"
|
<TextBox x:Name="PhoneNr2CommentInput" Text="{Binding PhoneNrs[1].Comment, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"
|
||||||
|
Margin="0,100,10,0" Grid.Column="2"
|
||||||
TextChanged="TextBox_TextChanged"/>
|
TextChanged="TextBox_TextChanged"/>
|
||||||
|
|
||||||
<ComboBox x:Name="PhoneNr3TypeInput" DisplayMemberPath="Value" Margin="6,130,5,0" FontSize="12" Padding="6,4,4,4"/>
|
<ComboBox x:Name="PhoneNr3TypeInput" DisplayMemberPath="Value"
|
||||||
<TextBox x:Name="PhoneNr3Input" Margin="0,130,5,0" Grid.Column="1"
|
SelectedIndex="{Binding PhoneNrs[2].Type, Mode=TwoWay}" ItemsSource="{Binding PhoneNrTypes}"
|
||||||
|
Margin="6,130,5,0" FontSize="12" Padding="6,4,4,4"/>
|
||||||
|
<TextBox x:Name="PhoneNr3Input" Text="{Binding PhoneNrs[2].Number, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"
|
||||||
|
Margin="0,130,5,0" Grid.Column="1"
|
||||||
TextChanged="PhoneNrInput_TextChanged" LostFocus="PhoneNrInput_LostFocus"/>
|
TextChanged="PhoneNrInput_TextChanged" LostFocus="PhoneNrInput_LostFocus"/>
|
||||||
<TextBox x:Name="PhoneNr3CommentInput" Margin="0,130,10,0" Grid.Column="2"
|
<TextBox x:Name="PhoneNr3CommentInput" Text="{Binding PhoneNrs[2].Comment, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"
|
||||||
|
Margin="0,130,10,0" Grid.Column="2"
|
||||||
TextChanged="TextBox_TextChanged"/>
|
TextChanged="TextBox_TextChanged"/>
|
||||||
|
|
||||||
<ComboBox x:Name="PhoneNr4TypeInput" DisplayMemberPath="Value" Margin="6,160,5,0" FontSize="12" Padding="6,4,4,4"/>
|
<ComboBox x:Name="PhoneNr4TypeInput" DisplayMemberPath="Value"
|
||||||
<TextBox x:Name="PhoneNr4Input" Margin="0,160,5,0" Grid.Column="1"
|
SelectedIndex="{Binding PhoneNrs[3].Type, Mode=TwoWay}" ItemsSource="{Binding PhoneNrTypes}"
|
||||||
|
Margin="6,160,5,0" FontSize="12" Padding="6,4,4,4"/>
|
||||||
|
<TextBox x:Name="PhoneNr4Input" Text="{Binding PhoneNrs[3].Number, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"
|
||||||
|
Margin="0,160,5,0" Grid.Column="1"
|
||||||
TextChanged="PhoneNrInput_TextChanged" LostFocus="PhoneNrInput_LostFocus"/>
|
TextChanged="PhoneNrInput_TextChanged" LostFocus="PhoneNrInput_LostFocus"/>
|
||||||
<TextBox x:Name="PhoneNr4CommentInput" Margin="0,160,10,0" Grid.Column="2"
|
<TextBox x:Name="PhoneNr4CommentInput" Text="{Binding PhoneNrs[3].Comment, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"
|
||||||
|
Margin="0,160,10,0" Grid.Column="2"
|
||||||
TextChanged="TextBox_TextChanged"/>
|
TextChanged="TextBox_TextChanged"/>
|
||||||
|
|
||||||
<ComboBox x:Name="PhoneNr5TypeInput" DisplayMemberPath="Value" Margin="6,190,5,0" FontSize="12" Padding="6,4,4,4"/>
|
<ComboBox x:Name="PhoneNr5TypeInput" DisplayMemberPath="Value"
|
||||||
<TextBox x:Name="PhoneNr5Input" Margin="0,190,5,0" Grid.Column="1"
|
SelectedIndex="{Binding PhoneNrs[4].Type, Mode=TwoWay}" ItemsSource="{Binding PhoneNrTypes}"
|
||||||
|
Margin="6,190,5,0" FontSize="12" Padding="6,4,4,4"/>
|
||||||
|
<TextBox x:Name="PhoneNr5Input" Text="{Binding PhoneNrs[4].Number, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"
|
||||||
|
Margin="0,190,5,0" Grid.Column="1"
|
||||||
TextChanged="PhoneNrInput_TextChanged" LostFocus="PhoneNrInput_LostFocus"/>
|
TextChanged="PhoneNrInput_TextChanged" LostFocus="PhoneNrInput_LostFocus"/>
|
||||||
<TextBox x:Name="PhoneNr5CommentInput" Margin="0,190,10,0" Grid.Column="2"
|
<TextBox x:Name="PhoneNr5CommentInput" Text="{Binding PhoneNrs[4].Comment, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"
|
||||||
|
Margin="0,190,10,0" Grid.Column="2"
|
||||||
TextChanged="TextBox_TextChanged"/>
|
TextChanged="TextBox_TextChanged"/>
|
||||||
|
|
||||||
<ComboBox x:Name="PhoneNr6TypeInput" DisplayMemberPath="Value" Margin="6,220,5,0" FontSize="12" Padding="6,4,4,4"/>
|
<ComboBox x:Name="PhoneNr6TypeInput" DisplayMemberPath="Value"
|
||||||
<TextBox x:Name="PhoneNr6Input" Margin="0,220,5,0" Grid.Column="1"
|
SelectedIndex="{Binding PhoneNrs[5].Type, Mode=TwoWay}" ItemsSource="{Binding PhoneNrTypes}"
|
||||||
|
Margin="6,220,5,0" FontSize="12" Padding="6,4,4,4"/>
|
||||||
|
<TextBox x:Name="PhoneNr6Input" Text="{Binding PhoneNrs[5].Number, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"
|
||||||
|
Margin="0,220,5,0" Grid.Column="1"
|
||||||
TextChanged="PhoneNrInput_TextChanged" LostFocus="PhoneNrInput_LostFocus"/>
|
TextChanged="PhoneNrInput_TextChanged" LostFocus="PhoneNrInput_LostFocus"/>
|
||||||
<TextBox x:Name="PhoneNr6CommentInput" Margin="0,220,10,0" Grid.Column="2"
|
<TextBox x:Name="PhoneNr6CommentInput" Text="{Binding PhoneNrs[5].Comment, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"
|
||||||
|
Margin="0,220,10,0" Grid.Column="2"
|
||||||
TextChanged="TextBox_TextChanged"/>
|
TextChanged="TextBox_TextChanged"/>
|
||||||
|
|
||||||
<ComboBox x:Name="PhoneNr7TypeInput" DisplayMemberPath="Value" Margin="6,250,5,0" FontSize="12" Padding="6,4,4,4"/>
|
<ComboBox x:Name="PhoneNr7TypeInput" DisplayMemberPath="Value"
|
||||||
<TextBox x:Name="PhoneNr7Input" Margin="0,250,5,0" Grid.Column="1"
|
SelectedIndex="{Binding PhoneNrs[6].Type, Mode=TwoWay}" ItemsSource="{Binding PhoneNrTypes}"
|
||||||
|
Margin="6,250,5,0" FontSize="12" Padding="6,4,4,4"/>
|
||||||
|
<TextBox x:Name="PhoneNr7Input" Text="{Binding PhoneNrs[6].Number, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"
|
||||||
|
Margin="0,250,5,0" Grid.Column="1"
|
||||||
TextChanged="PhoneNrInput_TextChanged" LostFocus="PhoneNrInput_LostFocus"/>
|
TextChanged="PhoneNrInput_TextChanged" LostFocus="PhoneNrInput_LostFocus"/>
|
||||||
<TextBox x:Name="PhoneNr7CommentInput" Margin="0,250,10,0" Grid.Column="2"
|
<TextBox x:Name="PhoneNr7CommentInput" Text="{Binding PhoneNrs[6].Comment, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"
|
||||||
|
Margin="0,250,10,0" Grid.Column="2"
|
||||||
TextChanged="TextBox_TextChanged"/>
|
TextChanged="TextBox_TextChanged"/>
|
||||||
|
|
||||||
<ComboBox x:Name="PhoneNr8TypeInput" DisplayMemberPath="Value" Margin="6,280,5,0" FontSize="12" Padding="6,4,4,4"/>
|
<ComboBox x:Name="PhoneNr8TypeInput" DisplayMemberPath="Value"
|
||||||
<TextBox x:Name="PhoneNr8Input" Margin="0,280,5,0" Grid.Column="1"
|
SelectedIndex="{Binding PhoneNrs[7].Type, Mode=TwoWay}" ItemsSource="{Binding PhoneNrTypes}"
|
||||||
|
Margin="6,280,5,0" FontSize="12" Padding="6,4,4,4"/>
|
||||||
|
<TextBox x:Name="PhoneNr8Input" Text="{Binding PhoneNrs[7].Number, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"
|
||||||
|
Margin="0,280,5,0" Grid.Column="1"
|
||||||
TextChanged="PhoneNrInput_TextChanged" LostFocus="PhoneNrInput_LostFocus"/>
|
TextChanged="PhoneNrInput_TextChanged" LostFocus="PhoneNrInput_LostFocus"/>
|
||||||
<TextBox x:Name="PhoneNr8CommentInput" Margin="0,280,10,0" Grid.Column="2"
|
<TextBox x:Name="PhoneNr8CommentInput" Text="{Binding PhoneNrs[7].Comment, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"
|
||||||
|
Margin="0,280,10,0" Grid.Column="2"
|
||||||
TextChanged="TextBox_TextChanged"/>
|
TextChanged="TextBox_TextChanged"/>
|
||||||
|
|
||||||
<ComboBox x:Name="PhoneNr9TypeInput" DisplayMemberPath="Value" Margin="6,310,5,0" FontSize="12" Padding="6,4,4,4"/>
|
<ComboBox x:Name="PhoneNr9TypeInput" DisplayMemberPath="Value"
|
||||||
<TextBox x:Name="PhoneNr9Input" Margin="0,310,5,0" Grid.Column="1"
|
SelectedIndex="{Binding PhoneNrs[8].Type, Mode=TwoWay}" ItemsSource="{Binding PhoneNrTypes}"
|
||||||
|
Margin="6,310,5,0" FontSize="12" Padding="6,4,4,4"/>
|
||||||
|
<TextBox x:Name="PhoneNr9Input" Text="{Binding PhoneNrs[8].Number, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"
|
||||||
|
Margin="0,310,5,0" Grid.Column="1"
|
||||||
TextChanged="PhoneNrInput_TextChanged" LostFocus="PhoneNrInput_LostFocus"/>
|
TextChanged="PhoneNrInput_TextChanged" LostFocus="PhoneNrInput_LostFocus"/>
|
||||||
<TextBox x:Name="PhoneNr9CommentInput" Margin="0,280,10,0" Grid.Column="2"
|
<TextBox x:Name="PhoneNr9CommentInput" Text="{Binding PhoneNrs[8].Comment, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"
|
||||||
|
Margin="0,280,10,0" Grid.Column="2"
|
||||||
TextChanged="TextBox_TextChanged"/>
|
TextChanged="TextBox_TextChanged"/>
|
||||||
</Grid>
|
</Grid>
|
||||||
</GroupBox>
|
</GroupBox>
|
||||||
@ -409,11 +493,13 @@
|
|||||||
</Grid.ColumnDefinitions>
|
</Grid.ColumnDefinitions>
|
||||||
|
|
||||||
<Label Content="IBAN:" Margin="10,10,0,0" Grid.Column="0"/>
|
<Label Content="IBAN:" Margin="10,10,0,0" Grid.Column="0"/>
|
||||||
<TextBox x:Name="IbanInput" Margin="0,10,10,0" Grid.Column="1" Width="290" HorizontalAlignment="Left"
|
<TextBox x:Name="IbanInput" Text="{Binding Iban, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"
|
||||||
|
Margin="0,10,10,0" Grid.Column="1" Width="290" HorizontalAlignment="Left"
|
||||||
TextChanged="IbanInput_TextChanged" LostFocus="IbanInput_LostFocus"/>
|
TextChanged="IbanInput_TextChanged" LostFocus="IbanInput_LostFocus"/>
|
||||||
|
|
||||||
<Label Content="BIC:" Margin="10,40,0,0" Grid.Column="0"/>
|
<Label Content="BIC:" Margin="10,40,0,0" Grid.Column="0"/>
|
||||||
<TextBox x:Name="BicInput" Margin="0,40,10,0" Grid.Column="1" Width="150" HorizontalAlignment="Left"
|
<TextBox x:Name="BicInput" Text="{Binding Bic, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"
|
||||||
|
Margin="0,40,10,0" Grid.Column="1" Width="150" HorizontalAlignment="Left"
|
||||||
TextChanged="BicInput_TextChanged" LostFocus="BicInput_LostFocus"/>
|
TextChanged="BicInput_TextChanged" LostFocus="BicInput_LostFocus"/>
|
||||||
</Grid>
|
</Grid>
|
||||||
</GroupBox>
|
</GroupBox>
|
||||||
@ -426,21 +512,24 @@
|
|||||||
</Grid.ColumnDefinitions>
|
</Grid.ColumnDefinitions>
|
||||||
|
|
||||||
<Label Content="UID:" Margin="10,10,0,0" Grid.Column="0"/>
|
<Label Content="UID:" Margin="10,10,0,0" Grid.Column="0"/>
|
||||||
<TextBox x:Name="UstIdNrInput" Margin="0,10,10,0" Grid.Column="1" Width="96" HorizontalAlignment="Left"
|
<TextBox x:Name="UstIdNrInput" Text="{Binding UstIdNr, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"
|
||||||
|
Margin="0,10,10,0" Grid.Column="1" Width="96" HorizontalAlignment="Left"
|
||||||
TextChanged="UstIdNrInput_TextChanged" LostFocus="UstIdNrInput_LostFocus"/>
|
TextChanged="UstIdNrInput_TextChanged" LostFocus="UstIdNrInput_LostFocus"/>
|
||||||
|
|
||||||
<Label Content="Betriebs-Nr.:" Margin="10,40,0,0" Grid.Column="0"/>
|
<Label Content="Betriebs-Nr.:" Margin="10,40,0,0" Grid.Column="0"/>
|
||||||
<TextBox x:Name="LfbisNrInput" Margin="0,40,10,0" Grid.Column="1" Width="64" HorizontalAlignment="Left" TextAlignment="Right"
|
<TextBox x:Name="LfbisNrInput" Text="{Binding LfbisNr, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"
|
||||||
|
Margin="0,40,10,0" Grid.Column="1" Width="64" HorizontalAlignment="Left" TextAlignment="Right"
|
||||||
TextChanged="LfbisNrInput_TextChanged" LostFocus="LfbisNrInput_LostFocus"/>
|
TextChanged="LfbisNrInput_TextChanged" LostFocus="LfbisNrInput_LostFocus"/>
|
||||||
|
|
||||||
<CheckBox x:Name="BuchführendInput" Content="Buchführend" IsEnabled="False"
|
<CheckBox x:Name="BuchführendInput" Content="Buchführend" IsChecked="{Binding IsBuchführend, Mode=TwoWay}" IsEnabled="False"
|
||||||
Checked="CheckBox_Changed" Unchecked="CheckBox_Changed"
|
Checked="CheckBox_Changed" Unchecked="CheckBox_Changed"
|
||||||
Grid.Column="2" HorizontalAlignment="Left" Margin="10,15,0,0" VerticalAlignment="Top" IsChecked="False"/>
|
Grid.Column="2" HorizontalAlignment="Left" Margin="10,15,0,0" VerticalAlignment="Top"/>
|
||||||
|
|
||||||
<CheckBox x:Name="OrganicInput" Content="Bio" IsEnabled="False"
|
<CheckBox x:Name="OrganicInput" Content="Bio" IsChecked="{Binding IsOrganic, Mode=TwoWay}" IsEnabled="False"
|
||||||
Checked="CheckBox_Changed" Unchecked="CheckBox_Changed"
|
Checked="CheckBox_Changed" Unchecked="CheckBox_Changed"
|
||||||
Grid.Column="2" HorizontalAlignment="Left" Margin="10,45,0,0" VerticalAlignment="Top" IsChecked="False"/>
|
Grid.Column="2" HorizontalAlignment="Left" Margin="10,45,0,0" VerticalAlignment="Top"/>
|
||||||
<Button x:Name="OrganicButton" Content="easy-cert.com" Height="25" FontSize="12" IsEnabled="False"
|
<Button x:Name="OrganicButton" Content="easy-cert.com" IsEnabled="{Binding IsMemberSelected}"
|
||||||
|
Height="25" FontSize="12"
|
||||||
Click="OrganicButton_Click"
|
Click="OrganicButton_Click"
|
||||||
Grid.Column="2" HorizontalAlignment="Left" VerticalAlignment="Top" Margin="60,40,0,0"/>
|
Grid.Column="2" HorizontalAlignment="Left" VerticalAlignment="Top" Margin="60,40,0,0"/>
|
||||||
</Grid>
|
</Grid>
|
||||||
@ -453,17 +542,21 @@
|
|||||||
</Grid.ColumnDefinitions>
|
</Grid.ColumnDefinitions>
|
||||||
|
|
||||||
<Label Content="Name:" Margin="10,10,0,0" Grid.Column="0"/>
|
<Label Content="Name:" Margin="10,10,0,0" Grid.Column="0"/>
|
||||||
<TextBox x:Name="BillingNameInput" Margin="0,10,10,10" Grid.Column="1" Grid.ColumnSpan="2"
|
<TextBox x:Name="BillingNameInput" Text="{Binding BillingName, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"
|
||||||
|
Margin="0,10,10,10" Grid.Column="1" Grid.ColumnSpan="2"
|
||||||
TextChanged="TextBox_TextChanged"/>
|
TextChanged="TextBox_TextChanged"/>
|
||||||
|
|
||||||
<Label Content="Adresse:" Margin="10,40,0,0" Grid.Column="0"/>
|
<Label Content="Adresse:" Margin="10,40,0,0" Grid.Column="0"/>
|
||||||
<TextBox x:Name="BillingAddressInput" Margin="0,40,10,0" Grid.Column="1"
|
<TextBox x:Name="BillingAddressInput" Text="{Binding BillingAddress, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"
|
||||||
|
Margin="0,40,10,0" Grid.Column="1"
|
||||||
TextChanged="TextBox_TextChanged"/>
|
TextChanged="TextBox_TextChanged"/>
|
||||||
|
|
||||||
<Label Content="PLZ/Ort:" Margin="10,70,0,0" Grid.Column="0"/>
|
<Label Content="PLZ/Ort:" Margin="10,70,0,0" Grid.Column="0"/>
|
||||||
<TextBox x:Name="BillingPlzInput" Margin="0,70,0,0" Width="42" Grid.Column="1" HorizontalAlignment="Left"
|
<TextBox x:Name="BillingPlzInput" Text="{Binding BillingPlzString, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"
|
||||||
|
Margin="0,70,0,0" Width="42" Grid.Column="1" HorizontalAlignment="Left"
|
||||||
TextChanged="PlzInput_TextChanged" LostFocus="PlzInput_LostFocus" Tag="PLZ"/>
|
TextChanged="PlzInput_TextChanged" LostFocus="PlzInput_LostFocus" Tag="PLZ"/>
|
||||||
<ComboBox x:Name="BillingOrtInput" ItemTemplate="{StaticResource PostalDestTemplate}" TextSearch.TextPath="Ort.Name"
|
<ComboBox x:Name="BillingOrtInput" SelectedItem="{Binding BillingOrt, Mode=TwoWay}" ItemsSource="{Binding BillingOrtSource, Mode=TwoWay}"
|
||||||
|
ItemTemplate="{StaticResource PostalDestTemplate}" TextSearch.TextPath="Ort.Name"
|
||||||
Margin="47,70,10,0" Grid.Column="1"/>
|
Margin="47,70,10,0" Grid.Column="1"/>
|
||||||
</Grid>
|
</Grid>
|
||||||
</GroupBox>
|
</GroupBox>
|
||||||
@ -476,60 +569,69 @@
|
|||||||
</Grid.ColumnDefinitions>
|
</Grid.ColumnDefinitions>
|
||||||
|
|
||||||
<Label Content="Eintritt:" Margin="10,10,0,0" Grid.Column="0"/>
|
<Label Content="Eintritt:" Margin="10,10,0,0" Grid.Column="0"/>
|
||||||
<TextBox x:Name="EntryDateInput" Margin="0,10,10,0" Width="78" Grid.Column="1" HorizontalAlignment="Left" TextAlignment="Right"
|
<TextBox x:Name="EntryDateInput" Text="{Binding EntryDate, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"
|
||||||
|
Margin="0,10,10,0" Width="78" Grid.Column="1" HorizontalAlignment="Left" TextAlignment="Right"
|
||||||
TextChanged="DateInput_TextChanged" LostFocus="DateInput_LostFocus"/>
|
TextChanged="DateInput_TextChanged" LostFocus="DateInput_LostFocus"/>
|
||||||
|
|
||||||
<Label Content="Austritt:" Margin="10,40,0,0" Grid.Column="0"/>
|
<Label Content="Austritt:" Margin="10,40,0,0" Grid.Column="0"/>
|
||||||
<TextBox x:Name="ExitDateInput" Margin="0,40,10,0" Width="78" Grid.Column="1" HorizontalAlignment="Left" TextAlignment="Right"
|
<TextBox x:Name="ExitDateInput" Text="{Binding ExitDate, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"
|
||||||
|
Margin="0,40,10,0" Width="78" Grid.Column="1" HorizontalAlignment="Left" TextAlignment="Right"
|
||||||
TextChanged="DateInput_TextChanged" LostFocus="DateInput_LostFocus"/>
|
TextChanged="DateInput_TextChanged" LostFocus="DateInput_LostFocus"/>
|
||||||
|
|
||||||
<Label Content="Geschäftsanteile:" Margin="10,70,0,0" Grid.Column="0"/>
|
<Label Content="Geschäftsanteile:" Margin="10,70,0,0" Grid.Column="0"/>
|
||||||
<TextBox x:Name="BusinessSharesInput" Margin="0,70,10,0" Width="48" Grid.Column="1" HorizontalAlignment="Left" TextAlignment="Right"
|
<TextBox x:Name="BusinessSharesInput" Text="{Binding BusinessSharesString, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"
|
||||||
|
Margin="0,70,10,0" Width="48" Grid.Column="1" HorizontalAlignment="Left" TextAlignment="Right"
|
||||||
TextChanged="IntegerInput_TextChanged"/>
|
TextChanged="IntegerInput_TextChanged"/>
|
||||||
|
|
||||||
<Label Content="BH-Konto:" Margin="10,100,0,0" Grid.Column="0"/>
|
<Label Content="BH-Konto:" Margin="10,100,0,0" Grid.Column="0"/>
|
||||||
<TextBox x:Name="AccountingNrInput" Margin="0,100,10,0" Grid.Column="1"
|
<TextBox x:Name="AccountingNrInput" Text="{Binding AccountingNr, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"
|
||||||
|
Margin="0,100,10,0" Grid.Column="1"
|
||||||
TextChanged="TextBox_TextChanged"/>
|
TextChanged="TextBox_TextChanged"/>
|
||||||
|
|
||||||
<CheckBox x:Name="ActiveInput" Content="Aktiv" IsEnabled="False"
|
<CheckBox x:Name="ActiveInput" Content="Aktiv" IsChecked="{Binding IsActive, Mode=TwoWay}" IsEnabled="False"
|
||||||
Checked="ActiveInput_Changed" Unchecked="ActiveInput_Changed"
|
Checked="ActiveInput_Changed" Unchecked="ActiveInput_Changed"
|
||||||
Grid.Column="2" HorizontalAlignment="Left" Margin="10,15,0,0" VerticalAlignment="Top" IsChecked="False"/>
|
Grid.Column="2" HorizontalAlignment="Left" Margin="10,15,0,0" VerticalAlignment="Top"/>
|
||||||
|
|
||||||
<CheckBox x:Name="VollLieferantInput" Content="Volllieferant" IsEnabled="False"
|
<CheckBox x:Name="VollLieferantInput" Content="Volllieferant" IsChecked="{Binding IsVollLieferant, Mode=TwoWay}" IsEnabled="False"
|
||||||
Checked="CheckBox_Changed" Unchecked="CheckBox_Changed"
|
Checked="CheckBox_Changed" Unchecked="CheckBox_Changed"
|
||||||
Grid.Column="2" HorizontalAlignment="Left" Margin="10,45,0,0" VerticalAlignment="Top" IsChecked="False"/>
|
Grid.Column="2" HorizontalAlignment="Left" Margin="10,45,0,0" VerticalAlignment="Top"/>
|
||||||
|
|
||||||
<CheckBox x:Name="FunkionärInput" Content="Funktionär" IsEnabled="False"
|
<CheckBox x:Name="FunkionärInput" Content="Funktionär" IsChecked="{Binding IsFunktionär, Mode=TwoWay}" IsEnabled="False"
|
||||||
Checked="CheckBox_Changed" Unchecked="CheckBox_Changed"
|
Checked="CheckBox_Changed" Unchecked="CheckBox_Changed"
|
||||||
Grid.Column="2" HorizontalAlignment="Left" Margin="10,75,0,0" VerticalAlignment="Top" IsChecked="False"/>
|
Grid.Column="2" HorizontalAlignment="Left" Margin="10,75,0,0" VerticalAlignment="Top"/>
|
||||||
|
|
||||||
<Label Content="Stamm-Zwst.:" Margin="10,130,0,0" Grid.Column="0"/>
|
<Label Content="Stamm-Zwst.:" Margin="10,130,0,0" Grid.Column="0"/>
|
||||||
<ComboBox x:Name="BranchInput" DisplayMemberPath="Name" TextSearch.TextPath="Name"
|
<ComboBox x:Name="BranchInput" SelectedItem="{Binding Branch, Mode=TwoWay}" ItemsSource="{Binding BranchSource, Mode=TwoWay}"
|
||||||
|
DisplayMemberPath="Name" TextSearch.TextPath="Name"
|
||||||
Margin="0,130,10,0" Grid.Column="1" Grid.ColumnSpan="2"/>
|
Margin="0,130,10,0" Grid.Column="1" Grid.ColumnSpan="2"/>
|
||||||
|
|
||||||
<Label Content="Stammgemeinde:" Margin="10,160,0,0" Grid.Column="0"/>
|
<Label Content="Stammgemeinde:" Margin="10,160,0,0" Grid.Column="0"/>
|
||||||
<ComboBox x:Name="DefaultKgInput" DisplayMemberPath="Name" TextSearch.TextPath="Name"
|
<ComboBox x:Name="DefaultKgInput" SelectedItem="{Binding DefaultKg, Mode=TwoWay}" ItemsSource="{Binding DefaultKgSource, Mode=TwoWay}"
|
||||||
|
DisplayMemberPath="Name" TextSearch.TextPath="Name"
|
||||||
Margin="0,160,40,10" Grid.Column="1" Grid.ColumnSpan="2"/>
|
Margin="0,160,40,10" Grid.Column="1" Grid.ColumnSpan="2"/>
|
||||||
<Button x:Name="KgDetailsButton" Content="" FontFamily="Segoe MDL2 Assets" FontSize="14" Padding="0,1,0,0"
|
<Button x:Name="KgDetailsButton" Content="" FontFamily="Segoe MDL2 Assets" FontSize="14" Padding="0,1,0,0"
|
||||||
Click="KgDetailsButton_Click"
|
Click="KgDetailsButton_Click"
|
||||||
Grid.Column="2" VerticalAlignment="Top" HorizontalAlignment="Right" Width="25" Height="25" Margin="10,160,10,10"/>
|
Grid.Column="2" VerticalAlignment="Top" HorizontalAlignment="Right" Width="25" Height="25" Margin="10,160,10,10"/>
|
||||||
|
|
||||||
<Label Content="Anmerkung:" Margin="10,190,0,0" Grid.Column="0"/>
|
<Label Content="Anmerkung:" Margin="10,190,0,0" Grid.Column="0"/>
|
||||||
<TextBox x:Name="CommentInput" Margin="0,190,10,70" Grid.Column="1" Grid.ColumnSpan="2"
|
<TextBox x:Name="CommentInput" Text="{Binding Comment, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"
|
||||||
|
Margin="0,190,10,70" Grid.Column="1" Grid.ColumnSpan="2"
|
||||||
TextChanged="TextBox_TextChanged"
|
TextChanged="TextBox_TextChanged"
|
||||||
VerticalAlignment="Stretch" Height="auto" AcceptsReturn="True" TextWrapping="Wrap" VerticalScrollBarVisibility="Visible"/>
|
VerticalAlignment="Stretch" Height="auto" AcceptsReturn="True" TextWrapping="Wrap" VerticalScrollBarVisibility="Visible"/>
|
||||||
|
|
||||||
<Label Content="Kontaktart:" Margin="10,10,0,10" Grid.Column="0" VerticalAlignment="Bottom"/>
|
<Label Content="Kontaktart:" Margin="10,10,0,10" Grid.Column="0" VerticalAlignment="Bottom"/>
|
||||||
<CheckBox x:Name="ContactPostalInput" Content="Post" IsEnabled="False"
|
<CheckBox x:Name="ContactPostalInput" Content="Post" IsChecked="{Binding ContactViaPost, Mode=TwoWay}" IsEnabled="False"
|
||||||
Checked="CheckBox_Changed" Unchecked="CheckBox_Changed"
|
Checked="CheckBox_Changed" Unchecked="CheckBox_Changed"
|
||||||
HorizontalAlignment="Left" Margin="0,0,0,15" VerticalAlignment="Bottom" Grid.Column="1" Grid.ColumnSpan="2"/>
|
HorizontalAlignment="Left" Margin="0,0,0,15" VerticalAlignment="Bottom" Grid.Column="1" Grid.ColumnSpan="2"/>
|
||||||
<CheckBox x:Name="ContactEmailInput" Content="E-Mail" IsEnabled="False"
|
<CheckBox x:Name="ContactEmailInput" Content="E-Mail" IsChecked="{Binding ContactViaEmail, Mode=TwoWay}" IsEnabled="False"
|
||||||
Checked="ContactEmailInput_Changed" Unchecked="ContactEmailInput_Changed"
|
Checked="ContactEmailInput_Changed" Unchecked="ContactEmailInput_Changed"
|
||||||
HorizontalAlignment="Left" Margin="60,0,0,15" VerticalAlignment="Bottom" Grid.Column="1" Grid.ColumnSpan="2"/>
|
HorizontalAlignment="Left" Margin="60,0,0,15" VerticalAlignment="Bottom" Grid.Column="1" Grid.ColumnSpan="2"/>
|
||||||
|
|
||||||
<Button x:Name="DeliveryButton" Content="Lieferungen" Click="DeliveryButton_Click" IsEnabled="False"
|
<Button x:Name="DeliveryButton" Content="Lieferungen" IsEnabled="{Binding IsMemberSelected}"
|
||||||
|
Click="DeliveryButton_Click"
|
||||||
HorizontalAlignment="Right" Margin="10,00,10,37" Width="150" VerticalAlignment="Bottom" Grid.ColumnSpan="3"/>
|
HorizontalAlignment="Right" Margin="10,00,10,37" Width="150" VerticalAlignment="Bottom" Grid.ColumnSpan="3"/>
|
||||||
<Button x:Name="AreaCommitmentButton" Content="Flächenbindungen" Click="AreaCommitmentButton_Click" IsEnabled="False"
|
<Button x:Name="AreaCommitmentButton" Content="Flächenbindungen" IsEnabled="{Binding IsMemberSelected}"
|
||||||
|
Click="AreaCommitmentButton_Click"
|
||||||
HorizontalAlignment="Right" Margin="10,10,10,5" Width="150" VerticalAlignment="Bottom" Grid.ColumnSpan="3"/>
|
HorizontalAlignment="Right" Margin="10,10,10,5" Width="150" VerticalAlignment="Bottom" Grid.ColumnSpan="3"/>
|
||||||
</Grid>
|
</Grid>
|
||||||
</GroupBox>
|
</GroupBox>
|
||||||
@ -544,33 +646,43 @@
|
|||||||
<ColumnDefinition Width="Auto"/>
|
<ColumnDefinition Width="Auto"/>
|
||||||
<ColumnDefinition Width="200"/>
|
<ColumnDefinition Width="200"/>
|
||||||
<ColumnDefinition Width="Auto"/>
|
<ColumnDefinition Width="Auto"/>
|
||||||
<ColumnDefinition Width="2*"/>
|
<ColumnDefinition Width="1*"/>
|
||||||
<ColumnDefinition Width="Auto"/>
|
<ColumnDefinition Width="Auto"/>
|
||||||
<ColumnDefinition Width="3*"/>
|
<ColumnDefinition Width="1*"/>
|
||||||
<ColumnDefinition Width="Auto"/>
|
<ColumnDefinition Width="Auto"/>
|
||||||
<ColumnDefinition Width="3*"/>
|
<ColumnDefinition Width="1*"/>
|
||||||
</Grid.ColumnDefinitions>
|
</Grid.ColumnDefinitions>
|
||||||
</Grid>
|
</Grid>
|
||||||
</ItemsPanelTemplate>
|
</ItemsPanelTemplate>
|
||||||
</StatusBar.ItemsPanel>
|
</StatusBar.ItemsPanel>
|
||||||
<StatusBarItem>
|
<StatusBarItem>
|
||||||
<TextBlock Name="StatusMembers" Text="Mitglieder: -"/>
|
<TextBlock ToolTip="{Binding StatusMembersToolTip}">
|
||||||
|
Mitglieder: <Run Text="{Binding StatusMembers}"/>
|
||||||
|
</TextBlock>
|
||||||
</StatusBarItem>
|
</StatusBarItem>
|
||||||
<Separator Grid.Column="1"/>
|
<Separator Grid.Column="1"/>
|
||||||
<StatusBarItem Grid.Column="2">
|
<StatusBarItem Grid.Column="2">
|
||||||
<TextBlock Name="StatusBusinessShares" Text="Geschäftsanteile: -"/>
|
<TextBlock ToolTip="{Binding StatusBusinessSharesToolTip}">
|
||||||
|
Geschäftsanteile: <Run Text="{Binding StatusBusinessShares}"/>
|
||||||
|
</TextBlock>
|
||||||
</StatusBarItem>
|
</StatusBarItem>
|
||||||
<Separator Grid.Column="3"/>
|
<Separator Grid.Column="3"/>
|
||||||
<StatusBarItem Grid.Column="4">
|
<StatusBarItem Grid.Column="4">
|
||||||
<TextBlock Name="StatusAreaCommitment" Text="Gebundene Fläche: -"/>
|
<TextBlock ToolTip="{Binding StatusAreaCommitmentToolTip}">
|
||||||
|
Gebundene Fläche (<Run Text="{Binding StatusAreaCommitmentInfo}"/>): <Run Text="{Binding StatusAreaCommitment}"/>
|
||||||
|
</TextBlock>
|
||||||
</StatusBarItem>
|
</StatusBarItem>
|
||||||
<Separator Grid.Column="5"/>
|
<Separator Grid.Column="5"/>
|
||||||
<StatusBarItem Grid.Column="6">
|
<StatusBarItem Grid.Column="6">
|
||||||
<TextBlock Name="StatusDeliveriesLastSeason" Text="Lieferungen (letzte Saison): -"/>
|
<TextBlock ToolTip="{Binding StatusDeliveriesThisSeasonToolTip}">
|
||||||
|
Lieferungen (<Run Text="{Binding StatusDeliveriesThisSeasonInfo}"/>): <Run Text="{Binding StatusDeliveriesThisSeason}"/>
|
||||||
|
</TextBlock>
|
||||||
</StatusBarItem>
|
</StatusBarItem>
|
||||||
<Separator Grid.Column="7"/>
|
<Separator Grid.Column="7"/>
|
||||||
<StatusBarItem Grid.Column="8">
|
<StatusBarItem Grid.Column="8">
|
||||||
<TextBlock Name="StatusDeliveriesThisSeason" Text="Lieferungen (aktuelle Saison): -"/>
|
<TextBlock ToolTip="{Binding StatusDeliveriesLastSeasonToolTip}">
|
||||||
|
Lieferungen (<Run Text="{Binding StatusDeliveriesLastSeasonInfo}"/>): <Run Text="{Binding StatusDeliveriesLastSeason}"/>
|
||||||
|
</TextBlock>
|
||||||
</StatusBarItem>
|
</StatusBarItem>
|
||||||
</StatusBar>
|
</StatusBar>
|
||||||
</Grid>
|
</Grid>
|
||||||
|
File diff suppressed because it is too large
Load Diff
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user