legacy device setup screen flow from account settings

This commit is contained in:
2026-03-11 13:11:11 +01:00
parent 53cadd8499
commit ffc0a1f103
8 changed files with 150 additions and 113 deletions

View File

@@ -1,16 +1,18 @@
import 'package:design_system/design_system.dart'; import 'package:design_system/design_system.dart';
import 'package:flutter/material.dart'; import 'package:flutter/material.dart';
import 'package:flutter_riverpod/flutter_riverpod.dart'; import 'package:flutter_riverpod/flutter_riverpod.dart';
import 'package:legacy_auth/legacy_auth.dart';
import 'package:legacy_shared/legacy_shared.dart'; import 'package:legacy_shared/legacy_shared.dart';
import 'package:navigation/navigation.dart'; import 'package:navigation/navigation.dart';
import 'package:sf_localizations/sf_localizations.dart'; import 'package:sf_localizations/sf_localizations.dart';
import 'package:url_launcher/url_launcher.dart'; import 'package:url_launcher/url_launcher.dart';
import 'package:utils/utils.dart'; import 'package:utils/utils.dart';
import 'package:flutter/services.dart';
import 'package:qr_flutter/qr_flutter.dart'; import 'widgets/reg_code_dialog.dart';
class AccountSettingsScreen extends ConsumerWidget { class AccountSettingsScreen extends ConsumerWidget {
final NavigationContract navigationContract; final NavigationContract navigationContract;
static final _privacyUrl = 'https://savefamilygps.com/pages/politica-de-privacidad-reloj-gps-infantil-localizador-savefamily';
const AccountSettingsScreen({super.key, required this.navigationContract}); const AccountSettingsScreen({super.key, required this.navigationContract});
@@ -21,7 +23,7 @@ class AccountSettingsScreen extends ConsumerWidget {
final selectedDevice = ref.watch(selectedDeviceProvider); final selectedDevice = ref.watch(selectedDeviceProvider);
return LegacyPageLayout( return LegacyPageLayout(
theme: theme, theme: theme,
title: context.translate(I18n.accountSettings), title: context.translate(I18n.accountSettings),
body: SingleChildScrollView(child: Container( body: SingleChildScrollView(child: Container(
padding: SizeUtils.getByScreen( padding: SizeUtils.getByScreen(
@@ -43,7 +45,16 @@ theme: theme,
), ),
SizedBox(height: SizeUtils.getByScreen(small: 16, big: 15)), SizedBox(height: SizeUtils.getByScreen(small: 16, big: 15)),
AppSectionButton( AppSectionButton(
onPressed: (){}, onPressed: (){
Navigator.of(context).push(
MaterialPageRoute(
builder: (_) => LegacyDeviceSetupScreen(
navigationContract: navigationContract,
isFirstDevice: false
),
),
);
},
icon: Icons.add_circle_outline, icon: Icons.add_circle_outline,
text: I18n.addNewSF text: I18n.addNewSF
), ),
@@ -62,7 +73,7 @@ theme: theme,
SizedBox(height: SizeUtils.getByScreen(small: 16, big: 15)), SizedBox(height: SizeUtils.getByScreen(small: 16, big: 15)),
AppSectionButton( AppSectionButton(
onPressed: () async { onPressed: () async {
final Uri url = Uri.parse('https://savefamilygps.com/pages/politica-de-privacidad-reloj-gps-infantil-localizador-savefamily'); final Uri url = Uri.parse(_privacyUrl);
if (!await launchUrl(url)) { if (!await launchUrl(url)) {
throw Exception('Could not launch $url'); throw Exception('Could not launch $url');
} }
@@ -161,102 +172,3 @@ class AppSectionButton extends ConsumerWidget {
); );
} }
} }
class RegCodeDialog extends StatelessWidget {
final String regCode;
final String deviceId;
final String name;
const RegCodeDialog({
super.key,
required this.regCode,
required this.deviceId,
required this.name,
});
@override
Widget build(BuildContext context) {
return Container(
height: SizeUtils.getByScreen(small: 330, big: 328),
color: Colors.transparent,
child: Stack(
children: [
Align(
alignment: Alignment.bottomCenter,
child: Container(
height: SizeUtils.getByScreen(small: 300, big: 298),
width: SizeUtils.getByScreen(small: 350, big: 348),
padding: SizeUtils.getByScreen(
small: EdgeInsets.symmetric(vertical: 14, horizontal: 18),
big: EdgeInsets.symmetric(vertical: 12, horizontal: 16)
),
color: Colors.white,
child: Column(
mainAxisAlignment: MainAxisAlignment.end,
children: [
Align(
alignment: Alignment.topRight,
child: IconButton(
onPressed: (){Navigator.pop(context);},
icon: Icon(Icons.close),
padding: EdgeInsets.zero,
),
),
Text(name, style: TextStyle()),
Row(
mainAxisAlignment: MainAxisAlignment.center,
children: [
Text(context.translate(I18n.deviceIdLabel,
args: {'deviceId': deviceId})),
TextButton(
onPressed: (){Clipboard.setData(ClipboardData(text: deviceId));},
child: Text(context.translate(I18n.copy)),
)
],
),
QrImageView(
data: regCode,
version: QrVersions.auto,
size: SizeUtils.getByScreen(small: 100, big: 98),
padding: EdgeInsets.zero,
),
Row(
mainAxisAlignment: MainAxisAlignment.center,
children: [
Text(context.translate(I18n.regCodeLabel,
args: {'regCode': regCode})),
TextButton(
onPressed: (){Clipboard.setData(ClipboardData(text: regCode));},
child: Text(context.translate(I18n.copy))
)
],
)
],
),
),
),
Align(
alignment: Alignment.topCenter,
child: Container(
decoration: BoxDecoration(
shape: BoxShape.circle,
color: Color(0xFF00A1C6),
),
padding: SizeUtils.getByScreen(
small: EdgeInsets.all(12),
big: EdgeInsets.all(12)
),
child: Icon(
SFIcons.watch,
size: SizeUtils.getByScreen(small: 68, big: 66),
color: Colors.white,
),
)
),
],
),
);
}
}

View File

@@ -0,0 +1,104 @@
import 'package:design_system/design_system.dart';
import 'package:flutter/material.dart';
import 'package:flutter/services.dart';
import 'package:qr_flutter/qr_flutter.dart';
import 'package:sf_localizations/sf_localizations.dart';
import 'package:utils/utils.dart';
class RegCodeDialog extends StatelessWidget {
final String regCode;
final String deviceId;
final String name;
const RegCodeDialog({
super.key,
required this.regCode,
required this.deviceId,
required this.name,
});
@override
Widget build(BuildContext context) {
return Container(
height: SizeUtils.getByScreen(small: 330, big: 328),
color: Colors.transparent,
child: Stack(
children: [
Align(
alignment: Alignment.bottomCenter,
child: Container(
height: SizeUtils.getByScreen(small: 300, big: 298),
width: SizeUtils.getByScreen(small: 350, big: 348),
padding: SizeUtils.getByScreen(
small: EdgeInsets.symmetric(vertical: 14, horizontal: 18),
big: EdgeInsets.symmetric(vertical: 12, horizontal: 16)
),
color: Colors.white,
child: Column(
mainAxisAlignment: MainAxisAlignment.end,
children: [
Align(
alignment: Alignment.topRight,
child: IconButton(
onPressed: (){Navigator.pop(context);},
icon: Icon(Icons.close),
padding: EdgeInsets.zero,
),
),
Text(name, style: TextStyle()),
Row(
mainAxisAlignment: MainAxisAlignment.center,
children: [
Text(context.translate(I18n.deviceIdLabel,
args: {'deviceId': deviceId})),
TextButton(
onPressed: (){Clipboard.setData(ClipboardData(text: deviceId));},
child: Text(context.translate(I18n.copy)),
)
],
),
QrImageView(
data: regCode,
version: QrVersions.auto,
size: SizeUtils.getByScreen(small: 100, big: 98),
padding: EdgeInsets.zero,
),
Row(
mainAxisAlignment: MainAxisAlignment.center,
children: [
Text(context.translate(I18n.regCodeLabel,
args: {'regCode': regCode})),
TextButton(
onPressed: (){Clipboard.setData(ClipboardData(text: regCode));},
child: Text(context.translate(I18n.copy))
)
],
)
],
),
),
),
Align(
alignment: Alignment.topCenter,
child: Container(
decoration: BoxDecoration(
shape: BoxShape.circle,
color: Color(0xFF00A1C6),
),
padding: SizeUtils.getByScreen(
small: EdgeInsets.all(12),
big: EdgeInsets.all(12)
),
child: Icon(
SFIcons.watch,
size: SizeUtils.getByScreen(small: 68, big: 66),
color: Colors.white,
),
)
),
],
),
);
}
}

View File

@@ -586,6 +586,13 @@ packages:
url: "https://pub.dev" url: "https://pub.dev"
source: hosted source: hosted
version: "3.0.2" version: "3.0.2"
legacy_auth:
dependency: "direct main"
description:
path: "../legacy_auth"
relative: true
source: path
version: "0.0.1"
legacy_shared: legacy_shared:
dependency: "direct main" dependency: "direct main"
description: description:

View File

@@ -24,7 +24,8 @@ dependencies:
flutter: flutter:
sdk: flutter sdk: flutter
#modules dependencies go here #modules dependencies go here
legacy_auth:
path: ../../modules/legacy_auth
#packages dependencies go here #packages dependencies go here
design_system: design_system:
path: ../../../../packages/design_system path: ../../../../packages/design_system

View File

@@ -1,3 +1,4 @@
# melos_managed_dependency_overrides: legacy_auth
# melos_managed_dependency_overrides: activity,auth,design_system,flutter_treezor_entrust_sdk_bridge,fonts,home,legacy_shared,navigation,notifications,payments,sca_treezor,sf_infrastructure,sf_localizations,sf_shared,utils # melos_managed_dependency_overrides: activity,auth,design_system,flutter_treezor_entrust_sdk_bridge,fonts,home,legacy_shared,navigation,notifications,payments,sca_treezor,sf_infrastructure,sf_localizations,sf_shared,utils
dependency_overrides: dependency_overrides:
activity: activity:
@@ -12,6 +13,8 @@ dependency_overrides:
path: ../../../../packages/fonts path: ../../../../packages/fonts
home: home:
path: ../../../home path: ../../../home
legacy_auth:
path: ..\\legacy_auth
legacy_shared: legacy_shared:
path: ../../packages/legacy_shared path: ../../packages/legacy_shared
navigation: navigation:

View File

@@ -4,6 +4,7 @@ export 'src/features/link_phone/presentation/verify_code/verify_link_phone_code_
export 'src/features/login/login_builder.dart'; export 'src/features/login/login_builder.dart';
export 'src/features/recover_password/presentation/request_recovery/request_recovery_builder.dart'; export 'src/features/recover_password/presentation/request_recovery/request_recovery_builder.dart';
export 'src/features/device_setup/device_setup_builder.dart'; export 'src/features/device_setup/device_setup_builder.dart';
export 'src/features/device_setup/presentation/device_setup_screen.dart';
export 'src/features/sign_up/sign_up_builder.dart'; export 'src/features/sign_up/sign_up_builder.dart';
export 'src/core/data/datasource/session_local_datasource.dart'; export 'src/core/data/datasource/session_local_datasource.dart';
export 'src/core/providers/auth_repository_provider.dart'; export 'src/core/providers/auth_repository_provider.dart';

View File

@@ -11,8 +11,13 @@ import 'package:sf_localizations/sf_localizations.dart';
class LegacyDeviceSetupScreen extends ConsumerWidget { class LegacyDeviceSetupScreen extends ConsumerWidget {
final NavigationContract navigationContract; final NavigationContract navigationContract;
final bool isFirstDevice;
const LegacyDeviceSetupScreen({super.key, required this.navigationContract}); const LegacyDeviceSetupScreen({
super.key,
required this.navigationContract,
this.isFirstDevice = true,
});
@override @override
Widget build(BuildContext context, WidgetRef ref) { Widget build(BuildContext context, WidgetRef ref) {
@@ -95,13 +100,17 @@ class LegacyDeviceSetupScreen extends ConsumerWidget {
final ok = await vm.createDevice(); final ok = await vm.createDevice();
if (!context.mounted) return; if (!context.mounted) return;
if (ok) { if (ok) {
Navigator.of(context).push( if (isFirstDevice){
MaterialPageRoute( Navigator.of(context).push(
builder: (_) => LegacySuccessScreen( MaterialPageRoute(
navigationContract: navigationContract, builder: (_) => LegacySuccessScreen(
navigationContract: navigationContract,
),
), ),
), );
); } else {
Navigator.pop(context);
}
} }
return; return;
} }

View File

@@ -12,7 +12,7 @@ Future<void> _pickBornAt(
FocusManager.instance.primaryFocus?.unfocus(); FocusManager.instance.primaryFocus?.unfocus();
final now = DateTime.now(); final now = DateTime.now();
final initial = currentBornAt ?? DateTime(now.year - 18, now.month, now.day); final initial = currentBornAt ?? DateTime(now.year - 4, now.month, now.day);
final safeInitial = initial.isAfter(now) ? now : initial; final safeInitial = initial.isAfter(now) ? now : initial;
final picked = await showDatePicker( final picked = await showDatePicker(