[mob][photos] added logic of Pin and Password screen
This commit is contained in:
@@ -72,7 +72,8 @@ class Configuration {
|
||||
"has_selected_all_folders_for_backup";
|
||||
static const anonymousUserIDKey = "anonymous_user_id";
|
||||
static const endPointKey = "endpoint";
|
||||
|
||||
static const password = "user_pass";
|
||||
static const pin = "user_pin";
|
||||
static final _logger = Logger("Configuration");
|
||||
|
||||
String? _cachedToken;
|
||||
@@ -151,6 +152,29 @@ class Configuration {
|
||||
}
|
||||
}
|
||||
|
||||
Future<void> savePin(String userPin) async {
|
||||
await _preferences.setString(pin, userPin);
|
||||
await _preferences.remove(password);
|
||||
}
|
||||
|
||||
Future<String?> loadSavedPin() async {
|
||||
return _preferences.getString(pin);
|
||||
}
|
||||
|
||||
Future<void> savePassword(String pass) async {
|
||||
await _preferences.setString(password, pass);
|
||||
await _preferences.remove(pin);
|
||||
}
|
||||
|
||||
Future<String?> loadSavedPassword() async {
|
||||
return _preferences.getString(password);
|
||||
}
|
||||
|
||||
Future<void> removePinAndPassword() async {
|
||||
await _preferences.remove(pin);
|
||||
await _preferences.remove(password);
|
||||
}
|
||||
|
||||
// _cleanUpStaleFiles deletes all files in the temp directory that are older
|
||||
// than kTempFolderDeletionTimeBuffer except the the temp encrypted files for upload.
|
||||
// Those file are deleted by file uploader after the upload is complete or those
|
||||
|
||||
80
mobile/lib/generated/l10n.dart
generated
80
mobile/lib/generated/l10n.dart
generated
@@ -60,86 +60,6 @@ class S {
|
||||
);
|
||||
}
|
||||
|
||||
/// `Device Lock`
|
||||
String get deviceLock {
|
||||
return Intl.message(
|
||||
'Device lock',
|
||||
name: 'deviceLock',
|
||||
desc: '',
|
||||
args: [],
|
||||
);
|
||||
}
|
||||
|
||||
/// `PIN Lock`
|
||||
String get pinLock {
|
||||
return Intl.message(
|
||||
'PIN lock',
|
||||
name: 'pinLock',
|
||||
desc: '',
|
||||
args: [],
|
||||
);
|
||||
}
|
||||
|
||||
/// `Enter the pin to lock the app`
|
||||
String get enterThePinToLockTheApp {
|
||||
return Intl.message(
|
||||
'Enter the pin to lock the app',
|
||||
name: 'enterThePinToLockTheApp',
|
||||
desc: '',
|
||||
args: [],
|
||||
);
|
||||
}
|
||||
|
||||
/// `Re-enter to confirm the pin`
|
||||
String get reEnterToConfirmPin {
|
||||
return Intl.message(
|
||||
'Re-enter to confirm the pin',
|
||||
name: 'reEnterToConfirmPin',
|
||||
desc: '',
|
||||
args: [],
|
||||
);
|
||||
}
|
||||
|
||||
/// `Enter the password to lock the app`
|
||||
String get enterPasswordToLockApp {
|
||||
return Intl.message(
|
||||
'Enter the password to lock the app',
|
||||
name: 'enterPasswordToLockApp',
|
||||
desc: '',
|
||||
args: [],
|
||||
);
|
||||
}
|
||||
|
||||
/// `Next`
|
||||
String get next {
|
||||
return Intl.message(
|
||||
'Next',
|
||||
name: 'next',
|
||||
desc: '',
|
||||
args: [],
|
||||
);
|
||||
}
|
||||
|
||||
/// `When a pin is set , you need to enter password\n whenever you open the app .`
|
||||
String get whenPinIsSetYouNeedToEnterPassword {
|
||||
return Intl.message(
|
||||
'When a pin is set , you need to enter password\n whenever you open the app .',
|
||||
name: 'whenPinIsSetYouNeedToEnterPassword',
|
||||
desc: '',
|
||||
args: [],
|
||||
);
|
||||
}
|
||||
|
||||
/// `Enable PIN`
|
||||
String get enablePin {
|
||||
return Intl.message(
|
||||
'Enable PIN',
|
||||
name: 'enablePin',
|
||||
desc: '',
|
||||
args: [],
|
||||
);
|
||||
}
|
||||
|
||||
/// `Welcome back!`
|
||||
String get accountWelcomeBack {
|
||||
return Intl.message(
|
||||
|
||||
@@ -3,7 +3,13 @@ import "dart:async";
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:local_auth/local_auth.dart';
|
||||
import 'package:photos/core/configuration.dart';
|
||||
import "package:photos/generated/l10n.dart";
|
||||
import "package:photos/ui/components/buttons/button_widget.dart";
|
||||
import "package:photos/ui/components/dialog_widget.dart";
|
||||
import "package:photos/ui/components/models/button_type.dart";
|
||||
import "package:photos/ui/settings/TEMP/lock_screen_option.dart";
|
||||
import "package:photos/ui/settings/TEMP/lock_screen_option_password.dart";
|
||||
import "package:photos/ui/settings/TEMP/lock_screen_option_pin.dart";
|
||||
import 'package:photos/ui/tools/app_lock.dart';
|
||||
import 'package:photos/utils/auth_util.dart';
|
||||
import 'package:photos/utils/dialog_util.dart';
|
||||
@@ -14,6 +20,8 @@ class LocalAuthenticationService {
|
||||
static final LocalAuthenticationService instance =
|
||||
LocalAuthenticationService._privateConstructor();
|
||||
|
||||
final Configuration _configuration = Configuration.instance;
|
||||
|
||||
Future<bool> requestLocalAuthentication(
|
||||
BuildContext context,
|
||||
String infoMessage,
|
||||
@@ -41,6 +49,87 @@ class LocalAuthenticationService {
|
||||
String errorDialogContent, [
|
||||
String errorDialogTitle = "",
|
||||
]) async {
|
||||
final String? savedPin = await _configuration.loadSavedPin();
|
||||
final String? savedPassword = await _configuration.loadSavedPassword();
|
||||
|
||||
if (savedPassword != null) {
|
||||
final result = await Navigator.of(context).push(
|
||||
MaterialPageRoute(
|
||||
builder: (BuildContext context) {
|
||||
return LockScreenOptionPassword(
|
||||
isAuthenticating: true,
|
||||
authPass: savedPassword,
|
||||
);
|
||||
},
|
||||
),
|
||||
);
|
||||
if (result) {
|
||||
await Navigator.of(context).push(
|
||||
MaterialPageRoute(
|
||||
builder: (BuildContext context) {
|
||||
return const LockScreenOption();
|
||||
},
|
||||
),
|
||||
);
|
||||
return true;
|
||||
} else {
|
||||
await showDialogWidget(
|
||||
context: context,
|
||||
title: 'Password does not match',
|
||||
icon: Icons.lock,
|
||||
body: 'Please re-enter the password.',
|
||||
isDismissible: true,
|
||||
buttons: [
|
||||
ButtonWidget(
|
||||
buttonType: ButtonType.secondary,
|
||||
labelText: S.of(context).ok,
|
||||
isInAlert: true,
|
||||
buttonAction: ButtonAction.first,
|
||||
),
|
||||
],
|
||||
);
|
||||
}
|
||||
return false;
|
||||
} else if (savedPin != null) {
|
||||
final result = await Navigator.of(context).push(
|
||||
MaterialPageRoute(
|
||||
builder: (BuildContext context) {
|
||||
return LockScreenOptionPin(
|
||||
isAuthenticating: true,
|
||||
authPin: savedPin,
|
||||
);
|
||||
},
|
||||
),
|
||||
);
|
||||
if (result) {
|
||||
await Navigator.of(context).push(
|
||||
MaterialPageRoute(
|
||||
builder: (BuildContext context) {
|
||||
return const LockScreenOption();
|
||||
},
|
||||
),
|
||||
);
|
||||
return true;
|
||||
} else {
|
||||
await showDialogWidget(
|
||||
context: context,
|
||||
title: 'Pin does not match',
|
||||
icon: Icons.lock,
|
||||
body: 'Please re-enter the pin.',
|
||||
isDismissible: true,
|
||||
buttons: [
|
||||
ButtonWidget(
|
||||
buttonType: ButtonType.secondary,
|
||||
labelText: S.of(context).ok,
|
||||
isInAlert: true,
|
||||
buttonAction: ButtonAction.first,
|
||||
),
|
||||
],
|
||||
);
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
if (await _isLocalAuthSupportedOnDevice()) {
|
||||
AppLock.of(context)!.disable();
|
||||
final result = await requestAuthentication(
|
||||
|
||||
@@ -52,8 +52,8 @@ class LockScreenOption extends StatelessWidget {
|
||||
bgColor: colorScheme.fillFaint,
|
||||
),
|
||||
MenuItemWidget(
|
||||
captionedTextWidget: CaptionedTextWidget(
|
||||
title: S.of(context).deviceLock,
|
||||
captionedTextWidget: const CaptionedTextWidget(
|
||||
title: 'Device Lock',
|
||||
),
|
||||
alignCaptionedTextToLeft: true,
|
||||
isTopBorderRadiusRemoved: true,
|
||||
@@ -67,8 +67,8 @@ class LockScreenOption extends StatelessWidget {
|
||||
bgColor: colorScheme.fillFaint,
|
||||
),
|
||||
MenuItemWidget(
|
||||
captionedTextWidget: CaptionedTextWidget(
|
||||
title: S.of(context).pinLock,
|
||||
captionedTextWidget: const CaptionedTextWidget(
|
||||
title: 'PIN lock',
|
||||
),
|
||||
alignCaptionedTextToLeft: true,
|
||||
isTopBorderRadiusRemoved: true,
|
||||
@@ -89,8 +89,8 @@ class LockScreenOption extends StatelessWidget {
|
||||
bgColor: colorScheme.fillFaint,
|
||||
),
|
||||
MenuItemWidget(
|
||||
captionedTextWidget: CaptionedTextWidget(
|
||||
title: S.of(context).passwordLock,
|
||||
captionedTextWidget: const CaptionedTextWidget(
|
||||
title: 'Password lock',
|
||||
),
|
||||
alignCaptionedTextToLeft: true,
|
||||
isTopBorderRadiusRemoved: true,
|
||||
|
||||
@@ -1,4 +1,5 @@
|
||||
import "package:flutter/material.dart";
|
||||
import "package:photos/core/configuration.dart";
|
||||
import "package:photos/generated/l10n.dart";
|
||||
import "package:photos/theme/ente_theme.dart";
|
||||
import "package:photos/ui/components/buttons/button_widget.dart";
|
||||
@@ -6,7 +7,6 @@ import "package:photos/ui/components/buttons/icon_button_widget.dart";
|
||||
import "package:photos/ui/components/dialog_widget.dart";
|
||||
import "package:photos/ui/components/models/button_type.dart";
|
||||
import "package:photos/ui/components/text_input_widget.dart";
|
||||
import "package:photos/ui/settings/TEMP/lock_screen_option.dart";
|
||||
|
||||
class LockScreenOptionConfirmPassword extends StatefulWidget {
|
||||
const LockScreenOptionConfirmPassword({super.key, required this.password});
|
||||
@@ -18,22 +18,30 @@ class LockScreenOptionConfirmPassword extends StatefulWidget {
|
||||
|
||||
class _LockScreenOptionConfirmPasswordState
|
||||
extends State<LockScreenOptionConfirmPassword> {
|
||||
String confirmPassword = "";
|
||||
String _confirmPassword = "";
|
||||
final _confirmPasswordController = TextEditingController(text: null);
|
||||
|
||||
@override
|
||||
void dispose() {
|
||||
super.dispose();
|
||||
_confirmPasswordController.dispose();
|
||||
}
|
||||
final Configuration _configuration = Configuration.instance;
|
||||
final _focusNode = FocusNode();
|
||||
|
||||
@override
|
||||
void initState() {
|
||||
super.initState();
|
||||
WidgetsBinding.instance.addPostFrameCallback((_) async {
|
||||
await Future.delayed(const Duration(seconds: 1));
|
||||
_focusNode.requestFocus();
|
||||
});
|
||||
}
|
||||
|
||||
Future<void> _confirmPassword() async {
|
||||
if (widget.password == confirmPassword) {
|
||||
@override
|
||||
void dispose() {
|
||||
super.dispose();
|
||||
_focusNode.dispose();
|
||||
_confirmPasswordController.dispose();
|
||||
}
|
||||
|
||||
Future<void> _confirmPasswordMatch() async {
|
||||
if (widget.password == _confirmPassword) {
|
||||
await _configuration.savePassword(_confirmPassword);
|
||||
await showDialogWidget(
|
||||
context: context,
|
||||
title: 'Password has been set',
|
||||
@@ -49,11 +57,8 @@ class _LockScreenOptionConfirmPasswordState
|
||||
),
|
||||
],
|
||||
);
|
||||
await Navigator.of(context).push(
|
||||
MaterialPageRoute(
|
||||
builder: (BuildContext context) => const LockScreenOption(),
|
||||
),
|
||||
);
|
||||
Navigator.of(context).pop();
|
||||
Navigator.of(context).pop();
|
||||
} else {
|
||||
await showDialogWidget(
|
||||
context: context,
|
||||
@@ -79,7 +84,6 @@ class _LockScreenOptionConfirmPasswordState
|
||||
final colorTheme = getEnteColorScheme(context);
|
||||
final textTheme = getEnteTextTheme(context);
|
||||
return Scaffold(
|
||||
// resizeToAvoidBottomInset: false,
|
||||
body: Center(
|
||||
child: Column(
|
||||
crossAxisAlignment: CrossAxisAlignment.center,
|
||||
@@ -117,7 +121,7 @@ class _LockScreenOptionConfirmPasswordState
|
||||
),
|
||||
),
|
||||
Text(
|
||||
S.of(context).enterPasswordToLockApp,
|
||||
'Enter the password to lock the app',
|
||||
style: textTheme.bodyBold,
|
||||
),
|
||||
const Padding(padding: EdgeInsets.all(24)),
|
||||
@@ -126,6 +130,7 @@ class _LockScreenOptionConfirmPasswordState
|
||||
child: TextInputWidget(
|
||||
hintText: S.of(context).confirmPassword,
|
||||
borderRadius: 2,
|
||||
focusNode: _focusNode,
|
||||
isClearable: true,
|
||||
textCapitalization: TextCapitalization.words,
|
||||
textEditingController: _confirmPasswordController,
|
||||
@@ -133,7 +138,7 @@ class _LockScreenOptionConfirmPasswordState
|
||||
isPasswordInput: true,
|
||||
onChange: (String p0) {
|
||||
setState(() {
|
||||
confirmPassword = p0;
|
||||
_confirmPassword = p0;
|
||||
});
|
||||
},
|
||||
),
|
||||
@@ -142,12 +147,12 @@ class _LockScreenOptionConfirmPasswordState
|
||||
Padding(
|
||||
padding: const EdgeInsets.all(18.0),
|
||||
child: ButtonWidget(
|
||||
labelText: S.of(context).next,
|
||||
buttonType: confirmPassword.length > 8
|
||||
labelText: 'Next',
|
||||
buttonType: _confirmPassword.length > 3
|
||||
? ButtonType.primary
|
||||
: ButtonType.secondary,
|
||||
buttonSize: ButtonSize.large,
|
||||
onTap: () => _confirmPassword(),
|
||||
onTap: () => _confirmPasswordMatch(),
|
||||
),
|
||||
),
|
||||
const Padding(padding: EdgeInsets.only(bottom: 24)),
|
||||
|
||||
@@ -1,11 +1,11 @@
|
||||
import "package:flutter/material.dart";
|
||||
import "package:photos/core/configuration.dart";
|
||||
import "package:photos/generated/l10n.dart";
|
||||
import "package:photos/theme/ente_theme.dart";
|
||||
import "package:photos/ui/components/buttons/button_widget.dart";
|
||||
import "package:photos/ui/components/buttons/icon_button_widget.dart";
|
||||
import "package:photos/ui/components/dialog_widget.dart";
|
||||
import "package:photos/ui/components/models/button_type.dart";
|
||||
import "package:photos/ui/settings/TEMP/lock_screen_option.dart";
|
||||
import "package:pinput/pin_put/pin_put.dart";
|
||||
|
||||
class LockScreenOptionConfirmPin extends StatefulWidget {
|
||||
@@ -19,19 +19,34 @@ class LockScreenOptionConfirmPin extends StatefulWidget {
|
||||
class _LockScreenOptionConfirmPinState
|
||||
extends State<LockScreenOptionConfirmPin> {
|
||||
final _confirmPinController = TextEditingController(text: null);
|
||||
String _confirmPin = "";
|
||||
final Configuration _configuration = Configuration.instance;
|
||||
final _focusNode = FocusNode();
|
||||
|
||||
final _pinPutDecoration = BoxDecoration(
|
||||
border: Border.all(color: const Color.fromRGBO(45, 194, 98, 1.0)),
|
||||
borderRadius: BorderRadius.circular(15.0),
|
||||
);
|
||||
|
||||
@override
|
||||
void initState() {
|
||||
super.initState();
|
||||
WidgetsBinding.instance.addPostFrameCallback((_) async {
|
||||
await Future.delayed(const Duration(seconds: 1));
|
||||
_focusNode.requestFocus();
|
||||
});
|
||||
}
|
||||
|
||||
@override
|
||||
void dispose() {
|
||||
super.dispose();
|
||||
_focusNode.dispose();
|
||||
_confirmPinController.dispose();
|
||||
}
|
||||
|
||||
Future<void> confirmPin() async {
|
||||
if (widget.pin == _confirmCode) {
|
||||
Future<void> _confirmPinMatch() async {
|
||||
if (widget.pin == _confirmPin) {
|
||||
await _configuration.savePin(_confirmPin);
|
||||
await showDialogWidget(
|
||||
context: context,
|
||||
title: 'Pin has been set',
|
||||
@@ -47,11 +62,8 @@ class _LockScreenOptionConfirmPinState
|
||||
),
|
||||
],
|
||||
);
|
||||
await Navigator.of(context).push(
|
||||
MaterialPageRoute(
|
||||
builder: (BuildContext context) => const LockScreenOption(),
|
||||
),
|
||||
);
|
||||
Navigator.of(context).pop();
|
||||
Navigator.of(context).pop();
|
||||
} else {
|
||||
await showDialogWidget(
|
||||
context: context,
|
||||
@@ -72,8 +84,6 @@ class _LockScreenOptionConfirmPinState
|
||||
_confirmPinController.clear();
|
||||
}
|
||||
|
||||
String _confirmCode = "";
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
final colorTheme = getEnteColorScheme(context);
|
||||
@@ -123,7 +133,7 @@ class _LockScreenOptionConfirmPinState
|
||||
),
|
||||
),
|
||||
Text(
|
||||
S.of(context).reEnterToConfirmPin,
|
||||
'Re-enter to confirm the pin',
|
||||
style: textTheme.bodyBold,
|
||||
),
|
||||
const Padding(padding: EdgeInsets.all(12)),
|
||||
@@ -132,6 +142,7 @@ class _LockScreenOptionConfirmPinState
|
||||
child: PinPut(
|
||||
fieldsCount: 4,
|
||||
controller: _confirmPinController,
|
||||
focusNode: _focusNode,
|
||||
submittedFieldDecoration: _pinPutDecoration.copyWith(
|
||||
borderRadius: BorderRadius.circular(20.0),
|
||||
),
|
||||
@@ -151,7 +162,7 @@ class _LockScreenOptionConfirmPinState
|
||||
obscureText: '*',
|
||||
onChanged: (String pin) {
|
||||
setState(() {
|
||||
_confirmCode = pin;
|
||||
_confirmPin = pin;
|
||||
});
|
||||
},
|
||||
onSubmit: (value) {
|
||||
@@ -164,11 +175,11 @@ class _LockScreenOptionConfirmPinState
|
||||
padding: const EdgeInsets.all(18.0),
|
||||
child: ButtonWidget(
|
||||
labelText: S.of(context).confirm,
|
||||
buttonType: _confirmCode.length == 4
|
||||
buttonType: _confirmPin.length == 4
|
||||
? ButtonType.primary
|
||||
: ButtonType.secondary,
|
||||
buttonSize: ButtonSize.large,
|
||||
onTap: () => confirmPin(),
|
||||
onTap: () => _confirmPinMatch(),
|
||||
),
|
||||
),
|
||||
const Padding(padding: EdgeInsets.only(bottom: 24)),
|
||||
|
||||
@@ -3,14 +3,18 @@ import "package:photos/generated/l10n.dart";
|
||||
import "package:photos/theme/ente_theme.dart";
|
||||
import "package:photos/ui/components/buttons/button_widget.dart";
|
||||
import "package:photos/ui/components/buttons/icon_button_widget.dart";
|
||||
import "package:photos/ui/components/dialog_widget.dart";
|
||||
import "package:photos/ui/components/models/button_type.dart";
|
||||
import "package:photos/ui/components/text_input_widget.dart";
|
||||
import "package:photos/ui/settings/TEMP/lock_screen_option_confirm_password.dart";
|
||||
|
||||
class LockScreenOptionPassword extends StatefulWidget {
|
||||
const LockScreenOptionPassword({super.key});
|
||||
|
||||
const LockScreenOptionPassword({
|
||||
super.key,
|
||||
this.isAuthenticating = false,
|
||||
this.authPass,
|
||||
});
|
||||
final bool isAuthenticating;
|
||||
final String? authPass;
|
||||
@override
|
||||
State<LockScreenOptionPassword> createState() =>
|
||||
_LockScreenOptionPasswordState();
|
||||
@@ -19,19 +23,38 @@ class LockScreenOptionPassword extends StatefulWidget {
|
||||
class _LockScreenOptionPasswordState extends State<LockScreenOptionPassword> {
|
||||
final _passwordController = TextEditingController(text: null);
|
||||
String password = "";
|
||||
@override
|
||||
void dispose() {
|
||||
super.dispose();
|
||||
_passwordController.dispose();
|
||||
}
|
||||
final _focusNode = FocusNode();
|
||||
|
||||
@override
|
||||
void initState() {
|
||||
super.initState();
|
||||
WidgetsBinding.instance.addPostFrameCallback((_) async {
|
||||
await Future.delayed(const Duration(seconds: 1));
|
||||
_focusNode.requestFocus();
|
||||
});
|
||||
}
|
||||
|
||||
@override
|
||||
void dispose() {
|
||||
super.dispose();
|
||||
_passwordController.dispose();
|
||||
_focusNode.dispose();
|
||||
}
|
||||
|
||||
Future<bool> confirmPasswordAuth(String code) async {
|
||||
if (widget.authPass == code) {
|
||||
Navigator.of(context).pop(true);
|
||||
return true;
|
||||
}
|
||||
Navigator.of(context).pop(false);
|
||||
return false;
|
||||
}
|
||||
|
||||
Future<void> _confirmPassword() async {
|
||||
if (password.length > 8) {
|
||||
if (widget.isAuthenticating) {
|
||||
await confirmPasswordAuth(password);
|
||||
return;
|
||||
} else {
|
||||
await Navigator.of(context).push(
|
||||
MaterialPageRoute(
|
||||
builder: (BuildContext context) => LockScreenOptionConfirmPassword(
|
||||
@@ -39,22 +62,6 @@ class _LockScreenOptionPasswordState extends State<LockScreenOptionPassword> {
|
||||
),
|
||||
),
|
||||
);
|
||||
} else {
|
||||
await showDialogWidget(
|
||||
context: context,
|
||||
title: 'Password must have at least 8 characters',
|
||||
icon: Icons.lock,
|
||||
body: 'Please re-enter the password.',
|
||||
isDismissible: true,
|
||||
buttons: [
|
||||
ButtonWidget(
|
||||
buttonType: ButtonType.secondary,
|
||||
labelText: S.of(context).ok,
|
||||
isInAlert: true,
|
||||
buttonAction: ButtonAction.first,
|
||||
),
|
||||
],
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -63,7 +70,6 @@ class _LockScreenOptionPasswordState extends State<LockScreenOptionPassword> {
|
||||
final colorTheme = getEnteColorScheme(context);
|
||||
final textTheme = getEnteTextTheme(context);
|
||||
return Scaffold(
|
||||
// resizeToAvoidBottomInset: false,
|
||||
body: Center(
|
||||
child: Column(
|
||||
crossAxisAlignment: CrossAxisAlignment.center,
|
||||
@@ -101,7 +107,10 @@ class _LockScreenOptionPasswordState extends State<LockScreenOptionPassword> {
|
||||
),
|
||||
),
|
||||
Text(
|
||||
S.of(context).enterPasswordToLockApp,
|
||||
widget.isAuthenticating
|
||||
? 'Enter the password to change \nLockscreen settings.'
|
||||
: 'Enter the password to lock the app',
|
||||
textAlign: TextAlign.center,
|
||||
style: textTheme.bodyBold,
|
||||
),
|
||||
const Padding(padding: EdgeInsets.all(24)),
|
||||
@@ -111,6 +120,7 @@ class _LockScreenOptionPasswordState extends State<LockScreenOptionPassword> {
|
||||
hintText: S.of(context).password,
|
||||
borderRadius: 2,
|
||||
isClearable: true,
|
||||
focusNode: _focusNode,
|
||||
textCapitalization: TextCapitalization.words,
|
||||
textEditingController: _passwordController,
|
||||
prefixIcon: Icons.lock_outline,
|
||||
@@ -126,7 +136,7 @@ class _LockScreenOptionPasswordState extends State<LockScreenOptionPassword> {
|
||||
Padding(
|
||||
padding: const EdgeInsets.all(18.0),
|
||||
child: ButtonWidget(
|
||||
labelText: S.of(context).next,
|
||||
labelText: 'Next',
|
||||
buttonType: password.length > 8
|
||||
? ButtonType.primary
|
||||
: ButtonType.secondary,
|
||||
|
||||
@@ -1,5 +1,4 @@
|
||||
import "package:flutter/material.dart";
|
||||
import "package:photos/generated/l10n.dart";
|
||||
import "package:photos/theme/ente_theme.dart";
|
||||
import "package:photos/ui/components/buttons/button_widget.dart";
|
||||
import "package:photos/ui/components/buttons/icon_button_widget.dart";
|
||||
@@ -8,32 +7,65 @@ import "package:photos/ui/settings/TEMP/lock_screen_option_confirm_pin.dart";
|
||||
import "package:pinput/pin_put/pin_put.dart";
|
||||
|
||||
class LockScreenOptionPin extends StatefulWidget {
|
||||
const LockScreenOptionPin({super.key});
|
||||
const LockScreenOptionPin({
|
||||
super.key,
|
||||
this.isAuthenticating = false,
|
||||
this.authPin,
|
||||
});
|
||||
|
||||
final bool isAuthenticating;
|
||||
final String? authPin;
|
||||
@override
|
||||
State<LockScreenOptionPin> createState() => _LockScreenOptionPinState();
|
||||
}
|
||||
|
||||
class _LockScreenOptionPinState extends State<LockScreenOptionPin> {
|
||||
final _pinController = TextEditingController(text: null);
|
||||
String _code = "";
|
||||
final _focusNode = FocusNode();
|
||||
|
||||
final _pinPutDecoration = BoxDecoration(
|
||||
border: Border.all(color: const Color.fromRGBO(45, 194, 98, 1.0)),
|
||||
borderRadius: BorderRadius.circular(15.0),
|
||||
);
|
||||
|
||||
@override
|
||||
void initState() {
|
||||
super.initState();
|
||||
WidgetsBinding.instance.addPostFrameCallback((_) async {
|
||||
await Future.delayed(const Duration(seconds: 1));
|
||||
_focusNode.requestFocus();
|
||||
});
|
||||
}
|
||||
|
||||
@override
|
||||
void dispose() {
|
||||
super.dispose();
|
||||
_pinController.dispose();
|
||||
_focusNode.dispose();
|
||||
}
|
||||
|
||||
String _code = "";
|
||||
Future<void> confirmPin(String code) async {
|
||||
await Navigator.of(context).push(
|
||||
MaterialPageRoute(
|
||||
builder: (BuildContext context) =>
|
||||
LockScreenOptionConfirmPin(pin: code),
|
||||
),
|
||||
);
|
||||
Future<bool> confirmPinAuth(String code) async {
|
||||
if (widget.authPin == code) {
|
||||
Navigator.of(context).pop(true);
|
||||
return true;
|
||||
}
|
||||
Navigator.of(context).pop(false);
|
||||
return false;
|
||||
}
|
||||
|
||||
Future<void> _confirmPin(String code) async {
|
||||
if (widget.isAuthenticating) {
|
||||
await confirmPinAuth(code);
|
||||
return;
|
||||
} else {
|
||||
await Navigator.of(context).push(
|
||||
MaterialPageRoute(
|
||||
builder: (BuildContext context) =>
|
||||
LockScreenOptionConfirmPin(pin: code),
|
||||
),
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
@override
|
||||
@@ -85,13 +117,16 @@ class _LockScreenOptionPinState extends State<LockScreenOptionPin> {
|
||||
),
|
||||
),
|
||||
Text(
|
||||
S.of(context).enterThePinToLockTheApp,
|
||||
widget.isAuthenticating
|
||||
? 'Enter the pin to change Lockscreen settings.'
|
||||
: 'Enter the pin to lock the app',
|
||||
style: textTheme.bodyBold,
|
||||
),
|
||||
const Padding(padding: EdgeInsets.all(12)),
|
||||
Padding(
|
||||
padding: const EdgeInsets.fromLTRB(80, 0, 80, 0),
|
||||
child: PinPut(
|
||||
focusNode: _focusNode,
|
||||
fieldsCount: 4,
|
||||
controller: _pinController,
|
||||
submittedFieldDecoration: _pinPutDecoration.copyWith(
|
||||
@@ -130,7 +165,7 @@ class _LockScreenOptionPinState extends State<LockScreenOptionPin> {
|
||||
? ButtonType.primary
|
||||
: ButtonType.secondary,
|
||||
buttonSize: ButtonSize.large,
|
||||
onTap: () => confirmPin(_code),
|
||||
onTap: () => _confirmPin(_code),
|
||||
),
|
||||
),
|
||||
const Padding(padding: EdgeInsets.only(bottom: 24)),
|
||||
|
||||
@@ -0,0 +1,17 @@
|
||||
import "package:flutter/widgets.dart";
|
||||
|
||||
class LockScreenOptionPinSetting extends StatefulWidget {
|
||||
const LockScreenOptionPinSetting({super.key});
|
||||
|
||||
@override
|
||||
State<LockScreenOptionPinSetting> createState() =>
|
||||
_LockScreenOptionPinSettingState();
|
||||
}
|
||||
|
||||
class _LockScreenOptionPinSettingState
|
||||
extends State<LockScreenOptionPinSetting> {
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
return const Placeholder();
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user