Moved to api v2
This commit is contained in:
parent
ab1b6fd6eb
commit
44d229f0f6
10 changed files with 585 additions and 466 deletions
18
.vscode/launch.json
vendored
18
.vscode/launch.json
vendored
|
@ -26,12 +26,28 @@
|
|||
"request": "launch",
|
||||
"type": "dart",
|
||||
"deviceId": "iphone"
|
||||
},
|
||||
{
|
||||
"name": "macOS",
|
||||
"request": "launch",
|
||||
"type": "dart",
|
||||
"deviceId": "macOS"
|
||||
},
|
||||
{
|
||||
"name": "Samsung",
|
||||
"request": "launch",
|
||||
"type": "dart",
|
||||
"deviceId": "SM"
|
||||
}
|
||||
],
|
||||
"compounds": [
|
||||
{
|
||||
"name": "All Devices",
|
||||
"configurations": ["Android Emulator", "iPhone"]
|
||||
"configurations": ["Android Emulator", "iPhone", "macOS"]
|
||||
},
|
||||
{
|
||||
"name": "Mac + Samsung",
|
||||
"configurations": ["macOS", "Samsung"]
|
||||
}
|
||||
]
|
||||
}
|
|
@ -1,3 +1,7 @@
|
|||
v2.4.0
|
||||
Moved to api v2
|
||||
Added support for any train number, including train numbers starting with 0
|
||||
|
||||
v2.3.1
|
||||
Fixed badge background when arrival is known but not departure
|
||||
|
||||
|
|
|
@ -4,6 +4,6 @@ import 'package:info_tren/models/train_data.dart';
|
|||
const AUTHORITY = 'scraper.infotren.dcdevelop.xyz';
|
||||
|
||||
Future<TrainData> getTrain(String trainNumber) async {
|
||||
final response = await http.get(Uri.https(AUTHORITY, 'train/$trainNumber'));
|
||||
final response = await http.get(Uri.https(AUTHORITY, 'v2/train/$trainNumber'));
|
||||
return trainDataFromJson(response.body);
|
||||
}
|
|
@ -18,7 +18,7 @@ class SlimAppBar extends StatelessWidget {
|
|||
height: size,
|
||||
child: Container(
|
||||
color:
|
||||
Theme.of(context).appBarTheme.color ??
|
||||
Theme.of(context).appBarTheme.backgroundColor ??
|
||||
Theme.of(context).primaryColor,
|
||||
child: InkWell(
|
||||
onTap: (ModalRoute.of(context)?.canPop ?? false)
|
||||
|
|
|
@ -30,7 +30,7 @@ class TrainInfo extends StatelessWidget {
|
|||
switch (uiDesign) {
|
||||
case UiDesign.MATERIAL:
|
||||
if ([RefreshFutureBuilderState.none, RefreshFutureBuilderState.waiting].contains(snapshot.state)) {
|
||||
return TrainInfoLoadingMaterial(title: trainNumber.toString(),);
|
||||
return TrainInfoLoadingMaterial(title: trainNumber.toString(), loadingText: "Se încarcă...",);
|
||||
}
|
||||
else if (snapshot.state == RefreshFutureBuilderState.error) {
|
||||
return TrainInfoErrorMaterial(title: '$trainNumber - Error', error: snapshot.error!, refresh: refresh,);
|
||||
|
@ -39,13 +39,13 @@ class TrainInfo extends StatelessWidget {
|
|||
return TrainInfoMaterial(trainData: snapshot.data!, refresh: refresh,);
|
||||
case UiDesign.CUPERTINO:
|
||||
if ([RefreshFutureBuilderState.none, RefreshFutureBuilderState.waiting].contains(snapshot.state)) {
|
||||
return TrainInfoLoadingCupertino(title: trainNumber.toString(),);
|
||||
return TrainInfoLoadingCupertino(title: trainNumber.toString(), loadingText: "Se încarcă...",);
|
||||
}
|
||||
else if (snapshot.state == RefreshFutureBuilderState.error) {
|
||||
return TrainInfoErrorCupertino(title: '$trainNumber - Error', error: snapshot.error!, refresh: refresh,);
|
||||
}
|
||||
|
||||
return TrainInfoCupertino(trainData: snapshot.data!, refresh: refresh,);
|
||||
return TrainInfoCupertino(trainData: snapshot.data!, refresh: refresh, isRefreshing: snapshot.state == RefreshFutureBuilderState.refreshing,);
|
||||
default:
|
||||
throw UnmatchedUiDesignException(uiDesign);
|
||||
}
|
||||
|
|
|
@ -11,7 +11,11 @@ import 'package:info_tren/pages/train_info_page/view_train/train_info_cupertino_
|
|||
import 'package:info_tren/utils/state_to_string.dart';
|
||||
|
||||
class TrainInfoLoadingCupertino extends TrainInfoLoading {
|
||||
TrainInfoLoadingCupertino({required String title, String? loadingText}) : super(title: title, loadingText: loadingText, uiDesign: UiDesign.CUPERTINO);
|
||||
TrainInfoLoadingCupertino({required String title, String? loadingText})
|
||||
: super(
|
||||
title: title,
|
||||
loadingText: loadingText,
|
||||
uiDesign: UiDesign.CUPERTINO);
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
|
@ -31,7 +35,11 @@ class TrainInfoErrorCupertino extends TrainInfoError {
|
|||
required Object error,
|
||||
required String title,
|
||||
Future Function()? refresh,
|
||||
}) : super(error: error, title: title, refresh: refresh,);
|
||||
}) : super(
|
||||
error: error,
|
||||
title: title,
|
||||
refresh: refresh,
|
||||
);
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
|
@ -62,174 +70,210 @@ class TrainInfoErrorCupertino extends TrainInfoError {
|
|||
class TrainInfoCupertino extends StatelessWidget {
|
||||
final TrainData trainData;
|
||||
final Future Function()? refresh;
|
||||
final bool? isRefreshing;
|
||||
|
||||
TrainInfoCupertino({required this.trainData, this.refresh,});
|
||||
TrainInfoCupertino({
|
||||
required this.trainData,
|
||||
this.refresh,
|
||||
this.isRefreshing,
|
||||
});
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
return CupertinoPageScaffold(
|
||||
navigationBar: CupertinoNavigationBar(
|
||||
middle: Text("Informații despre ${trainData.rank} ${trainData.number}"),
|
||||
),
|
||||
child: SafeArea(
|
||||
top: false,
|
||||
bottom: false,
|
||||
child: Builder(
|
||||
builder: (context) {
|
||||
final topPadding = MediaQuery.of(context).padding.top;
|
||||
return CupertinoPageScaffold(
|
||||
navigationBar: CupertinoNavigationBar(
|
||||
middle: Text("Informații despre ${trainData.rank} ${trainData.number}"),
|
||||
trailing: refresh == null ? null : isRefreshing == true ? CupertinoActivityIndicator() : CupertinoButton(
|
||||
padding: const EdgeInsets.all(0),
|
||||
alignment: Alignment.center,
|
||||
child: Icon(CupertinoIcons.refresh),
|
||||
onPressed: () => refresh!(),
|
||||
),
|
||||
),
|
||||
child: SafeArea(
|
||||
top: false,
|
||||
bottom: false,
|
||||
child: Builder(builder: (context) {
|
||||
final topPadding = MediaQuery.of(context).padding.top;
|
||||
|
||||
return NestedScrollView(
|
||||
headerSliverBuilder: (context, innerBoxIsScrolled) {
|
||||
return [
|
||||
// SliverPadding(
|
||||
// padding: EdgeInsets.only(
|
||||
// top: topPadding,
|
||||
// ),
|
||||
// ),
|
||||
SliverPersistentHeaderPadding(maxHeight: topPadding,)
|
||||
];
|
||||
},
|
||||
body: Builder(
|
||||
builder: (context) {
|
||||
return CustomScrollView(
|
||||
slivers: <Widget>[
|
||||
if (refresh != null)
|
||||
CupertinoSliverRefreshControl(
|
||||
builder: (context, mode, pulledExtent, refreshTriggerPullDistance, refreshIndicatorExtent) {
|
||||
return Column(
|
||||
mainAxisSize: MainAxisSize.min,
|
||||
children: [
|
||||
Container(
|
||||
height: pulledExtent,
|
||||
child: Column(
|
||||
children: [
|
||||
Container(
|
||||
height: min(refreshIndicatorExtent, pulledExtent),
|
||||
child: Center(
|
||||
child: Builder(
|
||||
builder: (context) {
|
||||
if (mode == RefreshIndicatorMode.inactive) {
|
||||
return Container();
|
||||
}
|
||||
else if (mode == RefreshIndicatorMode.done) {
|
||||
return Text('Refreshed!');
|
||||
}
|
||||
else if (mode == RefreshIndicatorMode.drag) {
|
||||
return Row(
|
||||
mainAxisSize: MainAxisSize.min,
|
||||
children: [
|
||||
CupertinoActivityIndicator(animating: false,),
|
||||
Text('Pull to refresh...'),
|
||||
],
|
||||
);
|
||||
}
|
||||
else if (mode == RefreshIndicatorMode.armed) {
|
||||
return Row(
|
||||
mainAxisSize: MainAxisSize.min,
|
||||
children: [
|
||||
CupertinoActivityIndicator(animating: false,),
|
||||
Text('Release to refresh...'),
|
||||
],
|
||||
);
|
||||
}
|
||||
else {
|
||||
return Row(
|
||||
mainAxisSize: MainAxisSize.min,
|
||||
children: [
|
||||
CupertinoActivityIndicator(),
|
||||
Text('Refreshing'),
|
||||
],
|
||||
);
|
||||
}
|
||||
},
|
||||
),
|
||||
),
|
||||
),
|
||||
Expanded(child: Container(),),
|
||||
],
|
||||
return NestedScrollView(
|
||||
headerSliverBuilder: (context, innerBoxIsScrolled) {
|
||||
return [
|
||||
// SliverPadding(
|
||||
// padding: EdgeInsets.only(
|
||||
// top: topPadding,
|
||||
// ),
|
||||
// ),
|
||||
SliverPersistentHeaderPadding(
|
||||
maxHeight: topPadding,
|
||||
)
|
||||
];
|
||||
},
|
||||
body: Builder(builder: (context) {
|
||||
return CustomScrollView(
|
||||
slivers: <Widget>[
|
||||
if (refresh != null)
|
||||
CupertinoSliverRefreshControl(
|
||||
builder: (context, mode, pulledExtent,
|
||||
refreshTriggerPullDistance, refreshIndicatorExtent) {
|
||||
return Column(
|
||||
mainAxisSize: MainAxisSize.min,
|
||||
children: [
|
||||
Container(
|
||||
height: pulledExtent,
|
||||
child: Column(
|
||||
children: [
|
||||
Container(
|
||||
height: min(
|
||||
refreshIndicatorExtent, pulledExtent),
|
||||
child: Center(
|
||||
child: Builder(
|
||||
builder: (context) {
|
||||
if (mode ==
|
||||
RefreshIndicatorMode.inactive) {
|
||||
return Container();
|
||||
} else if (mode ==
|
||||
RefreshIndicatorMode.done) {
|
||||
return Text('Refreshed!');
|
||||
} else if (mode ==
|
||||
RefreshIndicatorMode.drag) {
|
||||
return Row(
|
||||
mainAxisSize: MainAxisSize.min,
|
||||
children: [
|
||||
CupertinoActivityIndicator(
|
||||
animating: false,
|
||||
),
|
||||
Text('Pull to refresh...'),
|
||||
],
|
||||
);
|
||||
} else if (mode ==
|
||||
RefreshIndicatorMode.armed) {
|
||||
return Row(
|
||||
mainAxisSize: MainAxisSize.min,
|
||||
children: [
|
||||
CupertinoActivityIndicator(
|
||||
animating: false,
|
||||
),
|
||||
Text('Release to refresh...'),
|
||||
],
|
||||
);
|
||||
} else {
|
||||
return Row(
|
||||
mainAxisSize: MainAxisSize.min,
|
||||
children: [
|
||||
CupertinoActivityIndicator(),
|
||||
Text('Refreshing'),
|
||||
],
|
||||
);
|
||||
}
|
||||
},
|
||||
),
|
||||
),
|
||||
],
|
||||
);
|
||||
},
|
||||
onRefresh: refresh,
|
||||
),
|
||||
DisplayTrainID(trainData: trainData,),
|
||||
DisplayTrainOperator(trainData: trainData,),
|
||||
DisplayTrainRoute(trainData: trainData,),
|
||||
DisplayTrainDeparture(trainData: trainData,),
|
||||
SliverToBoxAdapter(
|
||||
child: CupertinoDivider(
|
||||
color: FOREGROUND_WHITE,
|
||||
),
|
||||
),
|
||||
DisplayTrainLastInfo(trainData: trainData,),
|
||||
SliverToBoxAdapter(
|
||||
child: CupertinoDivider(),
|
||||
),
|
||||
SliverToBoxAdapter(
|
||||
child: IntrinsicHeight(
|
||||
child: Row(
|
||||
children: <Widget>[
|
||||
// Expanded(
|
||||
// child: DisplayTrainNextStop(trainData: trainData,),
|
||||
// ),
|
||||
),
|
||||
Expanded(
|
||||
child: DisplayTrainDestination(trainData: trainData,),
|
||||
child: Container(),
|
||||
),
|
||||
SizedBox(
|
||||
height: double.infinity,
|
||||
child: CupertinoVerticalDivider(),
|
||||
),
|
||||
Expanded(child: DisplayTrainRouteDistance(trainData: trainData,),),
|
||||
],
|
||||
),
|
||||
),
|
||||
),
|
||||
// SliverToBoxAdapter(
|
||||
// child: CupertinoDivider(),
|
||||
],
|
||||
);
|
||||
},
|
||||
onRefresh: refresh,
|
||||
),
|
||||
DisplayTrainID(
|
||||
trainData: trainData,
|
||||
),
|
||||
DisplayTrainOperator(
|
||||
trainData: trainData,
|
||||
),
|
||||
DisplayTrainRoute(
|
||||
trainData: trainData,
|
||||
),
|
||||
DisplayTrainDeparture(
|
||||
trainData: trainData,
|
||||
),
|
||||
SliverToBoxAdapter(
|
||||
child: CupertinoDivider(
|
||||
color: FOREGROUND_WHITE,
|
||||
),
|
||||
),
|
||||
DisplayTrainLastInfo(
|
||||
trainData: trainData,
|
||||
),
|
||||
SliverToBoxAdapter(
|
||||
child: CupertinoDivider(),
|
||||
),
|
||||
SliverToBoxAdapter(
|
||||
child: IntrinsicHeight(
|
||||
child: Row(
|
||||
children: <Widget>[
|
||||
// Expanded(
|
||||
// child: DisplayTrainNextStop(trainData: trainData,),
|
||||
// ),
|
||||
// SliverToBoxAdapter(
|
||||
// child: IntrinsicHeight(
|
||||
// child: Row(
|
||||
// children: <Widget>[
|
||||
// // Expanded(
|
||||
// // child: DisplayTrainRouteDuration(trainData: trainData,),
|
||||
// // ),
|
||||
// Expanded(child: Container(),),
|
||||
// SizedBox(
|
||||
// height: double.infinity,
|
||||
// child: CupertinoVerticalDivider(),
|
||||
// ),
|
||||
// Expanded(
|
||||
// child: DisplayTrainRouteDistance(trainData: trainData,),
|
||||
// )
|
||||
// ],
|
||||
// ),
|
||||
// ),
|
||||
// ),
|
||||
SliverToBoxAdapter(
|
||||
child: CupertinoDivider(
|
||||
color: FOREGROUND_WHITE,
|
||||
Expanded(
|
||||
child: DisplayTrainRouteDuration(
|
||||
trainData: trainData,
|
||||
),
|
||||
),
|
||||
DisplayTrainStations(
|
||||
trainData: trainData,
|
||||
// Expanded(
|
||||
// child: DisplayTrainDestination(trainData: trainData,),
|
||||
// ),
|
||||
SizedBox(
|
||||
height: double.infinity,
|
||||
child: CupertinoVerticalDivider(),
|
||||
),
|
||||
SliverToBoxAdapter(
|
||||
child: Container(
|
||||
height: MediaQuery.of(context).viewPadding.bottom,
|
||||
Expanded(
|
||||
child: DisplayTrainRouteDistance(
|
||||
trainData: trainData,
|
||||
),
|
||||
),
|
||||
],
|
||||
);
|
||||
}
|
||||
),
|
||||
),
|
||||
),
|
||||
);
|
||||
}
|
||||
),
|
||||
),
|
||||
);
|
||||
// SliverToBoxAdapter(
|
||||
// child: CupertinoDivider(),
|
||||
// ),
|
||||
// SliverToBoxAdapter(
|
||||
// child: IntrinsicHeight(
|
||||
// child: Row(
|
||||
// children: <Widget>[
|
||||
// // Expanded(
|
||||
// // child: DisplayTrainRouteDuration(trainData: trainData,),
|
||||
// // ),
|
||||
// Expanded(child: Container(),),
|
||||
// SizedBox(
|
||||
// height: double.infinity,
|
||||
// child: CupertinoVerticalDivider(),
|
||||
// ),
|
||||
// Expanded(
|
||||
// child: DisplayTrainRouteDistance(trainData: trainData,),
|
||||
// )
|
||||
// ],
|
||||
// ),
|
||||
// ),
|
||||
// ),
|
||||
SliverToBoxAdapter(
|
||||
child: CupertinoDivider(
|
||||
color: FOREGROUND_WHITE,
|
||||
),
|
||||
),
|
||||
DisplayTrainStations(
|
||||
trainData: trainData,
|
||||
),
|
||||
SliverToBoxAdapter(
|
||||
child: Container(
|
||||
height: MediaQuery.of(context).viewPadding.bottom,
|
||||
),
|
||||
),
|
||||
],
|
||||
);
|
||||
}),
|
||||
);
|
||||
}),
|
||||
),
|
||||
);
|
||||
|
||||
// return CupertinoPageScaffold(
|
||||
// navigationBar: CupertinoNavigationBar(
|
||||
|
@ -343,11 +387,22 @@ class DisplayTrainID extends StatelessWidget {
|
|||
@override
|
||||
Widget build(BuildContext context) {
|
||||
return SliverToBoxAdapter(
|
||||
child: Center(
|
||||
child: Center(
|
||||
child: Padding(
|
||||
padding: const EdgeInsets.all(8.0),
|
||||
child: Text(
|
||||
"${trainData.rank} ${trainData.number}",
|
||||
child: Text.rich(
|
||||
TextSpan(
|
||||
children: [
|
||||
TextSpan(
|
||||
text: trainData.rank,
|
||||
style: TextStyle(
|
||||
color: trainData.rank.startsWith('IR') ? Color.fromARGB(255, 255, 0, 0) : null,
|
||||
),
|
||||
),
|
||||
TextSpan(text: ' '),
|
||||
TextSpan(text: trainData.number,),
|
||||
],
|
||||
),
|
||||
style: CupertinoTheme.of(context).textTheme.navLargeTitleTextStyle,
|
||||
),
|
||||
),
|
||||
|
@ -364,31 +419,35 @@ class DisplayTrainRoute extends StatelessWidget {
|
|||
@override
|
||||
Widget build(BuildContext context) {
|
||||
return SliverToBoxAdapter(
|
||||
child: Row(
|
||||
child: Row(
|
||||
children: <Widget>[
|
||||
Center(
|
||||
child: Padding(
|
||||
padding: const EdgeInsets.all(4),
|
||||
child: Text(
|
||||
trainData.route.from,
|
||||
style: CupertinoTheme.of(context).textTheme.textStyle.copyWith(
|
||||
fontSize: 16,
|
||||
Expanded(
|
||||
child: Center(
|
||||
child: Padding(
|
||||
padding: const EdgeInsets.all(4),
|
||||
child: Text(
|
||||
trainData.route.from,
|
||||
style:
|
||||
CupertinoTheme.of(context).textTheme.textStyle.copyWith(
|
||||
fontSize: 16,
|
||||
),
|
||||
),
|
||||
),
|
||||
),
|
||||
),
|
||||
Expanded(child: Container(),),
|
||||
Center(child: Text("-")),
|
||||
Expanded(child: Container(),),
|
||||
Center(
|
||||
child: Padding(
|
||||
padding: const EdgeInsets.all(4),
|
||||
child: Text(
|
||||
trainData.route.to,
|
||||
style: CupertinoTheme.of(context).textTheme.textStyle.copyWith(
|
||||
fontSize: 16,
|
||||
Expanded(
|
||||
child: Center(
|
||||
child: Padding(
|
||||
padding: const EdgeInsets.all(4),
|
||||
child: Text(
|
||||
trainData.route.to,
|
||||
style:
|
||||
CupertinoTheme.of(context).textTheme.textStyle.copyWith(
|
||||
fontSize: 16,
|
||||
),
|
||||
textAlign: TextAlign.right,
|
||||
),
|
||||
textAlign: TextAlign.right,
|
||||
),
|
||||
),
|
||||
),
|
||||
|
@ -410,9 +469,9 @@ class DisplayTrainOperator extends StatelessWidget {
|
|||
child: Text(
|
||||
trainData.operator,
|
||||
style: CupertinoTheme.of(context).textTheme.textStyle.copyWith(
|
||||
fontSize: 14,
|
||||
fontStyle: FontStyle.italic,
|
||||
),
|
||||
fontSize: 14,
|
||||
fontStyle: FontStyle.italic,
|
||||
),
|
||||
),
|
||||
),
|
||||
);
|
||||
|
@ -433,9 +492,9 @@ class DisplayTrainDeparture extends StatelessWidget {
|
|||
// "Plecare în ${dataPlecare.day.toString().padLeft(2, '0')}.${dataPlecare.month.toString().padLeft(2, '0')}.${dataPlecare.year.toString().padLeft(4, '0')}",
|
||||
"Plecare în ${trainData.date}",
|
||||
style: CupertinoTheme.of(context).textTheme.textStyle.copyWith(
|
||||
fontStyle: FontStyle.italic,
|
||||
fontWeight: FontWeight.w200,
|
||||
),
|
||||
fontStyle: FontStyle.italic,
|
||||
fontWeight: FontWeight.w200,
|
||||
),
|
||||
textAlign: TextAlign.center,
|
||||
),
|
||||
),
|
||||
|
@ -451,7 +510,9 @@ class DisplayTrainLastInfo extends StatelessWidget {
|
|||
@override
|
||||
Widget build(BuildContext context) {
|
||||
if (trainData.status == null) {
|
||||
return SliverToBoxAdapter(child: Container(),);
|
||||
return SliverToBoxAdapter(
|
||||
child: Container(),
|
||||
);
|
||||
}
|
||||
|
||||
return SliverToBoxAdapter(
|
||||
|
@ -464,9 +525,9 @@ class DisplayTrainLastInfo extends StatelessWidget {
|
|||
child: Text(
|
||||
"Ultima informație",
|
||||
style: CupertinoTheme.of(context).textTheme.textStyle.copyWith(
|
||||
fontSize: 20,
|
||||
fontWeight: FontWeight.bold,
|
||||
),
|
||||
fontSize: 20,
|
||||
fontWeight: FontWeight.bold,
|
||||
),
|
||||
),
|
||||
),
|
||||
),
|
||||
|
@ -480,10 +541,12 @@ class DisplayTrainLastInfo extends StatelessWidget {
|
|||
textAlign: TextAlign.left,
|
||||
),
|
||||
),
|
||||
Expanded(child: Container(),),
|
||||
Expanded(
|
||||
child: Container(),
|
||||
),
|
||||
Padding(
|
||||
padding: const EdgeInsets.all(4),
|
||||
child: Text(
|
||||
child: Text(
|
||||
stateToString(trainData.status!.state),
|
||||
style: CupertinoTheme.of(context).textTheme.textStyle,
|
||||
textAlign: TextAlign.right,
|
||||
|
@ -510,20 +573,21 @@ class DisplayTrainLastInfo extends StatelessWidget {
|
|||
|
||||
if (data > 0) {
|
||||
return Text(
|
||||
"$data minute întârziere",
|
||||
style: CupertinoTheme.of(context).textTheme.textStyle.copyWith(
|
||||
fontSize: 14,
|
||||
color: CupertinoColors.destructiveRed,
|
||||
),
|
||||
"$data ${data == 1 ? 'minut' : 'minute'} întârziere",
|
||||
style:
|
||||
CupertinoTheme.of(context).textTheme.textStyle.copyWith(
|
||||
fontSize: 14,
|
||||
color: CupertinoColors.destructiveRed,
|
||||
),
|
||||
);
|
||||
}
|
||||
else {
|
||||
} else {
|
||||
return Text(
|
||||
"${-data} minute mai devreme",
|
||||
style: CupertinoTheme.of(context).textTheme.textStyle.copyWith(
|
||||
fontSize: 12,
|
||||
color: CupertinoColors.activeGreen,
|
||||
),
|
||||
"${-data} ${data == -1 ? 'minut' : 'minute'} mai devreme",
|
||||
style:
|
||||
CupertinoTheme.of(context).textTheme.textStyle.copyWith(
|
||||
fontSize: 12,
|
||||
color: CupertinoColors.activeGreen,
|
||||
),
|
||||
);
|
||||
}
|
||||
},
|
||||
|
@ -627,9 +691,9 @@ class DisplayTrainDestination extends StatelessWidget {
|
|||
child: Text(
|
||||
"Destinația",
|
||||
style: CupertinoTheme.of(context).textTheme.textStyle.copyWith(
|
||||
fontSize: 20,
|
||||
fontWeight: FontWeight.bold,
|
||||
),
|
||||
fontSize: 20,
|
||||
fontWeight: FontWeight.bold,
|
||||
),
|
||||
textAlign: TextAlign.center,
|
||||
),
|
||||
),
|
||||
|
@ -641,20 +705,22 @@ class DisplayTrainDestination extends StatelessWidget {
|
|||
child: Text(
|
||||
trainData.stations.last.name,
|
||||
style: CupertinoTheme.of(context).textTheme.textStyle.copyWith(
|
||||
fontSize: 18,
|
||||
fontWeight: FontWeight.w500,
|
||||
),
|
||||
fontSize: 18,
|
||||
fontWeight: FontWeight.w500,
|
||||
),
|
||||
textAlign: TextAlign.center,
|
||||
),
|
||||
),
|
||||
Builder(
|
||||
builder: (context) {
|
||||
final arrival = trainData.stations.last.arrival!.scheduleTime;
|
||||
final arrival =
|
||||
DateTime.parse(trainData.stations.last.arrival!.scheduleTime);
|
||||
final delay = trainData.stations.last.arrival!.status?.delay ?? 0;
|
||||
final parts = arrival.split(':');
|
||||
final arrivalDT = DateTime(DateTime.now().year, DateTime.now().month, DateTime.now().day, int.parse(parts[0]), int.parse(parts[1]));
|
||||
final arrivalWithDelay = arrivalDT.add(Duration(minutes: delay));
|
||||
final arrivalWithDelayString = '${arrivalWithDelay.hour}:${arrivalWithDelay.minute.toString().padLeft(2, "0")}';
|
||||
// final parts = arrival.split(':');
|
||||
// final arrivalDT = DateTime(DateTime.now().year, DateTime.now().month, DateTime.now().day, int.parse(parts[0]), int.parse(parts[1]));
|
||||
final arrivalWithDelay = arrival.add(Duration(minutes: delay));
|
||||
final arrivalWithDelayString =
|
||||
'${arrivalWithDelay.hour}:${arrivalWithDelay.minute.toString().padLeft(2, "0")}';
|
||||
// const months = ["ian", "feb", "mar", "apr", "mai", "iun", "iul", "aug", "sep", "oct", "noi", "dec"];
|
||||
|
||||
return Column(
|
||||
|
@ -673,26 +739,32 @@ class DisplayTrainDestination extends StatelessWidget {
|
|||
children: [
|
||||
TextSpan(text: ' '),
|
||||
TextSpan(
|
||||
text: '$arrival',
|
||||
style: delay == 0 ? null : TextStyle(
|
||||
decoration: TextDecoration.lineThrough,
|
||||
),
|
||||
text:
|
||||
'${arrival.hour.toString().padLeft(2, "0")}:${arrival.minute.toString().padLeft(2, "0")}',
|
||||
style: delay == 0
|
||||
? null
|
||||
: TextStyle(
|
||||
decoration: TextDecoration.lineThrough,
|
||||
),
|
||||
),
|
||||
if (delay != 0) ...[
|
||||
TextSpan(text: ' '),
|
||||
TextSpan(
|
||||
text: '$arrivalWithDelayString',
|
||||
style: TextStyle(
|
||||
color: delay > 0 ? CupertinoColors.destructiveRed : CupertinoColors.activeGreen,
|
||||
color: delay > 0
|
||||
? CupertinoColors.destructiveRed
|
||||
: CupertinoColors.activeGreen,
|
||||
),
|
||||
),
|
||||
]
|
||||
],
|
||||
),
|
||||
// "la ${arrival.hour.toString().padLeft(2, '0')}:${arrival.minute.toString().padLeft(2, '0')}",
|
||||
style: CupertinoTheme.of(context).textTheme.textStyle.copyWith(
|
||||
fontSize: 14,
|
||||
),
|
||||
style:
|
||||
CupertinoTheme.of(context).textTheme.textStyle.copyWith(
|
||||
fontSize: 14,
|
||||
),
|
||||
textAlign: TextAlign.center,
|
||||
),
|
||||
],
|
||||
|
@ -717,16 +789,16 @@ class DisplayTrainRouteDistance extends StatelessWidget {
|
|||
Text(
|
||||
"Distanța rutei",
|
||||
style: CupertinoTheme.of(context).textTheme.textStyle.copyWith(
|
||||
fontSize: 18,
|
||||
fontWeight: FontWeight.bold,
|
||||
),
|
||||
fontSize: 18,
|
||||
fontWeight: FontWeight.bold,
|
||||
),
|
||||
textAlign: TextAlign.center,
|
||||
),
|
||||
Text(
|
||||
"${trainData.stations.last.km} km",
|
||||
style: CupertinoTheme.of(context).textTheme.textStyle.copyWith(
|
||||
fontSize: 16,
|
||||
),
|
||||
fontSize: 16,
|
||||
),
|
||||
textAlign: TextAlign.center,
|
||||
),
|
||||
],
|
||||
|
@ -734,76 +806,87 @@ class DisplayTrainRouteDistance extends StatelessWidget {
|
|||
}
|
||||
}
|
||||
|
||||
// class DisplayTrainRouteDuration extends StatelessWidget {
|
||||
// final TrainData trainData;
|
||||
//
|
||||
// DisplayTrainRouteDuration({required this.trainData});
|
||||
//
|
||||
// @override
|
||||
// Widget build(BuildContext context) {
|
||||
// return Column(
|
||||
// mainAxisSize: MainAxisSize.min,
|
||||
// children: <Widget>[
|
||||
// Text(
|
||||
// "Durata rutei",
|
||||
// style: CupertinoTheme.of(context).textTheme.textStyle.copyWith(
|
||||
// fontSize: 18,
|
||||
// fontWeight: FontWeight.bold,
|
||||
// ),
|
||||
// textAlign: TextAlign.center,
|
||||
// ),
|
||||
// FutureDisplay<Duration>(
|
||||
// future: trainData.routeDuration,
|
||||
// builder: (context, duration) {
|
||||
// var durationString = StringBuffer();
|
||||
//
|
||||
// bool firstWritten = false;
|
||||
//
|
||||
// if (duration.inDays > 0) {
|
||||
// firstWritten = true;
|
||||
// if (duration.inDays == 1) durationString.write("1 zi");
|
||||
// else durationString.write("${duration.inDays} zile");
|
||||
// duration -= Duration(days: duration.inDays);
|
||||
// }
|
||||
//
|
||||
// if (duration.inHours > 0) {
|
||||
// if (firstWritten) {
|
||||
// durationString.write(", ");
|
||||
// }
|
||||
// firstWritten = true;
|
||||
// if (duration.inHours == 1) durationString.write("1 oră");
|
||||
// else durationString.write("${duration.inHours} ore");
|
||||
// duration -= Duration(hours: duration.inHours);
|
||||
// }
|
||||
//
|
||||
// if (duration.inMinutes > 0) {
|
||||
// if (firstWritten) {
|
||||
// durationString.write(", ");
|
||||
// }
|
||||
// firstWritten = true;
|
||||
// if (duration.inMinutes == 1) durationString.write("1 minut");
|
||||
// else durationString.write("${duration.inMinutes} minute");
|
||||
// duration -= Duration(minutes: duration.inMinutes);
|
||||
// }
|
||||
//
|
||||
// return Text(
|
||||
// durationString.toString(),
|
||||
// style: CupertinoTheme.of(context).textTheme.textStyle.copyWith(
|
||||
// fontSize: 16,
|
||||
// ),
|
||||
// textAlign: TextAlign.center,
|
||||
// );
|
||||
// },
|
||||
// ),
|
||||
// ],
|
||||
// );
|
||||
// }
|
||||
// }
|
||||
class DisplayTrainRouteDuration extends StatelessWidget {
|
||||
final TrainData trainData;
|
||||
|
||||
DisplayTrainRouteDuration({required this.trainData});
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
return Column(
|
||||
mainAxisSize: MainAxisSize.min,
|
||||
children: <Widget>[
|
||||
Text(
|
||||
"Durata rutei",
|
||||
style: CupertinoTheme.of(context).textTheme.textStyle.copyWith(
|
||||
fontSize: 18,
|
||||
fontWeight: FontWeight.bold,
|
||||
),
|
||||
textAlign: TextAlign.center,
|
||||
),
|
||||
Builder(
|
||||
builder: (context) {
|
||||
var duration =
|
||||
DateTime.parse(trainData.stations.last.arrival!.scheduleTime)
|
||||
.difference(DateTime.parse(
|
||||
trainData.stations.first.departure!.scheduleTime));
|
||||
var durationString = StringBuffer();
|
||||
|
||||
bool firstWritten = false;
|
||||
|
||||
if (duration.inDays > 0) {
|
||||
firstWritten = true;
|
||||
if (duration.inDays == 1)
|
||||
durationString.write("1 zi");
|
||||
else
|
||||
durationString.write("${duration.inDays} zile");
|
||||
duration -= Duration(days: duration.inDays);
|
||||
}
|
||||
|
||||
if (duration.inHours > 0) {
|
||||
if (firstWritten) {
|
||||
durationString.write(", ");
|
||||
}
|
||||
firstWritten = true;
|
||||
if (duration.inHours == 1)
|
||||
durationString.write("1 oră");
|
||||
else
|
||||
durationString.write("${duration.inHours} ore");
|
||||
duration -= Duration(hours: duration.inHours);
|
||||
}
|
||||
|
||||
if (duration.inMinutes > 0) {
|
||||
if (firstWritten) {
|
||||
durationString.write(", ");
|
||||
}
|
||||
firstWritten = true;
|
||||
if (duration.inMinutes == 1)
|
||||
durationString.write("1 minut");
|
||||
else
|
||||
durationString.write("${duration.inMinutes} minute");
|
||||
duration -= Duration(minutes: duration.inMinutes);
|
||||
}
|
||||
|
||||
return Text(
|
||||
durationString.toString(),
|
||||
style: CupertinoTheme.of(context).textTheme.textStyle.copyWith(
|
||||
fontSize: 16,
|
||||
),
|
||||
textAlign: TextAlign.center,
|
||||
);
|
||||
},
|
||||
),
|
||||
],
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
class DisplayTrainStations extends StatelessWidget {
|
||||
final TrainData trainData;
|
||||
|
||||
DisplayTrainStations({required this.trainData,});
|
||||
DisplayTrainStations({
|
||||
required this.trainData,
|
||||
});
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
|
@ -812,8 +895,7 @@ class DisplayTrainStations extends StatelessWidget {
|
|||
(context, index) {
|
||||
if (index.isOdd) {
|
||||
return CupertinoDivider();
|
||||
}
|
||||
else {
|
||||
} else {
|
||||
final itemIndex = index ~/ 2;
|
||||
return IndexedSemantics(
|
||||
child: DisplayTrainStation(
|
||||
|
|
|
@ -43,8 +43,9 @@ class DisplayTrainStation extends StatelessWidget {
|
|||
final isOnTime = delay <= 0 && real == true;
|
||||
final isNotScheduled = false;
|
||||
|
||||
return KmBadge(
|
||||
station: station,
|
||||
return Badge(
|
||||
text: station.km.toString(),
|
||||
caption: 'km',
|
||||
isNotScheduled: isNotScheduled,
|
||||
isDelayed: isDelayed,
|
||||
isOnTime: isOnTime,
|
||||
|
@ -55,7 +56,11 @@ class DisplayTrainStation extends StatelessWidget {
|
|||
child: Title(
|
||||
station: station,
|
||||
),
|
||||
)
|
||||
),
|
||||
if (station.platform == null)
|
||||
Container(width: 48, height: 48,)
|
||||
else
|
||||
Badge(text: station.platform!, caption: 'linia'),
|
||||
],
|
||||
),
|
||||
Time(
|
||||
|
@ -69,14 +74,16 @@ class DisplayTrainStation extends StatelessWidget {
|
|||
}
|
||||
}
|
||||
|
||||
class KmBadge extends StatelessWidget {
|
||||
final Station station;
|
||||
class Badge extends StatelessWidget {
|
||||
final String text;
|
||||
final String caption;
|
||||
final bool isNotScheduled;
|
||||
final bool isOnTime;
|
||||
final bool isDelayed;
|
||||
|
||||
KmBadge({
|
||||
required this.station,
|
||||
Badge({
|
||||
required this.text,
|
||||
required this.caption,
|
||||
this.isNotScheduled = false,
|
||||
this.isOnTime = false,
|
||||
this.isDelayed = false,
|
||||
|
@ -120,7 +127,7 @@ class KmBadge extends StatelessWidget {
|
|||
Expanded(
|
||||
child: Center(
|
||||
child: Text(
|
||||
station.km.toString(),
|
||||
text,
|
||||
style: CupertinoTheme.of(context).textTheme.textStyle.copyWith(
|
||||
fontSize: 20,
|
||||
fontWeight: MediaQuery.of(context).boldText ? FontWeight.w400 : FontWeight.w200,
|
||||
|
@ -131,9 +138,9 @@ class KmBadge extends StatelessWidget {
|
|||
),
|
||||
),
|
||||
Text(
|
||||
"km",
|
||||
caption,
|
||||
style: CupertinoTheme.of(context).textTheme.textStyle.copyWith(
|
||||
fontSize: 10,
|
||||
fontSize: 12,
|
||||
color: MediaQuery.of(context).boldText ? FOREGROUND_WHITE : foregroundColor,
|
||||
),
|
||||
),
|
||||
|
@ -247,16 +254,13 @@ class ArrivalTime extends StatelessWidget {
|
|||
}
|
||||
else {
|
||||
final delay = station.arrival!.status?.delay ?? 0;
|
||||
final time = station.arrival!.scheduleTime;
|
||||
final time = DateTime.parse(station.arrival!.scheduleTime);
|
||||
|
||||
if (delay == 0) {
|
||||
return Text("$time");
|
||||
return Text("${time.hour.toString().padLeft(2, "0")}:${time.minute.toString().padLeft(2, "0")}");
|
||||
}
|
||||
else if (delay > 0) {
|
||||
final splits = time.split(":").map((s) => int.parse(s)).toList();
|
||||
|
||||
final now = DateTime.now();
|
||||
final oldDate = DateTime(now.year, now.month, now.day, splits[0], splits[1]);
|
||||
final oldDate = time;
|
||||
final newDate = oldDate.add(Duration(minutes: delay));
|
||||
|
||||
return Column(
|
||||
|
@ -278,10 +282,7 @@ class ArrivalTime extends StatelessWidget {
|
|||
);
|
||||
}
|
||||
else {
|
||||
final splits = time.split(":").map((s) => int.parse(s)).toList();
|
||||
|
||||
final now = DateTime.now();
|
||||
final oldDate = DateTime(now.year, now.month, now.day, splits[0], splits[1]);
|
||||
final oldDate = time;
|
||||
final newDate = oldDate.add(Duration(minutes: delay));
|
||||
|
||||
return Column(
|
||||
|
@ -326,21 +327,26 @@ class StopTime extends StatelessWidget {
|
|||
Builder(
|
||||
builder: (context) {
|
||||
int stopsForInt = stopsFor;
|
||||
bool minutes = false;
|
||||
if (stopsForInt >= 60) {
|
||||
stopsForInt ~/= 60;
|
||||
minutes = true;
|
||||
}
|
||||
if (stopsForInt == 1) {
|
||||
return Text(
|
||||
"1 minut",
|
||||
minutes ? '1 minut' : '1 secundă',
|
||||
textAlign: TextAlign.center,
|
||||
);
|
||||
}
|
||||
else if (stopsForInt < 20) {
|
||||
return Text(
|
||||
"$stopsFor minute",
|
||||
'$stopsForInt ' + (minutes ? 'minute' : 'seconde'),
|
||||
textAlign: TextAlign.center,
|
||||
);
|
||||
}
|
||||
else {
|
||||
return Text(
|
||||
"$stopsFor de minute",
|
||||
'$stopsForInt de ' + (minutes ? 'minute' : 'secunde'),
|
||||
textAlign: TextAlign.center,
|
||||
);
|
||||
}
|
||||
|
@ -381,16 +387,13 @@ class DepartureTime extends StatelessWidget {
|
|||
}
|
||||
else {
|
||||
final delay = station.departure!.status?.delay ?? 0;
|
||||
final time = station.departure!.scheduleTime;
|
||||
final time = DateTime.parse(station.departure!.scheduleTime);
|
||||
|
||||
if (delay == 0) {
|
||||
return Text("$time");
|
||||
return Text("${time.hour.toString().padLeft(2, "0")}:${time.minute.toString().padLeft(2, "0")}");
|
||||
}
|
||||
else if (delay > 0) {
|
||||
final splits = time.split(":").map((s) => int.parse(s)).toList();
|
||||
|
||||
final now = DateTime.now();
|
||||
final oldDate = DateTime(now.year, now.month, now.day, splits[0], splits[1]);
|
||||
final oldDate = time;
|
||||
final newDate = oldDate.add(Duration(minutes: delay));
|
||||
|
||||
return Column(
|
||||
|
@ -412,10 +415,7 @@ class DepartureTime extends StatelessWidget {
|
|||
);
|
||||
}
|
||||
else {
|
||||
final splits = time.split(":").map((s) => int.parse(s)).toList();
|
||||
|
||||
final now = DateTime.now();
|
||||
final oldDate = DateTime(now.year, now.month, now.day, splits[0], splits[1]);
|
||||
final oldDate = time;
|
||||
final newDate = oldDate.add(Duration(minutes: delay));
|
||||
|
||||
return Column(
|
||||
|
@ -460,7 +460,7 @@ class Delay extends StatelessWidget {
|
|||
if (delay == 0 || delay == null) return Container();
|
||||
else if (delay > 0) {
|
||||
return Text(
|
||||
"$delay minute întârziere",
|
||||
"$delay ${delay == 1 ? 'minut' : 'minute'} întârziere",
|
||||
style: CupertinoTheme.of(context).textTheme.textStyle.copyWith(
|
||||
color: CupertinoColors.destructiveRed,
|
||||
fontSize: 14,
|
||||
|
@ -470,7 +470,7 @@ class Delay extends StatelessWidget {
|
|||
}
|
||||
else if (delay < 0) {
|
||||
return Text(
|
||||
"${-delay} minute mai devreme",
|
||||
"${-delay} ${delay == -1 ? 'minut' : 'minute'} mai devreme",
|
||||
style: CupertinoTheme.of(context).textTheme.textStyle.copyWith(
|
||||
color: CupertinoColors.activeGreen,
|
||||
fontSize: 14,
|
||||
|
|
|
@ -75,12 +75,18 @@ class TrainInfoMaterial extends StatelessWidget {
|
|||
body: Column(
|
||||
children: <Widget>[
|
||||
if (isSmallScreen(context))
|
||||
SlimAppBar(
|
||||
title: 'INFO TREN - ${trainData.rank} ${trainData.number}'
|
||||
SafeArea(
|
||||
bottom: false,
|
||||
left: false,
|
||||
right: false,
|
||||
child: SlimAppBar(
|
||||
title: 'INFO TREN - ${trainData.rank} ${trainData.number}'
|
||||
),
|
||||
),
|
||||
Expanded(
|
||||
child: SafeArea(
|
||||
bottom: false,
|
||||
top: isSmallScreen(context) ? false : true,
|
||||
child: RefreshIndicator(
|
||||
onRefresh: refresh ?? () async {},
|
||||
child: CustomScrollView(
|
||||
|
@ -114,7 +120,8 @@ class TrainInfoMaterial extends StatelessWidget {
|
|||
child: Row(
|
||||
children: <Widget>[
|
||||
// Expanded(child: DisplayTrainNextStop(trainData: trainData,)),
|
||||
Expanded(child: DisplayTrainDestination(trainData: trainData,)),
|
||||
// Expanded(child: DisplayTrainDestination(trainData: trainData,)),
|
||||
Expanded(child: DisplayTrainRouteDuration(trainData: trainData,)),
|
||||
Expanded(child: DisplayTrainRouteDistance(trainData: trainData,),),
|
||||
],
|
||||
),
|
||||
|
@ -165,8 +172,19 @@ class DisplayTrainID extends StatelessWidget {
|
|||
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
return Text(
|
||||
"${trainData.rank} ${trainData.number}",
|
||||
return Text.rich(
|
||||
TextSpan(
|
||||
children: [
|
||||
TextSpan(
|
||||
text: trainData.rank,
|
||||
style: TextStyle(
|
||||
color: trainData.rank.startsWith('IR') ? Color.fromARGB(255, 255, 0, 0) : null,
|
||||
),
|
||||
),
|
||||
TextSpan(text: ' '),
|
||||
TextSpan(text: trainData.number,),
|
||||
],
|
||||
),
|
||||
style: (isSmallScreen(context)
|
||||
? Theme.of(context).textTheme.headline4
|
||||
: Theme.of(context).textTheme.headline3)?.copyWith(
|
||||
|
@ -205,29 +223,31 @@ class DisplayTrainRoute extends StatelessWidget {
|
|||
Widget build(BuildContext context) {
|
||||
return Row(
|
||||
children: <Widget>[
|
||||
Center(
|
||||
child: Padding(
|
||||
padding: const EdgeInsets.all(4),
|
||||
child: Text(
|
||||
trainData.route.from,
|
||||
style: Theme.of(context).textTheme.bodyText2?.copyWith(
|
||||
fontSize: 16,
|
||||
Expanded(
|
||||
child: Center(
|
||||
child: Padding(
|
||||
padding: const EdgeInsets.all(4),
|
||||
child: Text(
|
||||
trainData.route.from,
|
||||
style: Theme.of(context).textTheme.bodyText2?.copyWith(
|
||||
fontSize: 16,
|
||||
),
|
||||
),
|
||||
),
|
||||
),
|
||||
),
|
||||
Expanded(child: Container(),),
|
||||
Center(child: Text("-")),
|
||||
Expanded(child: Container(),),
|
||||
Center(
|
||||
child: Padding(
|
||||
padding: const EdgeInsets.all(4),
|
||||
child: Text(
|
||||
trainData.route.to,
|
||||
style: Theme.of(context).textTheme.bodyText2?.copyWith(
|
||||
fontSize: 16,
|
||||
Expanded(
|
||||
child: Center(
|
||||
child: Padding(
|
||||
padding: const EdgeInsets.all(4),
|
||||
child: Text(
|
||||
trainData.route.to,
|
||||
style: Theme.of(context).textTheme.bodyText2?.copyWith(
|
||||
fontSize: 16,
|
||||
),
|
||||
textAlign: TextAlign.right,
|
||||
),
|
||||
textAlign: TextAlign.right,
|
||||
),
|
||||
),
|
||||
),
|
||||
|
@ -336,7 +356,7 @@ class DisplayTrainLastInfo extends StatelessWidget {
|
|||
|
||||
if (data > 0) {
|
||||
return Text(
|
||||
"$data minute întârziere",
|
||||
"$data ${data == 1 ? 'minut' : 'minute'} întârziere",
|
||||
style: Theme.of(context).textTheme.bodyText2?.copyWith(
|
||||
fontSize: isSmallScreen(context) ? 14 : 16,
|
||||
color: Colors.red.shade300,
|
||||
|
@ -345,7 +365,7 @@ class DisplayTrainLastInfo extends StatelessWidget {
|
|||
}
|
||||
else {
|
||||
return Text(
|
||||
"${-data} minute mai devreme",
|
||||
"${-data} ${data == -1 ? 'minut' : 'minute'} mai devreme",
|
||||
style: Theme.of(context).textTheme.bodyText2?.copyWith(
|
||||
fontSize: isSmallScreen(context) ? 14 : 16,
|
||||
color: Colors.green.shade300,
|
||||
|
@ -486,11 +506,9 @@ class DisplayTrainDestination extends StatelessWidget {
|
|||
),
|
||||
Builder(
|
||||
builder: (context) {
|
||||
final arrival = destination.arrival!.scheduleTime;
|
||||
final arrival = DateTime.parse(destination.arrival!.scheduleTime);
|
||||
final delay = trainData.stations.last.arrival!.status?.delay ?? 0;
|
||||
final parts = arrival.split(':');
|
||||
final arrivalDT = DateTime(DateTime.now().year, DateTime.now().month, DateTime.now().day, int.parse(parts[0]), int.parse(parts[1]));
|
||||
final arrivalWithDelay = arrivalDT.add(Duration(minutes: delay));
|
||||
final arrivalWithDelay = arrival.add(Duration(minutes: delay));
|
||||
final arrivalWithDelayString = '${arrivalWithDelay.hour}:${arrivalWithDelay.minute.toString().padLeft(2, "0")}';
|
||||
// const months = ["ian", "feb", "mar", "apr", "mai", "iun", "iul", "aug", "sep", "oct", "noi", "dec"];
|
||||
|
||||
|
@ -511,7 +529,7 @@ class DisplayTrainDestination extends StatelessWidget {
|
|||
children: [
|
||||
TextSpan(text: ' '),
|
||||
TextSpan(
|
||||
text: '$arrival',
|
||||
text: '${arrival.hour.toString().padLeft(2, '0')}:${arrival.minute.toString().padLeft(2, '0')}',
|
||||
style: delay == 0 ? null : TextStyle(
|
||||
decoration: TextDecoration.lineThrough,
|
||||
),
|
||||
|
@ -581,82 +599,81 @@ class DisplayTrainRouteDistance extends StatelessWidget {
|
|||
}
|
||||
}
|
||||
|
||||
// class DisplayTrainRouteDuration extends StatelessWidget {
|
||||
// final TrainData trainData;
|
||||
//
|
||||
// DisplayTrainRouteDuration({required this.trainData});
|
||||
//
|
||||
// @override
|
||||
// Widget build(BuildContext context) {
|
||||
// return Card(
|
||||
// child: Center(
|
||||
// child: Padding(
|
||||
// padding: const EdgeInsets.all(2),
|
||||
// child: Column(
|
||||
// mainAxisSize: MainAxisSize.min,
|
||||
// children: <Widget>[
|
||||
// Text(
|
||||
// "Durata rutei",
|
||||
// style: Theme.of(context).textTheme.bodyText2?.copyWith(
|
||||
// fontSize: isSmallScreen(context) ? 16 : 18,
|
||||
// fontWeight: FontWeight.bold,
|
||||
// ),
|
||||
// textAlign: TextAlign.center,
|
||||
// ),
|
||||
// FutureDisplay<Duration>(
|
||||
// future: trainData.routeDuration,
|
||||
// builder: (context, duration) {
|
||||
// var durationString = StringBuffer();
|
||||
//
|
||||
// bool firstWritten = false;
|
||||
//
|
||||
// if (duration.inDays > 0) {
|
||||
// firstWritten = true;
|
||||
// if (duration.inDays == 1) durationString.write("1 zi");
|
||||
// else durationString.write("${duration.inDays} zile");
|
||||
// duration -= Duration(days: duration.inDays);
|
||||
// }
|
||||
//
|
||||
// if (duration.inHours > 0) {
|
||||
// if (firstWritten) {
|
||||
// durationString.write(", ");
|
||||
// }
|
||||
// firstWritten = true;
|
||||
// if (duration.inHours == 1) durationString.write("1 oră");
|
||||
// else durationString.write("${duration.inHours} ore");
|
||||
// duration -= Duration(hours: duration.inHours);
|
||||
// }
|
||||
//
|
||||
// if (duration.inMinutes > 0) {
|
||||
// if (firstWritten) {
|
||||
// durationString.write(", ");
|
||||
// }
|
||||
// firstWritten = true;
|
||||
// if (duration.inMinutes == 1) durationString.write("1 minut");
|
||||
// else durationString.write("${duration.inMinutes} minute");
|
||||
// duration -= Duration(minutes: duration.inMinutes);
|
||||
// }
|
||||
//
|
||||
// return Text(
|
||||
// durationString.toString(),
|
||||
// style: Theme.of(context).textTheme.bodyText2?.copyWith(
|
||||
// fontSize: isSmallScreen(context) ? 14 : 16,
|
||||
// ),
|
||||
// textAlign: TextAlign.center,
|
||||
// );
|
||||
// },
|
||||
// ),
|
||||
// ],
|
||||
// ),
|
||||
// ),
|
||||
// ),
|
||||
// );
|
||||
// }
|
||||
// }
|
||||
class DisplayTrainRouteDuration extends StatelessWidget {
|
||||
final TrainData trainData;
|
||||
|
||||
DisplayTrainRouteDuration({required this.trainData});
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
return Card(
|
||||
child: Center(
|
||||
child: Padding(
|
||||
padding: const EdgeInsets.all(2),
|
||||
child: Column(
|
||||
mainAxisSize: MainAxisSize.min,
|
||||
children: <Widget>[
|
||||
Text(
|
||||
"Durata rutei",
|
||||
style: Theme.of(context).textTheme.bodyText2?.copyWith(
|
||||
fontSize: isSmallScreen(context) ? 20 : 22,
|
||||
fontWeight: FontWeight.bold,
|
||||
),
|
||||
textAlign: TextAlign.center,
|
||||
),
|
||||
Builder(
|
||||
builder: (context) {
|
||||
var duration = DateTime.parse(trainData.stations.last.arrival!.scheduleTime).difference(DateTime.parse(trainData.stations.first.departure!.scheduleTime));
|
||||
var durationString = StringBuffer();
|
||||
|
||||
bool firstWritten = false;
|
||||
|
||||
if (duration.inDays > 0) {
|
||||
firstWritten = true;
|
||||
if (duration.inDays == 1) durationString.write("1 zi");
|
||||
else durationString.write("${duration.inDays} zile");
|
||||
duration -= Duration(days: duration.inDays);
|
||||
}
|
||||
|
||||
if (duration.inHours > 0) {
|
||||
if (firstWritten) {
|
||||
durationString.write(", ");
|
||||
}
|
||||
firstWritten = true;
|
||||
if (duration.inHours == 1) durationString.write("1 oră");
|
||||
else durationString.write("${duration.inHours} ore");
|
||||
duration -= Duration(hours: duration.inHours);
|
||||
}
|
||||
|
||||
if (duration.inMinutes > 0) {
|
||||
if (firstWritten) {
|
||||
durationString.write(", ");
|
||||
}
|
||||
firstWritten = true;
|
||||
if (duration.inMinutes == 1) durationString.write("1 minut");
|
||||
else durationString.write("${duration.inMinutes} minute");
|
||||
duration -= Duration(minutes: duration.inMinutes);
|
||||
}
|
||||
|
||||
return Text(
|
||||
durationString.toString(),
|
||||
style: Theme.of(context).textTheme.bodyText2?.copyWith(
|
||||
fontSize: isSmallScreen(context) ? 18 : 20,
|
||||
),
|
||||
textAlign: TextAlign.center,
|
||||
);
|
||||
},
|
||||
),
|
||||
],
|
||||
),
|
||||
),
|
||||
),
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
class DisplayTrainStations extends StatelessWidget {
|
||||
final TrainData trainData;
|
||||
|
||||
DisplayTrainStations({required this.trainData});
|
||||
|
||||
@override
|
||||
|
|
|
@ -46,8 +46,9 @@ class DisplayTrainStation extends StatelessWidget {
|
|||
final isOnTime = delay <= 0 && real == true;
|
||||
final isNotScheduled = false;
|
||||
|
||||
return KmBadge(
|
||||
station: station,
|
||||
return Badge(
|
||||
text: station.km.toString(),
|
||||
caption: 'km',
|
||||
isNotScheduled: isNotScheduled,
|
||||
isDelayed: isDelayed,
|
||||
isOnTime: isOnTime,
|
||||
|
@ -59,6 +60,10 @@ class DisplayTrainStation extends StatelessWidget {
|
|||
station: station,
|
||||
),
|
||||
),
|
||||
if (station.platform == null)
|
||||
Container(width: isSmallScreen(context) ? 42 : 48, height: isSmallScreen(context) ? 42 : 48,)
|
||||
else
|
||||
Badge(text: station.platform!, caption: 'linia',),
|
||||
],
|
||||
),
|
||||
Time(
|
||||
|
@ -74,14 +79,16 @@ class DisplayTrainStation extends StatelessWidget {
|
|||
}
|
||||
}
|
||||
|
||||
class KmBadge extends StatelessWidget {
|
||||
final Station station;
|
||||
class Badge extends StatelessWidget {
|
||||
final String text;
|
||||
final String caption;
|
||||
final bool isNotScheduled;
|
||||
final bool isOnTime;
|
||||
final bool isDelayed;
|
||||
|
||||
KmBadge({
|
||||
required this.station,
|
||||
Badge({
|
||||
required this.text,
|
||||
required this.caption,
|
||||
this.isNotScheduled = false,
|
||||
this.isOnTime = false,
|
||||
this.isDelayed = false,
|
||||
|
@ -124,7 +131,7 @@ class KmBadge extends StatelessWidget {
|
|||
Expanded(
|
||||
child: Center(
|
||||
child: Text(
|
||||
station.km.toString(),
|
||||
text,
|
||||
style: Theme.of(context).textTheme.bodyText2?.copyWith(
|
||||
fontSize: isSmallScreen(context) ? 16 : 20,
|
||||
fontWeight: MediaQuery.of(context).boldText ? FontWeight.w400 : FontWeight.w200,
|
||||
|
@ -135,7 +142,7 @@ class KmBadge extends StatelessWidget {
|
|||
),
|
||||
),
|
||||
Text(
|
||||
"km",
|
||||
caption,
|
||||
style: Theme.of(context).textTheme.bodyText2?.copyWith(
|
||||
fontSize: 10,
|
||||
color: MediaQuery.of(context).boldText ? Colors.white70 : foregroundColor,
|
||||
|
@ -254,16 +261,13 @@ class ArrivalTime extends StatelessWidget {
|
|||
}
|
||||
else {
|
||||
final delay = station.arrival!.status?.delay ?? 0;
|
||||
final time = station.arrival!.scheduleTime;
|
||||
final time = DateTime.parse(station.arrival!.scheduleTime);
|
||||
|
||||
if (delay == 0) {
|
||||
return Text("$time");
|
||||
return Text("${time.hour.toString().padLeft(2, '0')}:${time.minute.toString().padLeft(2, '0')}");
|
||||
}
|
||||
else if (delay > 0) {
|
||||
final splits = time.split(":").map((s) => int.parse(s)).toList();
|
||||
|
||||
final now = DateTime.now();
|
||||
final oldDate = DateTime(now.year, now.month, now.day, splits[0], splits[1]);
|
||||
final oldDate = time;
|
||||
final newDate = oldDate.add(Duration(minutes: delay));
|
||||
|
||||
return Column(
|
||||
|
@ -285,10 +289,7 @@ class ArrivalTime extends StatelessWidget {
|
|||
);
|
||||
}
|
||||
else {
|
||||
final splits = time.split(":").map((s) => int.parse(s)).toList();
|
||||
|
||||
final now = DateTime.now();
|
||||
final oldDate = DateTime(now.year, now.month, now.day, splits[0], splits[1]);
|
||||
final oldDate = time;
|
||||
final newDate = oldDate.add(Duration(minutes: delay));
|
||||
|
||||
return Column(
|
||||
|
@ -332,21 +333,26 @@ class StopTime extends StatelessWidget {
|
|||
Builder(
|
||||
builder: (context) {
|
||||
int stopsForInt = station.stoppingTime!;
|
||||
bool minutes = false;
|
||||
if (stopsForInt >= 60) {
|
||||
stopsForInt ~/= 60;
|
||||
minutes = true;
|
||||
}
|
||||
if (stopsForInt == 1) {
|
||||
return Text(
|
||||
"1 minut",
|
||||
"1 " + (minutes ? 'minut' : 'secundă'),
|
||||
textAlign: TextAlign.center,
|
||||
);
|
||||
}
|
||||
else if (stopsForInt < 20) {
|
||||
return Text(
|
||||
"${station.stoppingTime} minute",
|
||||
"$stopsForInt ${minutes ? 'minute' : 'secunde'}",
|
||||
textAlign: TextAlign.center,
|
||||
);
|
||||
}
|
||||
else {
|
||||
return Text(
|
||||
"${station.stoppingTime} de minute",
|
||||
"$stopsForInt de ${minutes ? 'minute' : 'secunde'}",
|
||||
textAlign: TextAlign.center,
|
||||
);
|
||||
}
|
||||
|
@ -390,16 +396,13 @@ class DepartureTime extends StatelessWidget {
|
|||
}
|
||||
else {
|
||||
final delay = station.departure!.status?.delay ?? 0;
|
||||
final time = station.departure!.scheduleTime;
|
||||
final time = DateTime.parse(station.departure!.scheduleTime);
|
||||
|
||||
if (delay == 0) {
|
||||
return Text("$time");
|
||||
return Text("${time.hour.toString().padLeft(2, '0')}:${time.minute.toString().padLeft(2, '0')}");
|
||||
}
|
||||
else if (delay > 0) {
|
||||
final splits = time.split(":").map((s) => int.parse(s)).toList();
|
||||
|
||||
final now = DateTime.now();
|
||||
final oldDate = DateTime(now.year, now.month, now.day, splits[0], splits[1]);
|
||||
final oldDate = time;
|
||||
final newDate = oldDate.add(Duration(minutes: delay));
|
||||
|
||||
return Column(
|
||||
|
@ -421,10 +424,7 @@ class DepartureTime extends StatelessWidget {
|
|||
);
|
||||
}
|
||||
else {
|
||||
final splits = time.split(":").map((s) => int.parse(s)).toList();
|
||||
|
||||
final now = DateTime.now();
|
||||
final oldDate = DateTime(now.year, now.month, now.day, splits[0], splits[1]);
|
||||
final oldDate = time;
|
||||
final newDate = oldDate.add(Duration(minutes: delay));
|
||||
|
||||
return Column(
|
||||
|
@ -470,7 +470,7 @@ class Delay extends StatelessWidget {
|
|||
if (delay == 0 || delay == null) return Container();
|
||||
else if (delay > 0) {
|
||||
return Text(
|
||||
"$delay minute întârziere",
|
||||
"$delay ${delay == 1 ? 'minut' : 'minute'} întârziere",
|
||||
style: Theme.of(context).textTheme.bodyText2?.copyWith(
|
||||
color: Colors.red.shade300,
|
||||
fontSize: 14,
|
||||
|
@ -480,7 +480,7 @@ class Delay extends StatelessWidget {
|
|||
}
|
||||
else if (delay < 0) {
|
||||
return Text(
|
||||
"${-delay} minute mai devreme",
|
||||
"${-delay} ${delay == -1 ? 'minut' : 'minute'} mai devreme",
|
||||
style: Theme.of(context).textTheme.bodyText2?.copyWith(
|
||||
color: Colors.green.shade300,
|
||||
fontSize: 14,
|
||||
|
|
|
@ -11,7 +11,7 @@ description: O aplicație de vizualizare a datelor puse la dispoziție de Inform
|
|||
# In iOS, build-name is used as CFBundleShortVersionString while build-number used as CFBundleVersion.
|
||||
# Read more about iOS versioning at
|
||||
# https://developer.apple.com/library/archive/documentation/General/Reference/InfoPlistKeyReference/Articles/CoreFoundationKeys.html
|
||||
version: 2.3.1
|
||||
version: 2.4.0
|
||||
|
||||
environment:
|
||||
sdk: ">=2.12.0 <3.0.0"
|
||||
|
|
Loading…
Add table
Reference in a new issue