bar tap correct

This commit is contained in:
davmar
2026-09-17 01:00:11 +02:00
parent b62164dde5
commit a23739d717
+83 -26
View File
@@ -957,10 +957,12 @@ class _OverviewScreenState extends State<OverviewScreen> {
final resolvedLabelIds = labelId != null final resolvedLabelIds = labelId != null
? {labelId} ? {labelId}
: (labelIds ?? : (labelIds ??
{ (_metric == OverviewMetricMode.labels
? {
// Open with the same labels currently shown on the chart. // Open with the same labels currently shown on the chart.
for (final id in _includedLabelIds) id, for (final id in _includedLabelIds) id,
}); }
: <String>{}));
Navigator.of(context).push( Navigator.of(context).push(
MaterialPageRoute<void>( MaterialPageRoute<void>(
builder: (_) => TransactionsScreen( builder: (_) => TransactionsScreen(
@@ -968,7 +970,8 @@ class _OverviewScreenState extends State<OverviewScreen> {
initialLabelIds: resolvedLabelIds, initialLabelIds: resolvedLabelIds,
initialLabelMatch: LabelMatchMode.or, initialLabelMatch: LabelMatchMode.or,
initialFlow: flow, initialFlow: flow,
initialSearchInMonthOnly: !yearly && resolvedLabelIds.isNotEmpty, // A specific bar/period should always scope to that month (or year).
initialSearchInMonthOnly: !yearly,
initialYear: yearly ? period.year : null, initialYear: yearly ? period.year : null,
), ),
), ),
@@ -1615,10 +1618,7 @@ class _ChartCard extends StatelessWidget {
margin: EdgeInsets.zero, margin: EdgeInsets.zero,
clipBehavior: Clip.antiAlias, clipBehavior: Clip.antiAlias,
shape: RoundedRectangleBorder(borderRadius: radius), shape: RoundedRectangleBorder(borderRadius: radius),
// Whole card opens the chart filter; nested buttons/legend keep their own taps. // Header/legend open the chart-wide filter; bars handle their own taps.
child: InkWell(
onTap: onChartTap,
borderRadius: radius,
child: Padding( child: Padding(
padding: EdgeInsets.fromLTRB( padding: EdgeInsets.fromLTRB(
compact ? 12 : 14, compact ? 12 : 14,
@@ -1626,6 +1626,13 @@ class _ChartCard extends StatelessWidget {
compact ? 10 : 14, compact ? 10 : 14,
compact ? 12 : 16, compact ? 12 : 16,
), ),
child: Column(
children: [
Material(
color: Colors.transparent,
child: InkWell(
onTap: onChartTap,
borderRadius: BorderRadius.circular(12),
child: Column( child: Column(
children: [ children: [
if (compact) ...[ if (compact) ...[
@@ -1774,6 +1781,10 @@ class _ChartCard extends StatelessWidget {
const SizedBox(height: 8), const SizedBox(height: 8),
], ],
], ],
],
),
),
),
SizedBox( SizedBox(
height: chartHeight, height: chartHeight,
child: metric == OverviewMetricMode.flow child: metric == OverviewMetricMode.flow
@@ -1800,7 +1811,6 @@ class _ChartCard extends StatelessWidget {
], ],
), ),
), ),
),
); );
} }
} }
@@ -1858,17 +1868,37 @@ class _FlowBars extends StatelessWidget {
); );
} }
return GestureDetector( return BarChart(
behavior: HitTestBehavior.opaque,
onTap: onChartTap,
child: IgnorePointer(
// fl_chart otherwise owns the gesture arena and empty taps go nowhere.
// Tap opens this chart's filters; legend / history still open columns.
child: BarChart(
BarChartData( BarChartData(
maxY: safeMax, maxY: safeMax,
groupsSpace: period == OverviewPeriodMode.yearly ? 16 : 10, groupsSpace: period == OverviewPeriodMode.yearly ? 16 : 10,
barTouchData: const BarTouchData(enabled: false), barTouchData: BarTouchData(
handleBuiltInTouches: false,
touchTooltipData: BarTouchTooltipData(
getTooltipItem: (group, groupIndex, rod, rodIndex) => null,
),
touchCallback: (event, response) {
if (event is! FlTapUpEvent) return;
final spot = response?.spot;
if (spot == null) {
onChartTap();
return;
}
final index = spot.touchedBarGroupIndex;
if (index < 0 || index >= months.length) {
onChartTap();
return;
}
final rod = spot.touchedRodDataIndex;
// Rod 0 = expense, rod 1 = income (see barGroups below).
final flow = rod == 0
? TxFlowFilter.expense
: rod == 1
? TxFlowFilter.income
: null;
onMonthTap(months[index], flow: flow);
},
),
titlesData: FlTitlesData( titlesData: FlTitlesData(
topTitles: topTitles:
const AxisTitles(sideTitles: SideTitles(showTitles: false)), const AxisTitles(sideTitles: SideTitles(showTitles: false)),
@@ -1954,8 +1984,6 @@ class _FlowBars extends StatelessWidget {
], ],
), ),
duration: Duration.zero, duration: Duration.zero,
),
),
); );
} }
} }
@@ -2165,16 +2193,47 @@ class _LabelMonthBars extends StatelessWidget {
final axisInterval = ((safeMax - safeMin) / 3).abs(); final axisInterval = ((safeMax - safeMin) / 3).abs();
final interval = axisInterval <= 0 ? 1.0 : axisInterval; final interval = axisInterval <= 0 ? 1.0 : axisInterval;
return GestureDetector( return BarChart(
behavior: HitTestBehavior.opaque,
onTap: onChartTap,
child: IgnorePointer(
child: BarChart(
BarChartData( BarChartData(
minY: safeMin, minY: safeMin,
maxY: safeMax, maxY: safeMax,
groupsSpace: period == OverviewPeriodMode.yearly ? 16 : 10, groupsSpace: period == OverviewPeriodMode.yearly ? 16 : 10,
barTouchData: const BarTouchData(enabled: false), barTouchData: BarTouchData(
handleBuiltInTouches: false,
touchTooltipData: BarTouchTooltipData(
getTooltipItem: (group, groupIndex, rod, rodIndex) => null,
),
touchCallback: (event, response) {
if (event is! FlTapUpEvent) return;
final spot = response?.spot;
if (spot == null) {
onChartTap();
return;
}
final index = spot.touchedBarGroupIndex;
if (index < 0 || index >= months.length) {
onChartTap();
return;
}
final month = months[index];
if (stacked) {
final stackIndex = spot.touchedStackItemIndex;
if (stackIndex >= 0 && stackIndex < topLabels.length) {
onMonthTap(month, labelId: topLabels[stackIndex].label.id);
return;
}
// "Other" segment or whole column → that period with chart labels.
onMonthTap(month);
return;
}
final rod = spot.touchedRodDataIndex;
if (rod >= 0 && rod < topLabels.length) {
onMonthTap(month, labelId: topLabels[rod].label.id);
return;
}
onMonthTap(month);
},
),
titlesData: FlTitlesData( titlesData: FlTitlesData(
topTitles: const AxisTitles(sideTitles: SideTitles(showTitles: false)), topTitles: const AxisTitles(sideTitles: SideTitles(showTitles: false)),
rightTitles: rightTitles:
@@ -2247,8 +2306,6 @@ class _LabelMonthBars extends StatelessWidget {
], ],
), ),
duration: Duration.zero, duration: Duration.zero,
),
),
); );
} }
} }