Erweiterungen

This commit is contained in:
Sven committed 2026-02-25 10:40:29 +01:00
1 parent 955d7b3cb4
commit e9811da904
25 files changed
+1505 -128

No files matched your search

+4 -3
View File
@@ -9,6 +9,7 @@ import '../main.dart';
import '../model/job.dart';
import '../objectbox.g.dart';
import '../popups/files_popup.dart';
import '../tools/app_localizations.dart';
import '../tools/constants.dart';
import '../tools/util.dart';
@@ -237,11 +238,11 @@ class _HeaderWidgetState extends State<_HeaderWidget> with ProducerMixin {
SizedBox(
height: 100,
width: cellWidth * 2,
child: const Center(
child: Center(
child: Text(
textAlign: TextAlign.center,
"Angenommene Aufträge",
style: TextStyle(
'accepted_jobs'.tr,
style: const TextStyle(
fontWeight: FontWeight.bold,
fontSize: 18,
color: Colors.white),
+3 -2
View File
@@ -10,6 +10,7 @@ import 'package:stadtbote/tools/constants.dart';
import 'package:stadtbote/tools/messages/publish_payload_message.dart';
import 'package:badges/badges.dart' as badges;
import '../tools/app_localizations.dart';
import '../tools/util.dart';
class ApproachAreaPage extends ContentViewWidget {
@@ -101,8 +102,8 @@ class _ApproachAreaPageState extends State<ApproachAreaPage>
{
showZipPopup(
context,
'ACHTUNG: Wenn Sie Ihre PLZ ändern, verlieren Sie Ihr Ranking!\n',
'Freimelden',
'zip_change_warning'.tr,
'release'.tr,
(zip) => {_sendZip(rank, zip)}),
}
},
+14 -13
View File
@@ -18,6 +18,7 @@ import 'package:stadtbote/tools/messages/remove_state_0_job_from_map.dart';
import '../main.dart';
import '../model/job.dart';
import '../popups/files_popup.dart';
import '../tools/app_localizations.dart';
import '../tools/constants.dart';
import '../tools/util.dart';
@@ -124,9 +125,9 @@ class _AssignedJobsPageState extends State<AssignedJobsPage> with ProducerMixin,
child: badges.Badge(
position: badges.BadgePosition.topEnd(top: -13, end: -5),
showBadge: true,
badgeContent: const Text(
'Neu',
style: TextStyle(
badgeContent: Text(
'new'.tr,
style: const TextStyle(
color: Colors.white,
fontSize: 18.0,
),
@@ -159,7 +160,7 @@ class _AssignedJobsPageState extends State<AssignedJobsPage> with ProducerMixin,
),
],
),
Text('Auftragsnummer: ${job.externalId}'),
Text('${'order_number'.tr}: ${job.externalId}'),
Text(job.tours[0].comp),
Text(job.tours[0].street),
Text(job.tours[0].city),
@@ -173,11 +174,11 @@ class _AssignedJobsPageState extends State<AssignedJobsPage> with ProducerMixin,
headerAlignment: ExpandablePanelHeaderAlignment.center,
tapBodyToCollapse: true,
),
header: const Padding(
padding: EdgeInsets.all(0),
header: Padding(
padding: const EdgeInsets.all(0),
child: Text(
"Weitere Infos....",
style: TextStyle(fontSize: 15, color: Colors.black, fontWeight: FontWeight.bold),
'more_info'.tr,
style: const TextStyle(fontSize: 15, color: Colors.black, fontWeight: FontWeight.bold),
)),
collapsed: const SizedBox(),
expanded: Column(
@@ -202,7 +203,7 @@ class _AssignedJobsPageState extends State<AssignedJobsPage> with ProducerMixin,
const SizedBox(height: 20),
Row(children: [
Expanded(
child: getDefaultButton(!job.global ? 'Ablehnen' : 'Ignorieren', () {
child: getDefaultButton(!job.global ? 'decline'.tr : 'ignore'.tr, () {
sendMessage(
routingKey: Constants.messageTopicRemoveJob,
payload: RemoveJobMessage(id: job.externalId),
@@ -217,7 +218,7 @@ class _AssignedJobsPageState extends State<AssignedJobsPage> with ProducerMixin,
),
const SizedBox(width: 20),
Expanded(
child: getDefaultButton('Annehmen', () {
child: getDefaultButton('accept'.tr, () {
sendMessage(
routingKey: Constants.messageTopicRemoveJob,
payload: RemoveJobMessage(id: job.externalId),
@@ -380,11 +381,11 @@ class _HeaderWidgetState extends State<_HeaderWidget> with ProducerMixin {
SizedBox(
height: 100,
width: cellWidth * 2,
child: const Center(
child: Center(
child: Text(
textAlign: TextAlign.center,
"Zugewiesene Aufträge",
style: TextStyle(fontWeight: FontWeight.bold, fontSize: 18, color: Colors.white),
'assigned_jobs'.tr,
style: const TextStyle(fontWeight: FontWeight.bold, fontSize: 18, color: Colors.white),
),
),
),
+4 -3
View File
@@ -9,6 +9,7 @@ import 'package:stadtbote/messages/pop_content_view_message.dart';
import '../main.dart';
import '../model/job.dart';
import '../popups/files_popup.dart';
import '../tools/app_localizations.dart';
import '../tools/constants.dart';
import '../tools/util.dart';
@@ -226,11 +227,11 @@ class _HeaderWidgetState extends State<_HeaderWidget> with ProducerMixin {
SizedBox(
height: 100,
width: cellWidth * 2,
child: const Center(
child: Center(
child: Text(
textAlign: TextAlign.center,
"Erledigte Aufträge",
style: TextStyle(
'finished_jobs'.tr,
style: const TextStyle(
fontWeight: FontWeight.bold,
fontSize: 18,
color: Colors.white),
+22 -21
View File
@@ -15,6 +15,7 @@ import 'package:stadtbote/model/chat_message.dart';
import 'package:stadtbote/model/session_status.dart';
import 'package:stadtbote/network_messages/logout_message.dart';
import 'package:stadtbote/popups/infos_popup.dart';
import 'package:stadtbote/tools/app_localizations.dart';
import 'package:stadtbote/tools/constants.dart';
import 'package:stadtbote/tools/messages/job_received_message.dart';
import 'package:stadtbote/tools/messages/publish_payload_message.dart';
@@ -104,7 +105,7 @@ class _MainPageState extends State<MainPage> with ConsumerMixin, ProducerMixin {
elevation: 0,
),
child: getDefaultButton(
'Zugewiesene Aufträge',
'assigned_jobs'.tr,
image: Image.asset('assets/zugewiesene_auftraege.png',
width: 30, height: 30),
() async => {
@@ -144,7 +145,7 @@ class _MainPageState extends State<MainPage> with ConsumerMixin, ProducerMixin {
elevation: 0,
),
child: getDefaultButton(
'Angenommene Aufträge',
'accepted_jobs'.tr,
image: Image.asset(
'assets/angenommene_auftraege.png',
width: 30,
@@ -163,7 +164,7 @@ class _MainPageState extends State<MainPage> with ConsumerMixin, ProducerMixin {
Visibility(
visible: !_loggedOut,
child: getDefaultButton(
'Erledigte Aufträge',
'finished_jobs'.tr,
image: Image.asset('assets/erledigte_auftraege.png',
width: 30, height: 30),
() async => {
@@ -199,7 +200,7 @@ class _MainPageState extends State<MainPage> with ConsumerMixin, ProducerMixin {
elevation: 0,
),
child: getDefaultButton(
'Nachrichten',
'messages'.tr,
image: Image.asset('assets/nachrichten.png',
width: 30, height: 30),
() async => {
@@ -216,7 +217,7 @@ class _MainPageState extends State<MainPage> with ConsumerMixin, ProducerMixin {
Visibility(
visible: !_loggedOut,
child: getDefaultButton(
'Anfahrtsbereich',
'approach_area'.tr,
image: Image.asset('assets/anfahrtsbereich.png',
width: 30, height: 30),
() async => {
@@ -230,7 +231,7 @@ class _MainPageState extends State<MainPage> with ConsumerMixin, ProducerMixin {
Visibility(
visible: !_loggedOut && _showBWVButton,
child: getDefaultButton(
'Wunschziel für heute',
'desired_zip'.tr,
image: Image.asset('assets/wunsch_plz.png',
width: 30, height: 30),
() async => {
@@ -241,7 +242,7 @@ class _MainPageState extends State<MainPage> with ConsumerMixin, ProducerMixin {
}),
),
SizedBox(height: _loggedOut == true ? 0 : 20),
getDefaultButton(_loggedOut ? 'Anmelden' : 'Abmelden',
getDefaultButton(_loggedOut ? 'login'.tr : 'logout'.tr,
image: Image.asset(
_loggedOut
? 'assets/anmelden.png'
@@ -360,12 +361,12 @@ class _MainPageState extends State<MainPage> with ConsumerMixin, ProducerMixin {
showLogoutAlertDialog(BuildContext context) async {
Widget yesButton = TextButton(
child: const Text("Ja"),
child: Text('yes'.tr),
onPressed: () async {
Navigator.of(context).pop();
showMessageDialog(
context, "Information", "Sie werden abgemeldet.\nBitte warten...");
context, 'information'.tr, 'logging_out'.tr);
_sendLogoutMessage();
@@ -394,7 +395,7 @@ class _MainPageState extends State<MainPage> with ConsumerMixin, ProducerMixin {
);
Widget noButton = TextButton(
child: const Text("Nein"),
child: Text('no'.tr),
onPressed: () {
Navigator.of(context).pop();
},
@@ -402,8 +403,8 @@ class _MainPageState extends State<MainPage> with ConsumerMixin, ProducerMixin {
// set up the AlertDialog
AlertDialog alert = AlertDialog(
title: const Text("Warnung"),
content: const Text("Wollen Sie sich wirklich abmelden?"),
title: Text('warning'.tr),
content: Text('logout_confirm'.tr),
actions: [
yesButton,
noButton,
@@ -547,18 +548,18 @@ class _HeaderWidgetState extends State<_HeaderWidget> with ConsumerMixin {
children: <Widget>[
SizedBox(
width: cellWidth,
child: const Text(
'Meldung',
child: Text(
'message'.tr,
textAlign: TextAlign.center,
style: TextStyle(fontSize: 11, color: Colors.white),
style: const TextStyle(fontSize: 11, color: Colors.white),
),
),
SizedBox(
width: cellWidth,
child: const Text(
'Ortung',
child: Text(
'location'.tr,
textAlign: TextAlign.center,
style: TextStyle(fontSize: 11, color: Colors.white),
style: const TextStyle(fontSize: 11, color: Colors.white),
),
),
],
@@ -602,10 +603,10 @@ class _HeaderWidgetState extends State<_HeaderWidget> with ConsumerMixin {
),
Column(
children: [
const Text(
'Kurierkennung',
Text(
'courier_id'.tr,
textAlign: TextAlign.center,
style: TextStyle(fontSize: 11, color: Colors.white),
style: const TextStyle(fontSize: 11, color: Colors.white),
),
ValueListenableBuilder<String>(
valueListenable: _sidValueNotifier,
+5 -4
View File
@@ -12,6 +12,7 @@ import 'package:stadtbote/network_messages/messages_showed.dart';
import 'package:stadtbote/tools/constants.dart';
import 'package:stadtbote/tools/messages/publish_payload_message.dart';
import '../tools/app_localizations.dart';
import '../tools/util.dart';
class MessagesPage extends ContentViewWidget {
@@ -51,7 +52,7 @@ class _MessagesPageState extends State<MessagesPage> with ProducerMixin {
final box = MyApp.objectBoxStore.box<SessionStatus>();
final sessions = box.getAll();
var status = sessions.isNotEmpty ? sessions.first : null;
_sid = status != null ? status.sid : 'Unbekannt';
_sid = status != null ? status.sid : 'unknown'.tr;
_sendMessagesReadMessage();
@@ -165,17 +166,17 @@ class _MessagesPageState extends State<MessagesPage> with ProducerMixin {
padding: const EdgeInsets.all(5),
child: Column(
children: [
const Text('Soll die Nachricht gelöscht werden?'),
Text('delete_message_confirm'.tr),
const SizedBox(height: 20),
Row(children: [
Expanded(
child: getDefaultButton('Nein',
child: getDefaultButton('no'.tr,
() => {Navigator.of(context).pop()}),
),
const SizedBox(width: 20),
Expanded(
child: getDefaultButton(
'Ja',
'yes'.tr,
() async => {
MyApp.objectBoxStore.box<sbmessage.ChatMessage>()
.remove(int.parse(message.id)),
+5 -4
View File
@@ -6,6 +6,7 @@ import 'package:stadtbote/messages/pop_content_view_message.dart';
import 'package:stadtbote/network_messages/set_desired_zip_message.dart';
import 'package:stadtbote/tools/messages/publish_payload_message.dart';
import '../tools/app_localizations.dart';
import '../tools/constants.dart';
import '../tools/util.dart';
@@ -43,7 +44,7 @@ class _SetDesiredZipPageState extends State<SetDesiredZipPage>
return Padding(
padding: const EdgeInsets.all(8.0),
child: Column(children: [
const Text("Bitte geben Sie Ihr Wunschziel für heute ein"),
Text('enter_desired_zip'.tr),
const SizedBox(height: 20),
Row(
mainAxisAlignment:
@@ -67,7 +68,7 @@ class _SetDesiredZipPageState extends State<SetDesiredZipPage>
),
const SizedBox(height: 20),
getDefaultButton(
'Übernehmen',
'apply'.tr,
() => {
if (textEditController.text.isEmpty ||
textEditController.text.length == 5)
@@ -82,8 +83,8 @@ class _SetDesiredZipPageState extends State<SetDesiredZipPage>
}
else
{
showAlertDialog("Fehler",
"Das Feld muss leer sein, oder es müssen fünf Zahlen eingegeben werden")
showAlertDialog('error'.tr,
'zip_validation_error'.tr)
}
})
]),
+5 -4
View File
@@ -26,6 +26,7 @@ import 'package:stadtbote/tools/messages/publish_payload_message.dart';
import '../main.dart';
import '../model/task_info.dart';
import '../tools/app_localizations.dart';
import '../tools/util.dart';
class TaskListPage extends ContentViewWidget {
@@ -93,7 +94,7 @@ class _TaskListPageState extends State<TaskListPage> with ProducerMixin {
visible: _commisionNumber.isNotEmpty,
child: Row(
children: [
Text('Komm-#: $_commisionNumber', style: const TextStyle(fontSize: 20), textAlign: TextAlign.left),
Text('${'commission_number_short'.tr}: $_commisionNumber', style: const TextStyle(fontSize: 20), textAlign: TextAlign.left),
],
),
),
@@ -314,7 +315,7 @@ class _TaskListPageState extends State<TaskListPage> with ProducerMixin {
}
taskInfo.answer = jsonEncode(answer.toJson());
taskInfo.additionalText = "Barcodes gescannt";
taskInfo.additionalText = 'barcodes_scanned'.tr;
taskInfo.completed = true;
setState(() {});
@@ -349,7 +350,7 @@ class _TaskListPageState extends State<TaskListPage> with ProducerMixin {
box.put(picture);
}
taskInfo.additionalText = "Fotos aufgenommen";
taskInfo.additionalText = 'photos_taken'.tr;
taskInfo.completed = true;
if (mounted) {
@@ -446,7 +447,7 @@ class _TaskListPageState extends State<TaskListPage> with ProducerMixin {
answer.sign = signature;
taskInfo.answer = jsonEncode(answer.toJson());
taskInfo.additionalText = "Unterschrift erfasst";
taskInfo.additionalText = 'signature_captured'.tr;
taskInfo.completed = true;
_sendFinTourMessage();
+12 -11
View File
@@ -8,6 +8,7 @@ import 'package:stadtbote/model/job_tour.dart';
import '../model/job.dart';
import '../popups/files_popup.dart';
import '../popups/map_popup.dart';
import '../tools/app_localizations.dart';
import '../tools/constants.dart';
import '../tools/util.dart';
@@ -59,7 +60,7 @@ class _TourDetailsPageState extends State<TourDetailsPage> with ProducerMixin {
if (widget.tour.rem.isNotEmpty) {
remark += '${widget.tour.rem}\n';
} else {
remark = "* Keine Bemerkung vorhanden *";
remark = 'no_remark'.tr;
}
return Padding(
@@ -77,7 +78,7 @@ class _TourDetailsPageState extends State<TourDetailsPage> with ProducerMixin {
crossAxisAlignment: CrossAxisAlignment.stretch,
children: [
Text(
"${"Station ${widget.tour.sort}"} ${mapTourMode(widget.tour.mode)}",
"${'station'.tr} ${widget.tour.sort} ${mapTourMode(widget.tour.mode)}",
textAlign: TextAlign.left,
),
Text(
@@ -97,11 +98,11 @@ class _TourDetailsPageState extends State<TourDetailsPage> with ProducerMixin {
textAlign: TextAlign.left,
),
Text(
"Tel.: ${widget.tour.phone}",
"${'phone'.tr} ${widget.tour.phone}",
textAlign: TextAlign.left,
),
Text(
"Komm-#: ${widget.tour.com}",
"${'commission_number'.tr}: ${widget.tour.com}",
textAlign: TextAlign.left,
),
if (widget.tour.files != null && widget.tour.files!.isNotEmpty) ...[
@@ -110,9 +111,9 @@ class _TourDetailsPageState extends State<TourDetailsPage> with ProducerMixin {
children: [
FilesBadge(files: widget.tour.files),
const SizedBox(width: 8),
const Text(
'Dateien verfügbar',
style: TextStyle(
Text(
'files_available'.tr,
style: const TextStyle(
fontSize: 12,
color: Colors.grey,
),
@@ -122,7 +123,7 @@ class _TourDetailsPageState extends State<TourDetailsPage> with ProducerMixin {
],
const SizedBox(height: 10),
getDefaultButton(
'Karte',
'map'.tr,
() => {
if (widget.tour.pos != null)
{
@@ -131,8 +132,8 @@ class _TourDetailsPageState extends State<TourDetailsPage> with ProducerMixin {
}
else
{
showAlertDialog('Information',
'Es liegt keine Position für diese Station vor')
showAlertDialog('information'.tr,
'no_position'.tr)
}
}),
],
@@ -158,7 +159,7 @@ class _TourDetailsPageState extends State<TourDetailsPage> with ProducerMixin {
),
const SizedBox(height: 10),
getDefaultButton(
'Weiter',
'next'.tr,
() async => {
sendMessage(
routingKey: Constants.messageTopicPushContentView,
+3 -2
View File
@@ -8,6 +8,7 @@ import 'package:stadtbote/popups/map_popup.dart';
import '../model/job.dart';
import '../popups/files_popup.dart';
import '../tools/app_localizations.dart';
import '../tools/constants.dart';
import '../tools/util.dart';
@@ -102,7 +103,7 @@ class _TourListPageState extends State<TourListPage> with ProducerMixin {
foregroundColor: WidgetStateProperty.all<Color>(Colors.black),
),
onPressed: () => {showMapPopup(context, widget.job.tours[0], widget.job.tours)},
child: const Text("Karte")),
child: Text('map'.tr)),
))
],
),
@@ -157,7 +158,7 @@ class _TourListPageState extends State<TourListPage> with ProducerMixin {
children: [
Expanded(
child: Text(
"${"Station ${tour.sort}"} ${mapTourMode(tour.mode)}",
"${'station'.tr} ${tour.sort} ${mapTourMode(tour.mode)}",
textAlign: TextAlign.left,
),
),