Files
sendico/frontend/pweb/lib/widgets/password/password.dart
2025-11-13 15:06:15 +03:00

105 lines
3.0 KiB
Dart

import 'package:flutter/material.dart';
import 'package:fancy_password_field/fancy_password_field.dart';
import 'package:pweb/config/constants.dart';
import 'package:pweb/generated/i18n/app_localizations.dart';
class PasswordField extends StatefulWidget {
final TextEditingController controller;
final ValueChanged<bool>? onValid;
final bool hasStrengthIndicator;
final String? labelText;
final Set<ValidationRule> rules;
final AutovalidateMode? autovalidateMode;
final Widget Function(Set<ValidationRule>, String)? validationRuleBuilder;
const PasswordField({
super.key,
required this.controller,
this.onValid,
this.validationRuleBuilder,
this.labelText,
this.hasStrengthIndicator = false,
this.autovalidateMode,
this.rules = const {},
});
@override
State<PasswordField> createState() => _PasswordFieldState();
}
class _PasswordFieldState extends State<PasswordField> {
bool _lastValidationResult = false;
void _onChanged(String value) {
bool isValid = widget.rules.every((rule) => rule.validate(value));
// Only trigger onValid if validation result has changed
if (isValid != _lastValidationResult) {
_lastValidationResult = isValid;
widget.onValid?.call(isValid);
}
}
@override
Widget build(BuildContext context) {
return FancyPasswordField(
key: widget.key,
controller: widget.controller,
decoration: InputDecoration(
labelText: widget.labelText ?? AppLocalizations.of(context)!.password,
),
validationRules: widget.rules,
hasStrengthIndicator: widget.hasStrengthIndicator,
validationRuleBuilder: widget.validationRuleBuilder,
autovalidateMode: widget.autovalidateMode,
onChanged: _onChanged,
);
}
}
Widget defaulRulesPasswordField(
BuildContext context, {
required TextEditingController controller,
Key? key,
ValueChanged<bool>? onValid,
Widget Function(Set<ValidationRule>, String)? validationRuleBuilder,
String? labelText,
FocusNode? focusNode,
AutovalidateMode? autovalidateMode,
bool hasStrengthIndicator = false,
Set<ValidationRule> additionalRules = const {},
}) {
Set<ValidationRule> rules = {
DigitValidationRule(
customText: AppLocalizations.of(context)!.passwordValidationRuleDigit,
),
UppercaseValidationRule(
customText: AppLocalizations.of(context)!.passwordValidationRuleUpperCase,
),
LowercaseValidationRule(
customText: AppLocalizations.of(context)!.passwordValidationRuleLowerCase,
),
MinCharactersValidationRule(
Constants.minPasswordCharacters,
customText: AppLocalizations.of(context)!
.passwordValidationRuleMinCharacters(Constants.minPasswordCharacters),
),
...additionalRules,
};
return PasswordField(
key: key,
controller: controller,
onValid: onValid,
validationRuleBuilder: validationRuleBuilder,
hasStrengthIndicator: hasStrengthIndicator,
labelText: labelText,
autovalidateMode: autovalidateMode,
rules: rules,
);
}