Codementor Events

Create reusable password field in flutter with preview check

Published Mar 23, 2019

It took 4 days search to find this, so I'm sharing it with the community, credit goes to X-Wei.

Problem:

Creating a password field in flutter with preview check as below:

psswrd.png

Solution:

  • Define StatefulWidget to for a new widget named PasswordField as below:
class PasswordField extends StatefulWidget { const PasswordField({ }); _PasswordFieldState createState() => new _PasswordFieldState();
} class _PasswordFieldState extends State<PasswordField> { Widget build(BuildContext context) { return TextFormField( );
}
  • Define the required widget parameter in the StatefulWidget class above, as below:
const PasswordField({ this.fieldKey, this.maxLength, this.hintText, this.labelText, this.helperText, this.onSaved, this.validator, this.onFieldSubmitted, }); final Key fieldKey; final int maxLength; final String hintText; final String labelText; final String helperText; final FormFieldSetter<String> onSaved; final FormFieldValidator<String> validator; final ValueChanged<String> onFieldSubmitted;

In the widget State return a TextFormField that has a decoration: InputDecoration

In the decoration: InputDecoration define a suffixIcon: GestureDetector that has a child: Icon and onTap function that change the state, like below:

suffixIcon: GestureDetector( onTap: () { setState(() { _obscureText = !_obscureText; }); }, child: Icon(_obscureText ? Icons.visibility : Icons.visibility_off), ),
  • So, the full StatefulWidget of our PasswordField, became as below password.dart:
import 'package:flutter/material.dart'; class PasswordField extends StatefulWidget { const PasswordField({ this.fieldKey, this.maxLength, this.hintText, this.labelText, this.helperText, this.onSaved, this.validator, this.onFieldSubmitted, }); final Key fieldKey; final int maxLength; final String hintText; final String labelText; final String helperText; final FormFieldSetter<String> onSaved; final FormFieldValidator<String> validator; final ValueChanged<String> onFieldSubmitted; _PasswordFieldState createState() => _PasswordFieldState();
} class _PasswordFieldState extends State<PasswordField> { bool _obscureText = true; Widget build(BuildContext context) { return TextFormField( key: widget.fieldKey, obscureText: _obscureText, maxLength: widget.maxLength ?? 8, onSaved: widget.onSaved, validator: widget.validator, onFieldSubmitted: widget.onFieldSubmitted, decoration: InputDecoration( border: const UnderlineInputBorder(), filled: true, hintText: widget.hintText, labelText: widget.labelText, helperText: widget.helperText, suffixIcon: GestureDetector( onTap: () { setState(() { _obscureText = !_obscureText; }); }, child: Icon(_obscureText ? Icons.visibility : Icons.visibility_off), ), ), ); }
}
  • Call this widget in your screen as any other widget, just like:
child: PasswordField( ),
  • Before calling this child, you need to define the below:
String _password; final _passwordFieldKey = GlobalKey<FormFieldState<String>>();
  • The full code to call it, can be as:
import 'package:flutter/material.dart';
import 'package:myApp/password.dart'; class LoginPage extends StatefulWidget { _LoginPageState createState() => new _LoginPageState();
} class _LoginPageState extends State<LoginPage> { final GlobalKey<FormState> _formKey = GlobalKey<FormState>(); String _email, _password; final _passwordFieldKey = GlobalKey<FormFieldState<String>>(); Widget build(BuildContext context) { return Scaffold( appBar: AppBar(), body: Form( key: _formKey, child: Column( children: <Widget>[TextFormField( validator: (input) { if(input.isEmpty){ return 'Provide an email'; } }, decoration: InputDecoration( labelText: 'Email' ), onSaved: (input) => _email = input, ), PasswordField( fieldKey: _passwordFieldKey, helperText: 'No more than 8 characters.', labelText: 'Password *', onSaved: (input) => _password = input, ), SizedBox(height: 24.0), RaisedButton( onPressed: signIn, child: Text('Sign in'), ),], ) ), ); } void signIn() async { if(_formKey.currentState.validate()){ _formKey.currentState.save(); print("email: $_email, password: $_password"); } }
}
Discover and read more posts from Hasan Yousef
get started