0
0
Fluttermobile~20 mins

Custom validators in Flutter - Mini App: Build & Ship

Choose your learning style9 modes available
Build: Registration Form
A simple registration form screen that validates user input using custom validators for email and password fields.
Target UI
Registration Form

Email: ______________________
Password: ___________________

[ Register ]
Add a TextFormField for email with a custom validator that checks if the input contains '@' and '.'
Add a TextFormField for password with a custom validator that checks if the password is at least 8 characters long
Add a Register button that shows a message if the form is valid or highlights errors if invalid
Starter Code
Flutter
import 'package:flutter/material.dart';

class RegistrationForm extends StatefulWidget {
  @override
  State<RegistrationForm> createState() => _RegistrationFormState();
}

class _RegistrationFormState extends State<RegistrationForm> {
  final _formKey = GlobalKey<FormState>();

  @override
  Widget build(BuildContext context) {
    return Scaffold(
      appBar: AppBar(title: const Text('Registration Form')),
      body: Padding(
        padding: const EdgeInsets.all(16.0),
        child: Form(
          key: _formKey,
          child: Column(
            children: [
              // TODO: Add email TextFormField with custom validator
              // TODO: Add password TextFormField with custom validator
              const SizedBox(height: 20),
              ElevatedButton(
                onPressed: () {
                  // TODO: Validate form and show message
                },
                child: const Text('Register'),
              ),
            ],
          ),
        ),
      ),
    );
  }
}
Task 1
Task 2
Task 3
Solution
Flutter
import 'package:flutter/material.dart';

class RegistrationForm extends StatefulWidget {
  @override
  State<RegistrationForm> createState() => _RegistrationFormState();
}

class _RegistrationFormState extends State<RegistrationForm> {
  final _formKey = GlobalKey<FormState>();
  final _emailController = TextEditingController();
  final _passwordController = TextEditingController();

  String? _emailValidator(String? value) {
    if (value == null || value.isEmpty) {
      return 'Please enter your email';
    }
    if (!value.contains('@') || !value.contains('.')) {
      return 'Enter a valid email address';
    }
    return null;
  }

  String? _passwordValidator(String? value) {
    if (value == null || value.isEmpty) {
      return 'Please enter your password';
    }
    if (value.length < 8) {
      return 'Password must be at least 8 characters';
    }
    return null;
  }

  void _submit() {
    if (_formKey.currentState?.validate() ?? false) {
      ScaffoldMessenger.of(context).showSnackBar(
        const SnackBar(content: Text('Registration successful!')),
      );
    }
  }

  @override
  Widget build(BuildContext context) {
    return Scaffold(
      appBar: AppBar(title: const Text('Registration Form')),
      body: Padding(
        padding: const EdgeInsets.all(16.0),
        child: Form(
          key: _formKey,
          child: Column(
            children: [
              TextFormField(
                controller: _emailController,
                decoration: const InputDecoration(labelText: 'Email'),
                keyboardType: TextInputType.emailAddress,
                validator: _emailValidator,
              ),
              TextFormField(
                controller: _passwordController,
                decoration: const InputDecoration(labelText: 'Password'),
                obscureText: true,
                validator: _passwordValidator,
              ),
              const SizedBox(height: 20),
              ElevatedButton(
                onPressed: _submit,
                child: const Text('Register'),
              ),
            ],
          ),
        ),
      ),
    );
  }
}

This solution uses two custom validator functions: _emailValidator and _passwordValidator. Each checks the input and returns an error message string if invalid or null if valid.

The email validator checks if the input contains both '@' and '.' characters to roughly validate an email format.

The password validator ensures the password is at least 8 characters long.

When the Register button is pressed, the form validates all fields. If all are valid, a success message appears using a SnackBar. Otherwise, the invalid fields show error messages below them.

This approach helps beginners understand how to create and use custom validation logic in Flutter forms.

Final Result
Completed Screen
Registration Form

Email: user@example.com
Password: ********

[ Register ]
User types email and password in the fields.
If input is invalid, error messages appear below the fields after pressing Register.
If input is valid, a SnackBar appears at the bottom saying 'Registration successful!'.
Stretch Goal
Add a confirm password field with a custom validator that checks if it matches the password field.
💡 Hint
Use a TextEditingController for the password and compare its value with the confirm password input inside the validator.