0.5.1
This commit is contained in:
@@ -56,4 +56,8 @@ public class User {
|
||||
private LocalDateTime createdAt;
|
||||
private LocalDateTime updatedAt;
|
||||
private Set<String> roles;
|
||||
|
||||
// Digitale Abwicklung und App-Nutzer Ortung
|
||||
private boolean digitalProcessingEnabled = true; // Digitale Abwicklung per App
|
||||
private boolean locationTrackingEnabled = true; // App-Nutzer orten
|
||||
}
|
||||
@@ -38,8 +38,10 @@ public class AddAppDeviceView extends VerticalLayout {
|
||||
// Formularfelder erstellen
|
||||
nameField = new TextField("Gerätename");
|
||||
nameField.setRequired(true);
|
||||
nameField.setRequiredIndicatorVisible(true);
|
||||
nameField.setPlaceholder("z.B. iPhone 15, Samsung Galaxy S24");
|
||||
nameField.setWidth("100%");
|
||||
nameField.addBlurListener(e -> validateNameField());
|
||||
|
||||
// Layout konfigurieren
|
||||
setSizeFull();
|
||||
@@ -103,10 +105,18 @@ public class AddAppDeviceView extends VerticalLayout {
|
||||
}
|
||||
|
||||
private void populateTestData() {
|
||||
nameField.setValue("iPhone 15 Pro");
|
||||
// No default values - field starts empty
|
||||
}
|
||||
|
||||
private void createAppDevice() {
|
||||
// Validate field first
|
||||
validateNameField();
|
||||
|
||||
if (nameField.isInvalid()) {
|
||||
Notification.show("Bitte füllen Sie das Pflichtfeld korrekt aus", 3000, Notification.Position.MIDDLE);
|
||||
return;
|
||||
}
|
||||
|
||||
if (binder.validate().isOk()) {
|
||||
try {
|
||||
AppDevice appDevice = new AppDevice();
|
||||
@@ -135,4 +145,15 @@ public class AddAppDeviceView extends VerticalLayout {
|
||||
private void navigateBack() {
|
||||
getUI().ifPresent(ui -> ui.navigate("app-devices"));
|
||||
}
|
||||
|
||||
private void validateNameField() {
|
||||
String value = nameField.getValue();
|
||||
if (value == null || value.trim().isEmpty()) {
|
||||
nameField.setInvalid(true);
|
||||
nameField.setErrorMessage("Gerätename ist ein Pflichtfeld");
|
||||
} else {
|
||||
nameField.setInvalid(false);
|
||||
nameField.setErrorMessage("");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -89,9 +89,16 @@ public class AddAppUserView extends VerticalLayout {
|
||||
// Configure fields
|
||||
designationField.setPlaceholder("(HH H 000)");
|
||||
designationField.setWidthFull();
|
||||
designationField.setRequiredIndicatorVisible(true);
|
||||
designationField.addBlurListener(e -> validateField(designationField, "Kennung ist ein Pflichtfeld"));
|
||||
|
||||
firstnameField.setWidthFull();
|
||||
firstnameField.setRequiredIndicatorVisible(true);
|
||||
firstnameField.addBlurListener(e -> validateField(firstnameField, "Vorname ist ein Pflichtfeld"));
|
||||
|
||||
lastnameField.setWidthFull();
|
||||
lastnameField.setRequiredIndicatorVisible(true);
|
||||
lastnameField.addBlurListener(e -> validateField(lastnameField, "Nachname ist ein Pflichtfeld"));
|
||||
|
||||
// Create horizontal layout for firstname and lastname
|
||||
HorizontalLayout nameLayout = new HorizontalLayout();
|
||||
@@ -100,20 +107,41 @@ public class AddAppUserView extends VerticalLayout {
|
||||
nameLayout.add(firstnameField, lastnameField);
|
||||
|
||||
phoneField.setWidthFull();
|
||||
phoneField.setRequiredIndicatorVisible(true);
|
||||
phoneField.addBlurListener(e -> validateField(phoneField, "Telefonnummer ist ein Pflichtfeld"));
|
||||
|
||||
appCodeField.setWidthFull();
|
||||
appCodeField.setRequiredIndicatorVisible(true);
|
||||
appCodeField.addBlurListener(e -> validateField(appCodeField, "App-Code ist ein Pflichtfeld"));
|
||||
|
||||
emailField.setWidthFull();
|
||||
emailField.setRequiredIndicatorVisible(true);
|
||||
emailField.addBlurListener(e -> validateEmailField());
|
||||
// Clear error message when user types a new email
|
||||
emailField.addValueChangeListener(e -> {
|
||||
emailField.setInvalid(false);
|
||||
emailField.setErrorMessage("");
|
||||
});
|
||||
|
||||
passwordField.setWidthFull();
|
||||
passwordField.setRequired(true);
|
||||
passwordField.setRequiredIndicatorVisible(true);
|
||||
passwordField.addBlurListener(e -> validatePasswordField());
|
||||
|
||||
confirmPasswordField.setWidthFull();
|
||||
confirmPasswordField.setRequired(true);
|
||||
confirmPasswordField.setRequiredIndicatorVisible(true);
|
||||
confirmPasswordField.addBlurListener(e -> validateConfirmPasswordField());
|
||||
|
||||
// Configure device dropdown
|
||||
// Geräteauswahl vorbereiten
|
||||
deviceComboBox.setWidthFull();
|
||||
deviceComboBox.setItemLabelGenerator(device -> device.getName());
|
||||
deviceComboBox.setRequired(true);
|
||||
deviceComboBox.setRequiredIndicatorVisible(true);
|
||||
deviceComboBox.setPlaceholder("Bitte wählen...");
|
||||
deviceComboBox.setItems(appDeviceService.findUnassignedDevices());
|
||||
deviceComboBox.addBlurListener(e -> validateDeviceField());
|
||||
|
||||
// Add fields to form
|
||||
formLayout.add(designationField);
|
||||
@@ -170,6 +198,12 @@ public class AddAppUserView extends VerticalLayout {
|
||||
}
|
||||
|
||||
private void createAppUser() {
|
||||
// Validate all fields first
|
||||
if (!validateAllFields()) {
|
||||
Notification.show("Bitte füllen Sie alle Pflichtfelder korrekt aus", 3000, Notification.Position.MIDDLE);
|
||||
return;
|
||||
}
|
||||
|
||||
try {
|
||||
// Create new AppUser object
|
||||
AppUser newAppUser = new AppUser();
|
||||
@@ -193,38 +227,106 @@ public class AddAppUserView extends VerticalLayout {
|
||||
|
||||
} catch (ValidationException e) {
|
||||
Notification.show("Bitte überprüfen Sie die Eingaben", 3000, Notification.Position.MIDDLE);
|
||||
} catch (org.springframework.dao.DuplicateKeyException e) {
|
||||
// Handle duplicate email error
|
||||
if (e.getMessage().contains("email")) {
|
||||
Notification.show("Diese E-Mail-Adresse ist bereits vergeben", 5000, Notification.Position.MIDDLE);
|
||||
emailField.focus();
|
||||
emailField.setInvalid(true);
|
||||
emailField.setErrorMessage("E-Mail-Adresse bereits vorhanden");
|
||||
} else {
|
||||
Notification.show("Ein Fehler ist aufgetreten: Doppelter Wert gefunden", 5000, Notification.Position.MIDDLE);
|
||||
}
|
||||
} catch (Exception e) {
|
||||
Notification.show("Fehler beim Anlegen des App-Nutzers: " + e.getMessage(), 5000, Notification.Position.MIDDLE);
|
||||
}
|
||||
}
|
||||
|
||||
private void populateTestData() {
|
||||
// Fill designation field
|
||||
designationField.setValue("HH H 001");
|
||||
|
||||
// Fill name fields
|
||||
firstnameField.setValue("Max");
|
||||
lastnameField.setValue("Mustermann");
|
||||
|
||||
// Fill phone field
|
||||
phoneField.setValue("+49 123 456789");
|
||||
|
||||
// Fill app code field
|
||||
appCodeField.setValue("APP001");
|
||||
|
||||
// Fill email field
|
||||
emailField.setValue("max.mustermann@example.com");
|
||||
|
||||
// Fill password field
|
||||
passwordField.setValue("testpassword123");
|
||||
|
||||
// Fill confirm password field
|
||||
confirmPasswordField.setValue("testpassword123");
|
||||
|
||||
// Set device to iPhone
|
||||
// deviceComboBox.setValue("iPhone"); // This line is removed as deviceComboBox
|
||||
// is now a ComboBox<AppDevice>
|
||||
// No default values - all fields start empty
|
||||
}
|
||||
|
||||
private void navigateBack() {
|
||||
getUI().ifPresent(ui -> ui.navigate("app-user"));
|
||||
}
|
||||
|
||||
private void validateField(TextField field, String errorMessage) {
|
||||
String value = field.getValue();
|
||||
if (value == null || value.trim().isEmpty()) {
|
||||
field.setInvalid(true);
|
||||
field.setErrorMessage(errorMessage);
|
||||
} else {
|
||||
field.setInvalid(false);
|
||||
field.setErrorMessage("");
|
||||
}
|
||||
}
|
||||
|
||||
private void validateEmailField() {
|
||||
String value = emailField.getValue();
|
||||
if (value == null || value.trim().isEmpty()) {
|
||||
emailField.setInvalid(true);
|
||||
emailField.setErrorMessage("E-Mail-Adresse ist ein Pflichtfeld");
|
||||
} else if (!value.contains("@") || !value.contains(".")) {
|
||||
emailField.setInvalid(true);
|
||||
emailField.setErrorMessage("Bitte geben Sie eine gültige E-Mail-Adresse ein");
|
||||
} else {
|
||||
emailField.setInvalid(false);
|
||||
emailField.setErrorMessage("");
|
||||
}
|
||||
}
|
||||
|
||||
private void validatePasswordField() {
|
||||
String value = passwordField.getValue();
|
||||
if (value == null || value.trim().isEmpty()) {
|
||||
passwordField.setInvalid(true);
|
||||
passwordField.setErrorMessage("Passwort ist ein Pflichtfeld");
|
||||
} else if (value.length() < 6) {
|
||||
passwordField.setInvalid(true);
|
||||
passwordField.setErrorMessage("Passwort muss mindestens 6 Zeichen lang sein");
|
||||
} else {
|
||||
passwordField.setInvalid(false);
|
||||
passwordField.setErrorMessage("");
|
||||
}
|
||||
}
|
||||
|
||||
private void validateConfirmPasswordField() {
|
||||
String password = passwordField.getValue();
|
||||
String confirmPassword = confirmPasswordField.getValue();
|
||||
if (confirmPassword == null || confirmPassword.trim().isEmpty()) {
|
||||
confirmPasswordField.setInvalid(true);
|
||||
confirmPasswordField.setErrorMessage("Bitte bestätigen Sie das Passwort");
|
||||
} else if (!confirmPassword.equals(password)) {
|
||||
confirmPasswordField.setInvalid(true);
|
||||
confirmPasswordField.setErrorMessage("Passwörter stimmen nicht überein");
|
||||
} else {
|
||||
confirmPasswordField.setInvalid(false);
|
||||
confirmPasswordField.setErrorMessage("");
|
||||
}
|
||||
}
|
||||
|
||||
private void validateDeviceField() {
|
||||
if (deviceComboBox.getValue() == null) {
|
||||
deviceComboBox.setInvalid(true);
|
||||
deviceComboBox.setErrorMessage("Bitte wählen Sie ein Gerät aus");
|
||||
} else {
|
||||
deviceComboBox.setInvalid(false);
|
||||
deviceComboBox.setErrorMessage("");
|
||||
}
|
||||
}
|
||||
|
||||
private boolean validateAllFields() {
|
||||
validateField(designationField, "Kennung ist ein Pflichtfeld");
|
||||
validateField(firstnameField, "Vorname ist ein Pflichtfeld");
|
||||
validateField(lastnameField, "Nachname ist ein Pflichtfeld");
|
||||
validateField(phoneField, "Telefonnummer ist ein Pflichtfeld");
|
||||
validateField(appCodeField, "App-Code ist ein Pflichtfeld");
|
||||
validateEmailField();
|
||||
validatePasswordField();
|
||||
validateConfirmPasswordField();
|
||||
validateDeviceField();
|
||||
|
||||
return !designationField.isInvalid() && !firstnameField.isInvalid() && !lastnameField.isInvalid()
|
||||
&& !phoneField.isInvalid() && !appCodeField.isInvalid() && !emailField.isInvalid()
|
||||
&& !passwordField.isInvalid() && !confirmPasswordField.isInvalid() && !deviceComboBox.isInvalid();
|
||||
}
|
||||
}
|
||||
|
||||
@@ -51,6 +51,7 @@ public class AddCustomerView extends Main {
|
||||
companyName = new TextField("Firma");
|
||||
companyName.setRequiredIndicatorVisible(true);
|
||||
companyName.setWidthFull();
|
||||
companyName.addBlurListener(e -> validateField(companyName));
|
||||
|
||||
// Anrede (Dropdown)
|
||||
title = new ComboBox<>("Anrede");
|
||||
@@ -62,16 +63,19 @@ public class AddCustomerView extends Main {
|
||||
firstName = new TextField("Vorname");
|
||||
firstName.setRequiredIndicatorVisible(true);
|
||||
firstName.setWidthFull();
|
||||
firstName.addBlurListener(e -> validateField(firstName));
|
||||
|
||||
// Nachname (Pflichtfeld)
|
||||
lastName = new TextField("Nachname");
|
||||
lastName.setRequiredIndicatorVisible(true);
|
||||
lastName.setWidthFull();
|
||||
lastName.addBlurListener(e -> validateField(lastName));
|
||||
|
||||
// Telefonnummer (Pflichtfeld)
|
||||
telephone = new TextField("Telefonnummer");
|
||||
telephone.setRequiredIndicatorVisible(true);
|
||||
telephone.setWidthFull();
|
||||
telephone.addBlurListener(e -> validateField(telephone));
|
||||
|
||||
// Fax (optional)
|
||||
fax = new TextField("Fax");
|
||||
@@ -81,14 +85,17 @@ public class AddCustomerView extends Main {
|
||||
mail = new TextField("E-Mail-Adresse");
|
||||
mail.setRequiredIndicatorVisible(true);
|
||||
mail.setWidthFull();
|
||||
mail.addBlurListener(e -> validateEmail());
|
||||
|
||||
// Straße (Pflichtfeld)
|
||||
street = new TextField("Straße");
|
||||
street.setRequiredIndicatorVisible(true);
|
||||
street.addBlurListener(e -> validateField(street));
|
||||
|
||||
// Hausnummer (Pflichtfeld)
|
||||
houseNumber = new TextField("Hausnr.");
|
||||
houseNumber.setRequiredIndicatorVisible(true);
|
||||
houseNumber.addBlurListener(e -> validateField(houseNumber));
|
||||
|
||||
// Adresszusatz (optional)
|
||||
addressAddition = new TextField("Adresszusatz");
|
||||
@@ -97,10 +104,12 @@ public class AddCustomerView extends Main {
|
||||
// PLZ (Pflichtfeld)
|
||||
zip = new TextField("Postleitzahl");
|
||||
zip.setRequiredIndicatorVisible(true);
|
||||
zip.addBlurListener(e -> validateField(zip));
|
||||
|
||||
// Ort (Pflichtfeld)
|
||||
city = new TextField("Ort");
|
||||
city.setRequiredIndicatorVisible(true);
|
||||
city.addBlurListener(e -> validateField(city));
|
||||
|
||||
// Binder-Konfiguration
|
||||
configureBinder();
|
||||
@@ -185,21 +194,19 @@ public class AddCustomerView extends Main {
|
||||
}
|
||||
|
||||
private void setTestData() {
|
||||
companyName.setValue("Mustermann Transport GmbH");
|
||||
title.setValue("Herr");
|
||||
firstName.setValue("Max");
|
||||
lastName.setValue("Mustermann");
|
||||
telephone.setValue("+49 40 123456789");
|
||||
fax.setValue("+49 40 123456790");
|
||||
mail.setValue("max.mustermann@mustermann-transport.de");
|
||||
street.setValue("Musterstraße");
|
||||
houseNumber.setValue("123");
|
||||
addressAddition.setValue("2. OG");
|
||||
zip.setValue("20095");
|
||||
city.setValue("Hamburg");
|
||||
// No default values - all fields start empty
|
||||
}
|
||||
|
||||
private void submit() {
|
||||
// First validate all fields
|
||||
boolean isValid = validateAllFields();
|
||||
|
||||
if (!isValid) {
|
||||
com.vaadin.flow.component.notification.Notification.show("Bitte füllen Sie alle Pflichtfelder aus", 3000,
|
||||
com.vaadin.flow.component.notification.Notification.Position.TOP_CENTER);
|
||||
return;
|
||||
}
|
||||
|
||||
try {
|
||||
Customer customer = new Customer();
|
||||
binder.writeBean(customer);
|
||||
@@ -220,4 +227,45 @@ public class AddCustomerView extends Main {
|
||||
com.vaadin.flow.component.notification.Notification.Position.TOP_CENTER);
|
||||
}
|
||||
}
|
||||
|
||||
private void validateField(TextField field) {
|
||||
String value = field.getValue();
|
||||
if (value == null || value.trim().isEmpty()) {
|
||||
field.setInvalid(true);
|
||||
field.setErrorMessage("Dieses Feld ist ein Pflichtfeld");
|
||||
} else {
|
||||
field.setInvalid(false);
|
||||
field.setErrorMessage("");
|
||||
}
|
||||
}
|
||||
|
||||
private void validateEmail() {
|
||||
String value = mail.getValue();
|
||||
if (value == null || value.trim().isEmpty()) {
|
||||
mail.setInvalid(true);
|
||||
mail.setErrorMessage("E-Mail-Adresse ist ein Pflichtfeld");
|
||||
} else if (!value.contains("@")) {
|
||||
mail.setInvalid(true);
|
||||
mail.setErrorMessage("Bitte geben Sie eine gültige E-Mail-Adresse ein");
|
||||
} else {
|
||||
mail.setInvalid(false);
|
||||
mail.setErrorMessage("");
|
||||
}
|
||||
}
|
||||
|
||||
private boolean validateAllFields() {
|
||||
validateField(companyName);
|
||||
validateField(firstName);
|
||||
validateField(lastName);
|
||||
validateField(telephone);
|
||||
validateField(street);
|
||||
validateField(houseNumber);
|
||||
validateField(zip);
|
||||
validateField(city);
|
||||
validateEmail();
|
||||
|
||||
return !companyName.isInvalid() && !firstName.isInvalid() && !lastName.isInvalid()
|
||||
&& !telephone.isInvalid() && !mail.isInvalid() && !street.isInvalid()
|
||||
&& !houseNumber.isInvalid() && !zip.isInvalid() && !city.isInvalid();
|
||||
}
|
||||
}
|
||||
|
||||
@@ -48,6 +48,7 @@ import de.assecutor.votianlt.pages.service.AppUserService;
|
||||
import de.assecutor.votianlt.model.AppUser;
|
||||
import de.assecutor.votianlt.pages.service.TaskTemplateService;
|
||||
import de.assecutor.votianlt.model.TaskTemplate;
|
||||
import de.assecutor.votianlt.model.User;
|
||||
import de.assecutor.votianlt.security.SecurityService;
|
||||
|
||||
import jakarta.annotation.security.RolesAllowed;
|
||||
@@ -331,9 +332,15 @@ public class AddJobView extends Main {
|
||||
saveDeliveryAddress = new Checkbox("Die Adresse für zukünftige Aufträge speichern.");
|
||||
saveDeliveryAddress.setValue(true);
|
||||
|
||||
// Digital processing
|
||||
// Digital processing - set value based on user's profile setting
|
||||
digitalProcessing = new Checkbox("Digitale Abwicklung per App");
|
||||
digitalProcessing.setValue(true);
|
||||
// Get current user's digital processing preference from profile
|
||||
try {
|
||||
User currentUser = securityService.getCurrentDatabaseUser();
|
||||
digitalProcessing.setValue(currentUser.isDigitalProcessingEnabled());
|
||||
} catch (Exception e) {
|
||||
digitalProcessing.setValue(true); // Default to true if user not found
|
||||
}
|
||||
appUser = new ComboBox<>("App-Nutzer");
|
||||
|
||||
// Load app users for current user and set up the ComboBox
|
||||
@@ -1224,25 +1231,31 @@ public class AddJobView extends Main {
|
||||
desc.setAllowCustomValue(true);
|
||||
desc.setPlaceholder("Wählen Sie eine Option oder geben Sie eigenen Text ein...");
|
||||
desc.setWidth("40%");
|
||||
desc.setRequiredIndicatorVisible(true);
|
||||
|
||||
IntegerField qty = new IntegerField("Anzahl");
|
||||
qty.setMin(1);
|
||||
qty.setValue(1);
|
||||
qty.setWidth("10%");
|
||||
qty.setRequiredIndicatorVisible(true);
|
||||
|
||||
NumberField weight = new NumberField("Gewicht");
|
||||
weight.setSuffixComponent(new Span("kg"));
|
||||
weight.setWidth("15%");
|
||||
weight.setRequiredIndicatorVisible(true);
|
||||
|
||||
NumberField len = new NumberField("Länge");
|
||||
len.setSuffixComponent(new Span("mm"));
|
||||
len.setWidth("12%");
|
||||
len.setRequiredIndicatorVisible(true);
|
||||
NumberField wid = new NumberField("Breite");
|
||||
wid.setSuffixComponent(new Span("mm"));
|
||||
wid.setWidth("12%");
|
||||
wid.setRequiredIndicatorVisible(true);
|
||||
NumberField hei = new NumberField("Höhe");
|
||||
hei.setSuffixComponent(new Span("mm"));
|
||||
hei.setWidth("12%");
|
||||
hei.setRequiredIndicatorVisible(true);
|
||||
|
||||
Button remove = new Button(new Icon(VaadinIcon.CLOSE_SMALL));
|
||||
remove.addThemeVariants(ButtonVariant.LUMO_ERROR, ButtonVariant.LUMO_TERTIARY);
|
||||
@@ -1270,31 +1283,59 @@ public class AddJobView extends Main {
|
||||
item.setWidthMm(wid.getValue());
|
||||
item.setHeightMm(hei.getValue());
|
||||
|
||||
// Validation helper to update field styling
|
||||
java.util.function.Consumer<com.vaadin.flow.component.HasValue<?, ?>> validateField = field -> {
|
||||
if (field instanceof ComboBox) {
|
||||
ComboBox<?> combo = (ComboBox<?>) field;
|
||||
String value = combo.getValue() != null ? combo.getValue().toString() : "";
|
||||
combo.setInvalid(value.trim().isEmpty());
|
||||
} else if (field instanceof NumberField) {
|
||||
NumberField numField = (NumberField) field;
|
||||
numField.setInvalid(numField.getValue() == null || numField.getValue() <= 0);
|
||||
} else if (field instanceof IntegerField) {
|
||||
IntegerField intField = (IntegerField) field;
|
||||
intField.setInvalid(intField.getValue() == null || intField.getValue() <= 0);
|
||||
}
|
||||
};
|
||||
|
||||
desc.addValueChangeListener(ev -> {
|
||||
item.setDescription(ev.getValue());
|
||||
validateField.accept(desc);
|
||||
updateTabLabels(); // Update tab validation when cargo description changes
|
||||
});
|
||||
qty.addValueChangeListener(ev -> {
|
||||
item.setQuantity(ev.getValue());
|
||||
validateField.accept(qty);
|
||||
updateTabLabels(); // Update tab validation when cargo quantity changes
|
||||
});
|
||||
weight.addValueChangeListener(ev -> {
|
||||
item.setWeightKg(ev.getValue());
|
||||
validateField.accept(weight);
|
||||
updateTabLabels(); // Update tab validation when cargo weight changes
|
||||
});
|
||||
len.addValueChangeListener(ev -> {
|
||||
item.setLengthMm(ev.getValue());
|
||||
validateField.accept(len);
|
||||
updateTabLabels(); // Update tab validation when cargo length changes
|
||||
});
|
||||
wid.addValueChangeListener(ev -> {
|
||||
item.setWidthMm(ev.getValue());
|
||||
validateField.accept(wid);
|
||||
updateTabLabels(); // Update tab validation when cargo width changes
|
||||
});
|
||||
hei.addValueChangeListener(ev -> {
|
||||
item.setHeightMm(ev.getValue());
|
||||
validateField.accept(hei);
|
||||
updateTabLabels(); // Update tab validation when cargo height changes
|
||||
});
|
||||
|
||||
// Initial validation
|
||||
validateField.accept(desc);
|
||||
validateField.accept(weight);
|
||||
validateField.accept(len);
|
||||
validateField.accept(wid);
|
||||
validateField.accept(hei);
|
||||
|
||||
if (afterCreate != null)
|
||||
afterCreate.accept(row);
|
||||
};
|
||||
|
||||
@@ -2,7 +2,7 @@ package de.assecutor.votianlt.pages.view;
|
||||
|
||||
import com.vaadin.flow.component.button.Button;
|
||||
import com.vaadin.flow.component.button.ButtonVariant;
|
||||
import com.vaadin.flow.component.combobox.ComboBox;
|
||||
import com.vaadin.flow.component.html.Span;
|
||||
import com.vaadin.flow.component.confirmdialog.ConfirmDialog;
|
||||
import com.vaadin.flow.component.formlayout.FormLayout;
|
||||
import com.vaadin.flow.component.html.H2;
|
||||
@@ -34,7 +34,7 @@ public class EditAppDeviceView extends VerticalLayout implements HasUrlParameter
|
||||
|
||||
// Formularfelder
|
||||
private final TextField nameField;
|
||||
private final ComboBox<AppUser> appUserComboBox;
|
||||
private final Span appUserDisplay;
|
||||
|
||||
// Aktuelles Endgerät
|
||||
private AppDevice currentAppDevice;
|
||||
@@ -53,20 +53,15 @@ public class EditAppDeviceView extends VerticalLayout implements HasUrlParameter
|
||||
nameField.setPlaceholder("z.B. iPhone 15, Samsung Galaxy S24");
|
||||
nameField.setWidth("100%");
|
||||
|
||||
// AppUser ComboBox
|
||||
appUserComboBox = new ComboBox<>("App-Nutzer zuordnen");
|
||||
appUserComboBox.setPlaceholder("App-Nutzer auswählen (optional)");
|
||||
appUserComboBox.setWidth("100%");
|
||||
appUserComboBox.setItemLabelGenerator(
|
||||
appUser -> appUser.getVorname() + " " + appUser.getNachname() + " (" + appUser.getEmail() + ")");
|
||||
|
||||
// Lade verfügbare App-Nutzer
|
||||
try {
|
||||
appUserComboBox.setItems(appUserService.findByCurrentUser());
|
||||
} catch (Exception e) {
|
||||
Notification.show("Fehler beim Laden der App-Nutzer: " + e.getMessage(), 3000,
|
||||
Notification.Position.MIDDLE);
|
||||
}
|
||||
// App-Nutzer Anzeige (nur lesend)
|
||||
appUserDisplay = new Span();
|
||||
appUserDisplay.getStyle().set("font-weight", "bold")
|
||||
.set("padding", "var(--lumo-space-s)")
|
||||
.set("border", "1px solid var(--lumo-contrast-20pct)")
|
||||
.set("border-radius", "var(--lumo-border-radius-m)")
|
||||
.set("background-color", "var(--lumo-contrast-5pct)")
|
||||
.set("display", "block")
|
||||
.set("width", "100%");
|
||||
|
||||
// Layout konfigurieren
|
||||
setSizeFull();
|
||||
@@ -96,7 +91,15 @@ public class EditAppDeviceView extends VerticalLayout implements HasUrlParameter
|
||||
// Formular
|
||||
FormLayout formLayout = new FormLayout();
|
||||
formLayout.setResponsiveSteps(new FormLayout.ResponsiveStep("0", 1));
|
||||
formLayout.add(nameField, appUserComboBox);
|
||||
// Label für App-Nutzer
|
||||
Span appUserLabel = new Span("Zugeordneter App-Nutzer:");
|
||||
appUserLabel.getStyle().set("font-weight", "500")
|
||||
.set("color", "var(--lumo-secondary-text-color)")
|
||||
.set("font-size", "var(--lumo-font-size-s)");
|
||||
|
||||
formLayout.add(nameField);
|
||||
formLayout.add(appUserLabel);
|
||||
formLayout.add(appUserDisplay);
|
||||
contentContainer.add(formLayout);
|
||||
|
||||
// Buttons
|
||||
@@ -142,6 +145,9 @@ public class EditAppDeviceView extends VerticalLayout implements HasUrlParameter
|
||||
if (currentAppDevice != null) {
|
||||
// Formular mit aktuellen Daten füllen
|
||||
binder.readBean(currentAppDevice);
|
||||
|
||||
// App-Nutzer Anzeige aktualisieren
|
||||
updateAppUserDisplay();
|
||||
} else {
|
||||
Notification.show("Endgerät nicht gefunden", 3000, Notification.Position.MIDDLE);
|
||||
navigateBack();
|
||||
@@ -151,20 +157,35 @@ public class EditAppDeviceView extends VerticalLayout implements HasUrlParameter
|
||||
private void setupBinder() {
|
||||
binder.forField(nameField).asRequired("Gerätename ist erforderlich").bind(AppDevice::getName,
|
||||
AppDevice::setName);
|
||||
}
|
||||
|
||||
binder.forField(appUserComboBox).bind(appDevice -> {
|
||||
if (appDevice.getAppUserId() != null) {
|
||||
return appUserService.findByCurrentUser().stream()
|
||||
.filter(user -> user.getId().equals(appDevice.getAppUserId())).findFirst().orElse(null);
|
||||
}
|
||||
return null;
|
||||
}, (appDevice, appUser) -> {
|
||||
if (appUser != null) {
|
||||
appDevice.setAppUserId(appUser.getId());
|
||||
private void updateAppUserDisplay() {
|
||||
if (currentAppDevice != null && currentAppDevice.getAppUserId() != null) {
|
||||
try {
|
||||
// Finde den zugeordneten App-Nutzer
|
||||
AppUser assignedUser = appUserService.findByCurrentUser().stream()
|
||||
.filter(user -> user.getId().equals(currentAppDevice.getAppUserId()))
|
||||
.findFirst()
|
||||
.orElse(null);
|
||||
|
||||
if (assignedUser != null) {
|
||||
String displayText = assignedUser.getVorname() + " " + assignedUser.getNachname() +
|
||||
" (" + assignedUser.getEmail() + ")";
|
||||
appUserDisplay.setText(displayText);
|
||||
appUserDisplay.getStyle().set("color", "var(--lumo-body-text-color)");
|
||||
} else {
|
||||
appDevice.setAppUserId(null);
|
||||
appUserDisplay.setText("App-Nutzer nicht gefunden (ID: " + currentAppDevice.getAppUserId() + ")");
|
||||
appUserDisplay.getStyle().set("color", "var(--lumo-error-text-color)");
|
||||
}
|
||||
} catch (Exception e) {
|
||||
appUserDisplay.setText("Fehler beim Laden des App-Nutzers");
|
||||
appUserDisplay.getStyle().set("color", "var(--lumo-error-text-color)");
|
||||
}
|
||||
} else {
|
||||
appUserDisplay.setText("Kein App-Nutzer zugeordnet");
|
||||
appUserDisplay.getStyle().set("color", "var(--lumo-secondary-text-color)");
|
||||
appUserDisplay.getStyle().set("font-style", "italic");
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
private void saveAppDevice() {
|
||||
|
||||
@@ -94,18 +94,38 @@ public class EditProfileView extends HorizontalLayout {
|
||||
|
||||
// Firmenfelder
|
||||
TextField companyField = new TextField("Firma");
|
||||
companyField.addBlurListener(e -> validateField(companyField, "Firma ist ein Pflichtfeld"));
|
||||
|
||||
TextField companyAddField = new TextField("Firmenzusatz");
|
||||
|
||||
TextField firstnameField = new TextField("Vorname");
|
||||
firstnameField.addBlurListener(e -> validateField(firstnameField, "Vorname ist ein Pflichtfeld"));
|
||||
|
||||
TextField lastnameField = new TextField("Nachname");
|
||||
lastnameField.addBlurListener(e -> validateField(lastnameField, "Nachname ist ein Pflichtfeld"));
|
||||
|
||||
TextField phoneField = new TextField("Telefonnummer");
|
||||
phoneField.addBlurListener(e -> validateField(phoneField, "Telefonnummer ist ein Pflichtfeld"));
|
||||
|
||||
TextField faxField = new TextField("Telefon (Fax)");
|
||||
TextField mobileField = new TextField("Telefon (Mobil)");
|
||||
|
||||
EmailField emailField = new EmailField("E-Mail-Adresse (Login)*");
|
||||
emailField.addBlurListener(e -> validateEmailField(emailField));
|
||||
|
||||
TextField streetField = new TextField("Straße");
|
||||
streetField.addBlurListener(e -> validateField(streetField, "Straße ist ein Pflichtfeld"));
|
||||
|
||||
TextField houseNumberField = new TextField("Hausnr");
|
||||
houseNumberField.addBlurListener(e -> validateField(houseNumberField, "Hausnummer ist ein Pflichtfeld"));
|
||||
|
||||
TextField addressAddField = new TextField("Adresszusatz");
|
||||
|
||||
TextField zipField = new TextField("Postleitzahl");
|
||||
zipField.addBlurListener(e -> validateField(zipField, "Postleitzahl ist ein Pflichtfeld"));
|
||||
|
||||
TextField cityField = new TextField("Stadt");
|
||||
cityField.addBlurListener(e -> validateField(cityField, "Stadt ist ein Pflichtfeld"));
|
||||
|
||||
// Abweichende Rechnungsadresse
|
||||
Checkbox diffInvoiceAddress = new Checkbox("Abweichende Rechnungsadresse");
|
||||
@@ -337,9 +357,33 @@ public class EditProfileView extends HorizontalLayout {
|
||||
VerticalLayout switches = new VerticalLayout();
|
||||
switches.setPadding(false);
|
||||
switches.setSpacing(true);
|
||||
|
||||
Checkbox digitalProcess = new Checkbox("Digitale Abwicklung per App");
|
||||
digitalProcess.setValue(currentUser.isDigitalProcessingEnabled());
|
||||
|
||||
Span digitalProcessInfo = new Span("Aktiviert die digitale Auftragsabwicklung über die mobile App");
|
||||
digitalProcessInfo.getStyle().set("font-size", "var(--lumo-font-size-s)")
|
||||
.set("color", "var(--lumo-secondary-text-color)")
|
||||
.set("margin-left", "var(--lumo-space-xl)");
|
||||
|
||||
Checkbox locateAppUser = new Checkbox("App-Nutzer orten");
|
||||
Checkbox digitalProcess = new Checkbox("Digitale Abwicklung");
|
||||
switches.add(locateAppUser, digitalProcess);
|
||||
locateAppUser.setValue(currentUser.isLocationTrackingEnabled());
|
||||
|
||||
Span locateAppUserInfo = new Span("Ermöglicht die Ortung von App-Nutzern während der Auftragsausführung");
|
||||
locateAppUserInfo.getStyle().set("font-size", "var(--lumo-font-size-s)")
|
||||
.set("color", "var(--lumo-secondary-text-color)")
|
||||
.set("margin-left", "var(--lumo-space-xl)");
|
||||
|
||||
// Save checkbox states when changed
|
||||
digitalProcess.addValueChangeListener(e -> {
|
||||
currentUser.setDigitalProcessingEnabled(e.getValue());
|
||||
});
|
||||
|
||||
locateAppUser.addValueChangeListener(e -> {
|
||||
currentUser.setLocationTrackingEnabled(e.getValue());
|
||||
});
|
||||
|
||||
switches.add(digitalProcess, digitalProcessInfo, locateAppUser, locateAppUserInfo);
|
||||
tabSheet.add("Einstellungen", switches);
|
||||
|
||||
// Sicherheit-Tab (2FA, Passwort, Konto)
|
||||
@@ -371,6 +415,15 @@ public class EditProfileView extends HorizontalLayout {
|
||||
Button saveProfile = new Button("Profiländerungen speichern");
|
||||
saveProfile.addThemeVariants(ButtonVariant.LUMO_PRIMARY);
|
||||
saveProfile.addClickListener(e -> {
|
||||
// Validate all required fields first
|
||||
boolean isValid = validateAllProfileFields(companyField, firstnameField, lastnameField, phoneField,
|
||||
emailField, streetField, houseNumberField, zipField, cityField);
|
||||
|
||||
if (!isValid) {
|
||||
Notification.show("Bitte füllen Sie alle Pflichtfelder korrekt aus", 3000, Notification.Position.MIDDLE);
|
||||
return;
|
||||
}
|
||||
|
||||
if (binder.validate().isOk()) {
|
||||
try {
|
||||
// Check if billing status changed
|
||||
@@ -620,4 +673,47 @@ public class EditProfileView extends HorizontalLayout {
|
||||
return value != null ? value : "";
|
||||
}
|
||||
|
||||
private void validateField(TextField field, String errorMessage) {
|
||||
String value = field.getValue();
|
||||
if (value == null || value.trim().isEmpty()) {
|
||||
field.setInvalid(true);
|
||||
field.setErrorMessage(errorMessage);
|
||||
} else {
|
||||
field.setInvalid(false);
|
||||
field.setErrorMessage("");
|
||||
}
|
||||
}
|
||||
|
||||
private void validateEmailField(EmailField emailField) {
|
||||
String value = emailField.getValue();
|
||||
if (value == null || value.trim().isEmpty()) {
|
||||
emailField.setInvalid(true);
|
||||
emailField.setErrorMessage("E-Mail-Adresse ist ein Pflichtfeld");
|
||||
} else if (!value.contains("@") || !value.contains(".")) {
|
||||
emailField.setInvalid(true);
|
||||
emailField.setErrorMessage("Bitte geben Sie eine gültige E-Mail-Adresse ein");
|
||||
} else {
|
||||
emailField.setInvalid(false);
|
||||
emailField.setErrorMessage("");
|
||||
}
|
||||
}
|
||||
|
||||
private boolean validateAllProfileFields(TextField companyField, TextField firstnameField, TextField lastnameField,
|
||||
TextField phoneField, EmailField emailField, TextField streetField,
|
||||
TextField houseNumberField, TextField zipField, TextField cityField) {
|
||||
validateField(companyField, "Firma ist ein Pflichtfeld");
|
||||
validateField(firstnameField, "Vorname ist ein Pflichtfeld");
|
||||
validateField(lastnameField, "Nachname ist ein Pflichtfeld");
|
||||
validateField(phoneField, "Telefonnummer ist ein Pflichtfeld");
|
||||
validateEmailField(emailField);
|
||||
validateField(streetField, "Straße ist ein Pflichtfeld");
|
||||
validateField(houseNumberField, "Hausnummer ist ein Pflichtfeld");
|
||||
validateField(zipField, "Postleitzahl ist ein Pflichtfeld");
|
||||
validateField(cityField, "Stadt ist ein Pflichtfeld");
|
||||
|
||||
return !companyField.isInvalid() && !firstnameField.isInvalid() && !lastnameField.isInvalid()
|
||||
&& !phoneField.isInvalid() && !emailField.isInvalid() && !streetField.isInvalid()
|
||||
&& !houseNumberField.isInvalid() && !zipField.isInvalid() && !cityField.isInvalid();
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user