Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Consolidate receipt_overlay and loading_overlay #511

Merged
merged 6 commits into from
Sep 28, 2023
Merged
Show file tree
Hide file tree
Changes from 2 commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
8 changes: 8 additions & 0 deletions lib/core/external/screen_brightness.dart
Original file line number Diff line number Diff line change
@@ -0,0 +1,8 @@
import 'package:screen_brightness/screen_brightness.dart' as sb;

class ScreenBrightness {
Future<void> setScreenBrightness(double brightness) async =>
sb.ScreenBrightness().setScreenBrightness(brightness);
Future<void> resetScreenBrightness() async =>
sb.ScreenBrightness().resetScreenBrightness();

Check warning on line 7 in lib/core/external/screen_brightness.dart

View check run for this annotation

Codecov / codecov/patch

lib/core/external/screen_brightness.dart#L4-L7

Added lines #L4 - L7 were not covered by tests
}
1 change: 0 additions & 1 deletion lib/core/network/network_request_executor_mapping.dart
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,6 @@ extension ExecutorMapX<R> on _ExecutorResult<R> {
extension ExecutorMapAllX<R> on _ExecutorResult<Iterable<R>> {
/// If the result of the [Future] is a [Right],
/// maps all values to a [List] of [C].
// TODO(marfavi): return Iterable instead of List?
_ExecutorResult<List<C>> mapAll<C>(C Function(R) mapper) async {
final result = await this;
return result.map((items) => items.map(mapper).toList());
Expand Down
6 changes: 5 additions & 1 deletion lib/core/strings.dart
Original file line number Diff line number Diff line change
Expand Up @@ -243,8 +243,12 @@
static const voucherCode = 'Voucher code';
static const voucherEmpty = 'Enter a voucher code';
static const voucherUsed = 'That voucher is already used';
static const youRedeemed = 'You redeemed';
static const voucherRedeemed = 'Voucher redeemed 🎉';
static String voucherYouRedeemedProducts(

Check warning on line 247 in lib/core/strings.dart

View check run for this annotation

Codecov / codecov/patch

lib/core/strings.dart#L247

Added line #L247 was not covered by tests
int numberOfTickets,
String productName,
) =>
'You redeemed $numberOfTickets $productName!';

Check warning on line 251 in lib/core/strings.dart

View check run for this annotation

Codecov / codecov/patch

lib/core/strings.dart#L251

Added line #L251 was not covered by tests

// Settings
static const settingsPageTitle = 'Settings';
Expand Down
40 changes: 21 additions & 19 deletions lib/core/widgets/components/loading_overlay.dart
Original file line number Diff line number Diff line change
@@ -1,24 +1,26 @@
import 'package:coffeecard/core/styles/app_colors.dart';
import 'package:flutter/material.dart';

void showLoadingOverlay(BuildContext context) {
final _ = showDialog(
context: context,
barrierColor: AppColors.scrim,
barrierDismissible: false,
useRootNavigator: true,
builder: (_) {
return WillPopScope(
// Will prevent Android back button from closing overlay.
onWillPop: () async => false,
child: const Center(
child: CircularProgressIndicator(color: AppColors.white),
),
);
},
);
}
class LoadingOverlay {
static void show(BuildContext context) {
fremartini marked this conversation as resolved.
Show resolved Hide resolved
final _ = showAdaptiveDialog(
context: context,
barrierColor: AppColors.scrim,
barrierDismissible: false,
useRootNavigator: true,
builder: (_) {
return WillPopScope(
// Will prevent Android back button from closing overlay.
onWillPop: () async => false,
child: const Center(
child: CircularProgressIndicator(color: AppColors.white),
),
);
},
);
}

void hideLoadingOverlay(BuildContext context) {
Navigator.of(context, rootNavigator: true).pop();
static void hide(BuildContext context) {
Navigator.of(context, rootNavigator: true).pop();
}
}
4 changes: 2 additions & 2 deletions lib/core/widgets/pages/splash/splash_error_page.dart
Original file line number Diff line number Diff line change
Expand Up @@ -43,12 +43,12 @@ class _SplashErrorPageState extends State<SplashErrorPage> {
onPressed: () async {
final environmentLoaded =
context.read<EnvironmentCubit>().getConfig();
showLoadingOverlay(context);
LoadingOverlay.show(context);
// Delay since it is otherwise not obvious
// a load is happening with no internet
final _ = await Future.delayed(const Duration(milliseconds: 200));
await environmentLoaded;
if (mounted) hideLoadingOverlay(context);
if (mounted) LoadingOverlay.hide(context);
},
child: Text(
Strings.retry,
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -68,9 +68,9 @@ class _LoginPagePasscodeState extends State<LoginPagePasscode> {
previous is LoginLoading || current is LoginLoading,
listener: (context, state) {
if (state is LoginLoading) {
showLoadingOverlay(context);
LoadingOverlay.show(context);
} else {
hideLoadingOverlay(context);
LoadingOverlay.hide(context);
}
},
buildWhen: (_, current) => current is! LoginLoading,
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -50,7 +50,7 @@ class ForgotPasscodeForm extends StatelessWidget {
}

Future<void> _onSubmit(BuildContext context, String email) async {
showLoadingOverlay(context);
LoadingOverlay.show(context);

final either =
await sl<AccountRemoteDataSource>().requestPasscodeReset(email);
Expand All @@ -74,7 +74,7 @@ class ForgotPasscodeForm extends StatelessWidget {
TextButton(
onPressed: () {
closeAppDialog(context);
hideLoadingOverlay(context);
LoadingOverlay.hide(context);
// Exits the forgot passcode flow
Navigator.pop(context);
},
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -116,12 +116,13 @@ class BuyTicketsPage extends StatelessWidget {
final updateReceiptsRequest =
context.read<ReceiptCubit>().fetchReceipts();

ReceiptOverlay.of(context).show(
ReceiptOverlay.show(
isTestEnvironment:
envState is EnvironmentLoaded && envState.env.isTest,
status: Strings.purchased,
productName: payment.productName,
timeUsed: payment.purchaseTime,
context: context,
);
await updateTicketsRequest;
await updateReceiptsRequest;
Expand Down
27 changes: 11 additions & 16 deletions lib/features/receipt/presentation/widgets/receipt_overlay.dart
Original file line number Diff line number Diff line change
@@ -1,30 +1,31 @@
import 'package:coffeecard/core/external/screen_brightness.dart';
import 'package:coffeecard/core/strings.dart';
import 'package:coffeecard/core/styles/app_colors.dart';
import 'package:coffeecard/core/styles/app_text_styles.dart';
import 'package:coffeecard/core/widgets/components/helpers/responsive.dart';
import 'package:coffeecard/features/receipt/presentation/widgets/receipt_card.dart';
import 'package:coffeecard/service_locator.dart';
import 'package:flutter/material.dart';
import 'package:gap/gap.dart';
import 'package:screen_brightness/screen_brightness.dart';

class ReceiptOverlay {
// TODO(marfavi): see if a more generic version can be made that supports both the loading overlay and this one, https://github.com/AnalogIO/coffeecard_app/issues/386
BuildContext _context;
static final ScreenBrightness screenBrightness = sl();

void hide() {
Navigator.of(_context).pop();
static void hide(BuildContext context) {
Navigator.of(context).pop();
}

Future<void> show({
static Future<void> show({
required String productName,
required DateTime timeUsed,
required bool isTestEnvironment,
required String status,
required BuildContext context,
}) async {
await ScreenBrightness().setScreenBrightness(1);
if (_context.mounted) {
await screenBrightness.setScreenBrightness(1);
if (context.mounted) {
final _ = await showDialog(
context: _context,
context: context,
barrierColor: AppColors.scrim,
builder: (context) {
return Padding(
Expand Down Expand Up @@ -52,12 +53,6 @@ class ReceiptOverlay {
},
);
}
await ScreenBrightness().resetScreenBrightness();
}

ReceiptOverlay.__create(this._context);

factory ReceiptOverlay.of(BuildContext context) {
return ReceiptOverlay.__create(context);
await screenBrightness.resetScreenBrightness();
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -79,7 +79,7 @@ class RegisterPageName extends StatelessWidget {
TextButton(
onPressed: () {
closeAppDialog(context);
hideLoadingOverlay(context);
LoadingOverlay.hide(context);
// Exits the register flow
Navigator.of(context, rootNavigator: true).pop();
},
Expand All @@ -104,7 +104,7 @@ class RegisterPageName extends StatelessWidget {
TextButton(
onPressed: () {
closeAppDialog(context);
hideLoadingOverlay(context);
LoadingOverlay.hide(context);
},
child: const Text(Strings.buttonClose),
),
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -40,7 +40,7 @@ class _RegisterNameFormState extends State<RegisterNameForm> {
}

Future<void> _showTerms(BuildContext context, String name) async {
showLoadingOverlay(context);
LoadingOverlay.show(context);
// Allow keyboard to disappear before showing dialog
final _ = await Future.delayed(const Duration(milliseconds: 350));
if (!mounted) return;
Expand All @@ -64,7 +64,7 @@ class _RegisterNameFormState extends State<RegisterNameForm> {
child: const Text(Strings.buttonDecline),
onPressed: () {
closeAppDialog(context);
if (mounted) hideLoadingOverlay(context);
if (mounted) LoadingOverlay.hide(context);
},
),
TextButton(
Expand Down
9 changes: 5 additions & 4 deletions lib/features/ticket/presentation/widgets/tickets_section.dart
Original file line number Diff line number Diff line change
Expand Up @@ -37,16 +37,16 @@ class TicketSection extends StatelessWidget {
Navigator.of(context, rootNavigator: true).pop();
}

showLoadingOverlay(context);
LoadingOverlay.show(context);
}
if (state is TicketUsed) {
// Refresh or load user info (for updated rank stats)
// (also refreshes leaderboard)
context.read<UserCubit>().fetchUserDetails();

final envState = context.read<EnvironmentCubit>().state;
hideLoadingOverlay(context);
ReceiptOverlay.of(context).show(
LoadingOverlay.hide(context);
ReceiptOverlay.show(
isTestEnvironment:
envState is EnvironmentLoaded && envState.env.isTest,
status: state.receipt is PurchaseReceipt
Expand All @@ -56,10 +56,11 @@ class TicketSection extends StatelessWidget {
: Strings.swiped,
productName: state.receipt.productName,
timeUsed: state.receipt.timeUsed,
context: context,
);
}
if (state is TicketsUseError) {
hideLoadingOverlay(context);
LoadingOverlay.hide(context);
appDialog(
context: context,
title: Strings.error,
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -25,8 +25,8 @@ class RedeemVoucherPage extends StatelessWidget {
create: (_) => sl<VoucherCubit>(),
child: BlocListener<VoucherCubit, VoucherState>(
listener: (context, state) {
if (state is VoucherLoading) return showLoadingOverlay(context);
hideLoadingOverlay(context);
if (state is VoucherLoading) return LoadingOverlay.show(context);
LoadingOverlay.hide(context);
if (state is VoucherSuccess) return _onSuccess(context, state);
if (state is VoucherError) return _onError(context, state);
},
Expand Down Expand Up @@ -55,7 +55,10 @@ class RedeemVoucherPage extends StatelessWidget {
],
children: [
Text(
'${Strings.youRedeemed} ${state.redeemedVoucher.numberOfTickets} ${state.redeemedVoucher.productName}!',
Strings.voucherYouRedeemedProducts(
state.redeemedVoucher.numberOfTickets,
state.redeemedVoucher.productName,
),
style: AppTextStyle.settingKey,
),
],
Expand Down
3 changes: 2 additions & 1 deletion lib/service_locator.dart
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@ import 'package:chopper/chopper.dart';
import 'package:coffeecard/core/api_uri_constants.dart';
import 'package:coffeecard/core/external/date_service.dart';
import 'package:coffeecard/core/external/external_url_launcher.dart';
import 'package:coffeecard/core/external/screen_brightness.dart';
import 'package:coffeecard/core/firebase_analytics_event_logging.dart';
import 'package:coffeecard/core/ignore_value.dart';
import 'package:coffeecard/core/network/network_request_executor.dart';
Expand Down Expand Up @@ -118,7 +119,7 @@ void configureServices() {
);

ignoreValue(sl.registerFactory(() => DateService()));

ignoreValue(sl.registerFactory(() => ScreenBrightness()));
ignoreValue(sl.registerLazySingleton(() => ExternalUrlLauncher()));

// provide the account repository to the reactivation authenticator
Expand Down
Loading