132 lines
4.5 KiB
Dart
132 lines
4.5 KiB
Dart
import 'package:flutter/material.dart';
|
|
import 'package:flutter_test/flutter_test.dart';
|
|
import 'package:provider/provider.dart';
|
|
|
|
import 'package:fuel_tax_tracker/models/fuel_entry.dart';
|
|
import 'package:fuel_tax_tracker/models/vehicle.dart';
|
|
import 'package:fuel_tax_tracker/screens/vehicle_detail_screen.dart';
|
|
import 'package:fuel_tax_tracker/services/app_state.dart';
|
|
|
|
/// Covers the "modern navigation" swipe added to the single-vehicle
|
|
/// receipt page: it's a PageView over every vehicle, starting on whichever
|
|
/// one was tapped — sliding left/right moves to the next/previous vehicle,
|
|
/// same as swiping between MainShell's bottom-nav tabs.
|
|
void main() {
|
|
final vehicleA = Vehicle(id: 'a', vin: 'VINAAAAAAAAAAAAAA', nickname: 'Truck', updatedAt: DateTime.utc(2026, 1, 1));
|
|
final vehicleB = Vehicle(id: 'b', vin: 'VINBBBBBBBBBBBBBB', nickname: 'Van', updatedAt: DateTime.utc(2026, 1, 1));
|
|
final vehicleC = Vehicle(id: 'c', vin: 'VINCCCCCCCCCCCCCC', nickname: 'Sedan', updatedAt: DateTime.utc(2026, 1, 1));
|
|
|
|
Future<void> pumpDetail(WidgetTester tester, AppState appState, String vehicleId) async {
|
|
await tester.pumpWidget(
|
|
ChangeNotifierProvider.value(
|
|
value: appState,
|
|
child: MaterialApp(home: VehicleDetailScreen(vehicleId: vehicleId)),
|
|
),
|
|
);
|
|
}
|
|
|
|
testWidgets('starts on the requested vehicle, not necessarily the first in the list',
|
|
(tester) async {
|
|
final appState = AppState()
|
|
..isLoading = false
|
|
..vehicles = [vehicleA, vehicleB, vehicleC];
|
|
|
|
await pumpDetail(tester, appState, 'b');
|
|
|
|
expect(find.widgetWithText(AppBar, 'Van'), findsOneWidget);
|
|
});
|
|
|
|
testWidgets('a right-to-left swipe advances to the next vehicle', (tester) async {
|
|
final appState = AppState()
|
|
..isLoading = false
|
|
..vehicles = [vehicleA, vehicleB, vehicleC];
|
|
|
|
await pumpDetail(tester, appState, 'a');
|
|
expect(find.widgetWithText(AppBar, 'Truck'), findsOneWidget);
|
|
|
|
await tester.fling(find.byType(PageView), const Offset(-400, 0), 1000);
|
|
await tester.pumpAndSettle();
|
|
|
|
expect(find.widgetWithText(AppBar, 'Van'), findsOneWidget);
|
|
});
|
|
|
|
testWidgets('a left-to-right swipe goes back to the previous vehicle', (tester) async {
|
|
final appState = AppState()
|
|
..isLoading = false
|
|
..vehicles = [vehicleA, vehicleB, vehicleC];
|
|
|
|
await pumpDetail(tester, appState, 'c');
|
|
expect(find.widgetWithText(AppBar, 'Sedan'), findsOneWidget);
|
|
|
|
await tester.fling(find.byType(PageView), const Offset(400, 0), 1000);
|
|
await tester.pumpAndSettle();
|
|
|
|
expect(find.widgetWithText(AppBar, 'Van'), findsOneWidget);
|
|
});
|
|
|
|
testWidgets('swiping does not go past the last vehicle', (tester) async {
|
|
final appState = AppState()
|
|
..isLoading = false
|
|
..vehicles = [vehicleA, vehicleB];
|
|
|
|
await pumpDetail(tester, appState, 'b');
|
|
|
|
await tester.fling(find.byType(PageView), const Offset(-400, 0), 1000);
|
|
await tester.pumpAndSettle();
|
|
|
|
expect(find.widgetWithText(AppBar, 'Van'), findsOneWidget, reason: 'stayed on the last page');
|
|
});
|
|
|
|
testWidgets('a single vehicle has nothing to swipe to and just shows itself', (tester) async {
|
|
final appState = AppState()
|
|
..isLoading = false
|
|
..vehicles = [vehicleA];
|
|
|
|
await pumpDetail(tester, appState, 'a');
|
|
|
|
expect(find.widgetWithText(AppBar, 'Truck'), findsOneWidget);
|
|
});
|
|
|
|
testWidgets('shows an estimated fuel refund next to price/gal when the setting is on',
|
|
(tester) async {
|
|
final entry = FuelEntry(
|
|
id: 'e1',
|
|
vehicleId: 'a',
|
|
date: DateTime(2026, 5, 14, 9, 30),
|
|
gallons: 10,
|
|
pricePerGallon: 3.5,
|
|
totalCost: 35,
|
|
updatedAt: DateTime.utc(2026, 5, 14),
|
|
);
|
|
final appState = AppState()
|
|
..isLoading = false
|
|
..vehicles = [vehicleA]
|
|
..fuelEntries = [entry]
|
|
..showEstimatedFuelRefund = true;
|
|
|
|
await pumpDetail(tester, appState, 'a');
|
|
|
|
// 10 gal * $0.125/gal = $1.25.
|
|
expect(find.textContaining('\$3.50/gal · Est. \$1.25'), findsOneWidget);
|
|
});
|
|
|
|
testWidgets('shows no estimated fuel refund when the setting is off (default)', (tester) async {
|
|
final entry = FuelEntry(
|
|
id: 'e1',
|
|
vehicleId: 'a',
|
|
date: DateTime(2026, 5, 14, 9, 30),
|
|
gallons: 10,
|
|
pricePerGallon: 3.5,
|
|
totalCost: 35,
|
|
updatedAt: DateTime.utc(2026, 5, 14),
|
|
);
|
|
final appState = AppState()
|
|
..isLoading = false
|
|
..vehicles = [vehicleA]
|
|
..fuelEntries = [entry];
|
|
|
|
await pumpDetail(tester, appState, 'a');
|
|
|
|
expect(find.textContaining('Est. \$'), findsNothing);
|
|
});
|
|
}
|