flutter_application_1/lib/widgets/chart_widget.dart

234 lines
8.5 KiB
Dart

import 'package:flutter/cupertino.dart';
import 'package:flutter/material.dart';
import 'package:syncfusion_flutter_charts/charts.dart';
// Widget zur Erstellung eines gestapelten Säulendiagramms
class StackedColumnChart extends StatelessWidget {
final List<double> lowerValues; // Liste der unteren Werte für das Diagramm
final List<double> upperValues; // Liste der oberen Werte für das Diagramm
const StackedColumnChart({
super.key,
required this.lowerValues,
required this.upperValues,
});
@override
Widget build(BuildContext context) {
return SfCartesianChart(
legend: const Legend(
isVisible: true,
position: LegendPosition.top,
),
primaryXAxis: const CategoryAxis(
title: AxisTitle(text: 'Jahr'),
),
primaryYAxis: const NumericAxis(
title: AxisTitle(text: 'Euro'),
),
series: <CartesianSeries>[
// Serie für die Einzahlungen (untere Werte)
StackedColumnSeries<SalesData, int>(
dataSource: _getLowerChartData(),
xValueMapper: (SalesData sales, _) => sales.year,
yValueMapper: (SalesData sales, _) => sales.value,
name: 'Einzahlungen',
color: CupertinoColors.systemGrey.darkHighContrastColor,
),
// Serie für die Zinsen (obere Werte)
StackedColumnSeries<SalesData, int>(
dataSource: _getUpperChartData(),
xValueMapper: (SalesData sales, _) => sales.year,
yValueMapper: (SalesData sales, _) => sales.value,
name: 'Zinsen',
color: CupertinoColors.systemGreen.highContrastColor,
),
],
// Konfiguration für die Interaktivität des Diagramms
trackballBehavior: TrackballBehavior(
enable: true,
tooltipSettings: const InteractiveTooltip(enable: true),
activationMode: ActivationMode.singleTap,
hideDelay: 2000,
),
);
}
// Methode zur Erstellung der Daten für die untere Serie (Einzahlungen)
List<SalesData> _getLowerChartData() {
List<SalesData> chartData = [];
for (int i = 0; i < lowerValues.length; i++) {
chartData.add(SalesData(i + 1, lowerValues[i]));
}
return chartData;
}
// Methode zur Erstellung der Daten für die obere Serie (Zinsen)
List<SalesData> _getUpperChartData() {
List<SalesData> chartData = [];
for (int i = 0; i < upperValues.length; i++) {
chartData.add(SalesData(i + 1, upperValues[i]));
}
return chartData;
}
}
// Klasse zur Modellierung der Datenpunkte im Diagramm
class SalesData {
final int year;
final double value;
SalesData(this.year, this.value);
}
// Widget, welches das Diagramm auf eine neue Seite auslagert
@override
Widget buildChartPage(BuildContext context, List<double> investedMoneyList, List<double> compoundInterestList) {
return Scaffold(
body: CustomScrollView(
slivers: <Widget>[
SliverToBoxAdapter(
child: Container(
padding: EdgeInsets.only(left: 10, right: 10, top: MediaQuery.of(context).padding.top + 10),
child: Row(
mainAxisAlignment: MainAxisAlignment.spaceBetween,
children: [
IconButton(
icon: const Icon(CupertinoIcons.chevron_left, size: 15), // Zurück-Pfeil
onPressed: () {
Navigator.pop(context);
},
),
const Text(
'Grafik',
style: TextStyle(fontWeight: FontWeight.bold),
),
const SizedBox(width: 40), // Platzhalter für zentrierte Ausrichtung
],
),
),
),
SliverToBoxAdapter( // Diagramm Anzeigen
child: Padding(
padding: const EdgeInsets.all(10.0),
child: StackedColumnChart(
lowerValues: investedMoneyList,
upperValues: compoundInterestList,
),
),
),
SliverToBoxAdapter( // Tabelle mit allen Werten anzeigen
child: Padding(
padding: const EdgeInsets.all(10.0),
child: Container(
decoration: BoxDecoration(
color: CupertinoColors.black,
borderRadius: BorderRadius.circular(5),
),
clipBehavior: Clip.antiAlias,
child: Table(
columnWidths: const {
0: FixedColumnWidth(60), // Spaltenbreite für die erste Spalte verringern
1: FlexColumnWidth(),
2: FlexColumnWidth(),
3: FlexColumnWidth(),
},
border: TableBorder.symmetric(
inside: const BorderSide(color: CupertinoColors.white, width: 1),
),
children: [
const TableRow(
decoration: BoxDecoration(color: CupertinoColors.darkBackgroundGray),
children: [
Padding(
padding: EdgeInsets.all(8.0),
child: Text(
'Jahr',
style: TextStyle(
color: CupertinoColors.white,
fontWeight: FontWeight.bold,
),
textAlign: TextAlign.center,
),
),
Padding(
padding: EdgeInsets.all(8.0),
child: Text(
'Einzahlungen',
style: TextStyle(
color: CupertinoColors.white,
fontWeight: FontWeight.bold,
),
textAlign: TextAlign.center,
),
),
Padding(
padding: EdgeInsets.all(8.0),
child: Text(
'Zinsen',
style: TextStyle(
color: CupertinoColors.white,
fontWeight: FontWeight.bold,
),
textAlign: TextAlign.center,
),
),
Padding(
padding: EdgeInsets.all(8.0),
child: Text(
'Endkapital',
style: TextStyle(
color: CupertinoColors.white,
fontWeight: FontWeight.bold,
),
textAlign: TextAlign.center,
),
),
],
),
for (int i = 0; i < investedMoneyList.length; i++)
TableRow(
children: [
Padding(
padding: const EdgeInsets.all(8.0),
child: Text(
'${i + 1}',
style: const TextStyle(color: CupertinoColors.white),
textAlign: TextAlign.center,
),
),
Padding(
padding: const EdgeInsets.all(8.0),
child: Text(
'${investedMoneyList[i]}',
style: const TextStyle(color: CupertinoColors.white),
textAlign: TextAlign.center,
),
),
Padding(
padding: const EdgeInsets.all(8.0),
child: Text(
'${compoundInterestList[i]}',
style: const TextStyle(color: CupertinoColors.white),
textAlign: TextAlign.center,
),
),
Padding(
padding: const EdgeInsets.all(8.0),
child: Text(
'${compoundInterestList[i] + investedMoneyList[i]}',
style: const TextStyle(color: CupertinoColors.white),
textAlign: TextAlign.center,
),
),
],
),
],
),
),
),
),
],
),
);
}