201 lines
6.1 KiB
Dart
201 lines
6.1 KiB
Dart
import 'dart:convert';
|
|
|
|
import 'package:checker/base/base_screen.dart';
|
|
import 'package:checker/base/base_state.dart';
|
|
import 'package:checker/db.dart';
|
|
import 'package:checker/strings.dart';
|
|
import 'package:flutter/material.dart';
|
|
import 'package:checker/network.dart';
|
|
import 'package:http/http.dart';
|
|
import 'package:intl/intl.dart';
|
|
|
|
class ReturnScreen extends BaseScreen {
|
|
final int userId;
|
|
final int bonus;
|
|
|
|
ReturnScreen(SqliteHelper helper, String app, this.userId, this.bonus) : super(helper, app);
|
|
|
|
@override
|
|
_ReturnScreenState createState() => _ReturnScreenState<ReturnScreen>(helper, app);
|
|
}
|
|
|
|
class _ReturnScreenState<T> extends BaseState<ReturnScreen> {
|
|
static DateFormat dateFormat = DateFormat('d MMM yy');
|
|
|
|
ScrollController _controller;
|
|
List _purchases = [];
|
|
int _bonus;
|
|
int _page = 1;
|
|
bool _fullLoaded = false;
|
|
bool _loading = false;
|
|
|
|
|
|
_ReturnScreenState(SqliteHelper helper, String app) : super(helper, app);
|
|
|
|
bool isAutomaticallyImplyLeading() => true;
|
|
|
|
@override
|
|
Widget getScreenContent() => ListView.separated(
|
|
itemBuilder: (context, index) {
|
|
final TextStyle style = Theme.of(context).textTheme.subhead;
|
|
if(index > 0) {
|
|
final item = _purchases[index - 1];
|
|
final DateTime date = DateTime.parse(item['date']);
|
|
final String formattedDate = dateFormat.format(date);
|
|
return GestureDetector(
|
|
child: Padding(
|
|
padding: const EdgeInsets.all(16),
|
|
child: Row(
|
|
children: <Widget>[
|
|
Expanded(
|
|
child: Text(formattedDate, style: style),
|
|
),
|
|
Expanded(
|
|
child: Text(item['sum_total'], style: style),
|
|
),
|
|
Expanded(
|
|
child: Text(item['sum_bonus'].toString(), style: style),
|
|
)
|
|
],
|
|
),
|
|
),
|
|
onTap: () => _confirmReturnPurchase(item, formattedDate),
|
|
);
|
|
} else {
|
|
final TextStyle headerStyle = style.copyWith(color: Colors.grey);
|
|
return Padding(
|
|
padding: const EdgeInsets.all(16),
|
|
child: Row(
|
|
children: <Widget>[
|
|
Expanded(
|
|
child: Container(),
|
|
),
|
|
Expanded(
|
|
child: Text(StringsLocalization.sum(), style: headerStyle),
|
|
),
|
|
Expanded(
|
|
child: Text(StringsLocalization.points(), style: headerStyle),
|
|
)
|
|
],
|
|
),
|
|
);
|
|
}
|
|
},
|
|
separatorBuilder: (_, index) => index == 0
|
|
? Container()
|
|
: Padding(
|
|
padding: const EdgeInsets.symmetric(horizontal: 16),
|
|
child: Divider(height: 1,),
|
|
),
|
|
itemCount: _purchases.length > 0 ? _purchases.length + 1 : _purchases.length,
|
|
controller: _controller);
|
|
|
|
@override
|
|
Widget build(BuildContext context) => getMainWidget();
|
|
|
|
@override
|
|
String getTitle() => StringsLocalization.returnLabel();
|
|
|
|
@override
|
|
void initState() {
|
|
super.initState();
|
|
setState(() {
|
|
loading = true;
|
|
});
|
|
_loadUserPurchases();
|
|
_bonus = widget.bonus;
|
|
_controller = ScrollController();
|
|
_controller.addListener(_scrollListener);
|
|
}
|
|
|
|
void _scrollListener() {
|
|
if (_controller.offset >= _controller.position.maxScrollExtent &&
|
|
!_controller.position.outOfRange) {
|
|
_loadUserPurchases();
|
|
}
|
|
}
|
|
|
|
void _loadUserPurchases() async {
|
|
if(!_fullLoaded && !_loading) {
|
|
_loading = true;
|
|
setState(() => loading = true);
|
|
String token = await helper.getToken();
|
|
Response response = await getUserPurchases(token, widget.userId, _page);
|
|
final responseJson = json.decode(response.body);
|
|
List purchases = responseJson['results'];
|
|
_fullLoaded = _page == responseJson['pages'];
|
|
setState(() {
|
|
loading = false;
|
|
_purchases.addAll(purchases);
|
|
});
|
|
_page++;
|
|
_loading = false;
|
|
setState(() => loading = false);
|
|
}
|
|
}
|
|
|
|
num extractReturnPoints(Map purchase) {
|
|
final returnPoints = purchase['sum_bonus'];
|
|
if(returnPoints is num) {
|
|
return returnPoints;
|
|
} else if(returnPoints is String) {
|
|
final RegExp returnPattern = RegExp(r"(\d+)");
|
|
final List<Match> digits = returnPattern.allMatches(returnPoints).toList();
|
|
return int.parse(digits[0].group(0)) - int.parse(digits[1].group(1));
|
|
} else {
|
|
return 0;
|
|
}
|
|
}
|
|
|
|
void _confirmReturnPurchase(Map purchase, String formattedDate) {
|
|
final num totalReturn = extractReturnPoints(purchase);
|
|
showDialog(
|
|
context: context,
|
|
builder: (context) =>
|
|
AlertDialog(
|
|
title: Text(StringsLocalization.confirmation()),
|
|
content: Text(StringsLocalization.returnConfirmation(
|
|
purchase['sum_total'], formattedDate, _bonus - totalReturn)),
|
|
actions: <Widget>[
|
|
FlatButton(
|
|
child: Text(StringsLocalization.no()),
|
|
onPressed: () => Navigator.pop(context),
|
|
),
|
|
FlatButton(
|
|
child: Text(StringsLocalization.yes()),
|
|
onPressed: () {
|
|
Navigator.pop(context);
|
|
_returnPurchase(purchase, formattedDate, totalReturn);
|
|
}
|
|
)
|
|
],
|
|
)
|
|
);
|
|
}
|
|
|
|
void _returnPurchase(Map purchase, String formattedDate, num totalReturn) async {
|
|
String token = await helper.getToken();
|
|
final Response response = await returnPurchase(token, widget.userId, purchase['id']);
|
|
if(response.statusCode == 204) {
|
|
_bonus += totalReturn;
|
|
setState(() {
|
|
_purchases.removeWhere((p) => p['id'] == purchase['id']);
|
|
});
|
|
showDialog(
|
|
context: context,
|
|
builder: (context) =>
|
|
AlertDialog(
|
|
title: Text(StringsLocalization.returnConfirmed()),
|
|
content: Text(StringsLocalization.returnConfirmedContent(purchase['sum_total'], formattedDate)),
|
|
actions: <Widget>[
|
|
FlatButton(
|
|
child: Text(StringsLocalization.yes()),
|
|
onPressed: () => Navigator.pop(context)
|
|
)
|
|
],
|
|
)
|
|
);
|
|
}
|
|
}
|
|
}
|