diff --git a/lib/pages/print/print_controller.dart b/lib/pages/print/print_controller.dart index e5ea651..acecc3e 100644 --- a/lib/pages/print/print_controller.dart +++ b/lib/pages/print/print_controller.dart @@ -33,7 +33,11 @@ class PrintController extends GetxController { doc.addPage( pw.Page( - pageFormat: PdfPageFormat.a4, + pageFormat: PdfPageFormat.a4.copyWith( + marginBottom: 1.0 * PdfPageFormat.cm, + marginLeft: 1.0 * PdfPageFormat.cm, + marginRight: 1.0 * PdfPageFormat.cm, + marginTop: 1.0 * PdfPageFormat.cm), build: (pw.Context context) { return pw.Column( crossAxisAlignment: pw.CrossAxisAlignment.start, @@ -57,7 +61,42 @@ class PrintController extends GetxController { ...tankungenByMonth.entries.map((entry) { final monthName = entry.key; final monthlyData = entry.value; - return pw.Column( + + // Monatliche Summen berechnen + final double monthlyLiters = monthlyData.fold( + 0.0, (sum, item) => sum + double.parse(item.liters)); + final double monthlyPrice = monthlyData.fold( + 0.0, + (sum, item) => + sum + double.parse(item.szSummePreis ?? '0.0')); + final double monthlyAvrLiterPrice = + monthlyPrice / monthlyLiters; + // Monatlicher Abschnitt + // Erstelle die Datenzeilen + final List> tableData = monthlyData.map((item) { + var modDate = item.date.substring(5); + var modPreisPerLiter = item.pricePerLiter.padRight(5, '0'); + return [ + modDate, + item.location, + item.liters, + modPreisPerLiter, + item.szSummePreis ?? '0.0', + item.odometer + ]; + }).toList(); + var monthAvrPricePerLiter = monthlyAvrLiterPrice.toStringAsFixed(3); + // Füge die Summenzeile hinzu + tableData.add([ + 'Summe', + '', // Leere Zelle für Ort + (monthlyLiters.toStringAsFixed(2)), + '$monthAvrPricePerLiter Ø', // Leere Zelle für Preis/L + (monthlyPrice.toStringAsFixed(2)), + '' + ]); + + return pw.Column( crossAxisAlignment: pw.CrossAxisAlignment.start, children: [ // Monatsüberschrift @@ -71,31 +110,80 @@ class PrintController extends GetxController { ), pw.SizedBox(height: 10), // Tabelle für den jeweiligen Monat - pw.TableHelper.fromTextArray( - headers: [ - 'Datum', - 'Ort', - 'Menge (L)', - 'Preis/L (€)', - 'Summe (€)' - ], - cellAlignment: pw.Alignment.centerLeft, + // pw.TableHelper.fromTextArray( + // headers: [ + // 'Datum', + // 'Ort', + // 'Menge (L)', + // 'Preis/L (€)', + // 'Summe (€)', + // 'KM-Stand' + // ], + // cellAlignment: pw.Alignment.centerLeft, + // border: pw.TableBorder.all(color: PdfColors.grey200), + // headerStyle: pw.TextStyle( + // fontWeight: pw.FontWeight.bold, font: font), + // data: tableData, + // cellStyle: pw.TextStyle(font: font), + // ), + + // Manuelle Erstellung der Tabelle mit individueller Formatierung + pw.Table( border: pw.TableBorder.all(color: PdfColors.grey200), - headerStyle: pw.TextStyle( - fontWeight: pw.FontWeight.bold, font: font), - data: monthlyData.map((item) { - var modDate = item.date.substring(5); - var modPreisPerLiter = - item.pricePerLiter.padRight(5, '0'); - return [ - modDate, - item.location, - item.liters, - modPreisPerLiter, - item.szSummePreis ?? '0.0', - ]; - }).toList(), + columnWidths: { + 0: const pw.FlexColumnWidth(1.0), // Datum + 1: const pw.FlexColumnWidth(4.0), // Ort + 2: const pw.FlexColumnWidth(1.3), // Menge + 3: const pw.FlexColumnWidth(1.3), // Preis/L + 4: const pw.FlexColumnWidth(1.4), // Summe + 5: const pw.FlexColumnWidth(1.3), // KM-Stand + }, + children: [ + // Kopfzeile mit grauem Hintergrund + pw.TableRow( + decoration: + const pw.BoxDecoration(color: PdfColors.grey200), + children: [ + _buildHeaderCell('Datum', font), + _buildHeaderCell('Ort', font), + _buildHeaderCell('Menge(L)', font), + _buildHeaderCell('Preis/L(€)', font), + _buildHeaderCell('Summe(€)', font), + _buildHeaderCell('Km-Stand', font), + ], + ), + // Datenzeilen + ...monthlyData.map((item) { + var modDate = item.date.substring(5); + var modPreisPerLiter = + item.pricePerLiter.padRight(5, '0'); + return pw.TableRow( + children: [ + _buildDataCell(modDate, font), + _buildDataCell(item.location, font), + _buildDataCell(item.liters, font), + _buildDataCell(modPreisPerLiter, font), + _buildDataCell(item.szSummePreis!, font), + _buildDataCell(item.odometer, font), + ], + ); + }), + // Summenzeile mit ANDERER grauem Hintergrund + pw.TableRow( + decoration: + const pw.BoxDecoration(color: PdfColors.grey300), + children: [ + _buildDataCell('', font), + _buildDataCell('Gesamt Summe Monat', font), + _buildDataCell('${monthlyLiters.toStringAsFixed(2)} L', font), + _buildDataCell('$monthAvrPricePerLiter Ø', font), + _buildDataCell('${monthlyPrice.toStringAsFixed(2)} €', font), + _buildDataCell('', font) + ], + ), + ], ), + pw.SizedBox(height: 20), ], ); @@ -137,4 +225,27 @@ class PrintController extends GetxController { void goToTankListPage() async { await Get.offAndToNamed(TanklistPage.namedRoute); } + + // Hilfs-Widgets für die Zellen + pw.Widget _buildHeaderCell(String text, pw.Font font) { + return pw.Container( + alignment: pw.Alignment.centerLeft, + padding: const pw.EdgeInsets.symmetric(vertical: 5, horizontal: 8), + child: pw.Text( + text, + style: pw.TextStyle(fontWeight: pw.FontWeight.bold, font: font), + ), + ); + } + + pw.Widget _buildDataCell(String text, pw.Font font, {bool alignRight = false}) { + return pw.Container( + alignment: alignRight ? pw.Alignment.centerRight : pw.Alignment.centerLeft, + padding: const pw.EdgeInsets.symmetric(vertical: 5, horizontal: 8), + child: pw.Text( + text, + style: pw.TextStyle(font: font), + ), + ); + } }