Repository: flutter
Issue: Inconsistency between web and mobile when showing errors in TextFormField with OutlineInputBorder 
Labels: framework,f: material design,a: quality,has reproducible steps,found in release: 2.0,found in release: 2.1,team-design,triaged-design

I wrote a widget in order to share the code for the "username" and "password" form fields. Validation is performed with Flutter BLoC and Formz packages so the "form field" widgets are built from a BlocBuilder simply reflecting its state.

![flutter textfield error](https://user-images.githubusercontent.com/81817935/113429926-914f1f00-93d9-11eb-8ef8-b31b6d87015d.png)

At first, I was displaying the error message and on the web version looked fine but, on the mobile version, the TextFormField label and the error message one were too close and looked ugly. So I simply decided to leave the red border and hide the error message returning an empty string and setting errorStyle: const TextStyle(height: 0), which I read to be the suggested way to hide the error message in the TextFormField widget.
At this point on mobile was fine while on the web version the error message wasn't displaying as well but the TextFormField expanded anyway on the bottom "outside" the red border unnecessarily.

First problem: the error message in the TextFormField with OutlineInputBorder is too close/overlap with the floating label on Android (cannot try with iOS).
Second problem: TextFormField expand on the bottom even when the error message string is empty
Third problem: the border of the TextFormField doesn't surround the expanded area when displaying an error message


```
 class LoginFormField extends FormzInput<String,String>{
  LoginFormField.pure([String value]) : super.pure(value ?? '');
  LoginFormField.dirty([String value = '']) : super.dirty(value);

  @override
  String validator(String value) {
  return value.isEmpty ? '' : null;
  }
}
```
```
class LoginFormFieldWidget extends StatelessWidget {
  const LoginFormFieldWidget({
    @required this.label,
    @required this.textInputAction,
    @required this.focusNode,
    this.nextFocusNode,
    @required this.formField,
    this.obscureText,
    @required this.prefixIcon,
    this.suffixIcon,
    @required this.onChanged,
  });

  final String label;
  final TextInputAction textInputAction;
  final FocusNode focusNode;
  final FocusNode nextFocusNode;
  final LoginFormField formField;
  final bool obscureText;
  final IconData prefixIcon;
  final IconData suffixIcon;
  final Function(String password) onChanged;

  @override
  Widget build(BuildContext context) {
    return Container(
      decoration: BoxDecoration(
        color: Colors.white,
        boxShadow: [
          BoxShadow(
              spreadRadius: 1,
              blurRadius: 1,
              offset: Offset(0, 2),
              color: Colors.grey[300])
        ],
        borderRadius: const BorderRadius.all(Radius.circular(8.0)),
      ),
      child: TextFormField(
        initialValue: formField.value,
        autovalidateMode: AutovalidateMode.always,
        textInputAction: textInputAction,
        focusNode: focusNode,
        onChanged: (value) => onChanged(value),
        onFieldSubmitted: (term) => nextFocusNode != null
            ? nextFocusNode.requestFocus()
            : focusNode.unfocus(),
        obscureText: obscureText ?? false,
        keyboardType: TextInputType.text,
        style: TextStyle(color: Colors.black87),
        //simply replace the empty string with an error message to reproduce the mobile label problem
        validator: (_) => formField.invalid ? '' : null,
        decoration: InputDecoration(
          labelText: label,
          labelStyle: loginLabelStyle,
          focusedBorder: OutlineInputBorder(
              borderSide: BorderSide(style: BorderStyle.none)),
          enabledBorder: OutlineInputBorder(
              borderSide: BorderSide(style: BorderStyle.none)),
          focusedErrorBorder:
              OutlineInputBorder(borderSide: BorderSide(color: Colors.red)),
          errorBorder:
              OutlineInputBorder(borderSide: BorderSide(color: Colors.red)),
          errorStyle: const TextStyle(height: 0),
          prefixIcon: Icon(prefixIcon, color: Colors.blue),
          suffixIcon: suffixIcon != null
              ? MouseRegion(
                  cursor: SystemMouseCursors.click,
                  child: GestureDetector(
                    onTap: () => context
                        .read<LogInBloc>()
                        .add(LogInEvent.passwordVisibilityChanged()),
                    child: Icon(suffixIcon, color: Colors.blue),
                  ),
                )
              : null,
        ),
      ),
    );
  }
}
```

flutter doctor -v output:
```
[√] Flutter (Channel stable, 2.0.3, on Microsoft Windows [Version 10.0.19041.867], locale en-GB)
    • Flutter version 2.0.3 at C:\flutter
    • Framework revision 4d7946a68d (2 weeks ago), 2021-03-18 17:24:33 -0700
    • Engine revision 3459eb2436
    • Dart version 2.12.2

[√] Android toolchain - develop for Android devices (Android SDK version 30.0.1)
    • Android SDK at C:\Users\***\AppData\Local\Android\sdk
    • Platform android-30, build-tools 30.0.1
    • Java binary at: C:\Program Files\Android\Android Studio\jre\bin\java
    • Java version OpenJDK Runtime Environment (build 1.8.0_242-release-1644-b01)
    • All Android licenses accepted.

[√] Chrome - develop for the web
    • Chrome at C:\Program Files (x86)\Google\Chrome\Application\chrome.exe

[√] Visual Studio - develop for Windows (Visual Studio Community 2019 16.8.4)
    • Visual Studio at C:\Program Files (x86)\Microsoft Visual Studio\2019\Community
    • Visual Studio Community 2019 version 16.8.30907.101
    • Windows 10 SDK version 10.0.18362.0

[√] Android Studio (version 4.1.0)
    • Android Studio at C:\Program Files\Android\Android Studio
    • Flutter plugin can be installed from:
       https://plugins.jetbrains.com/plugin/9212-flutter
    • Dart plugin can be installed from:
       https://plugins.jetbrains.com/plugin/6351-dart
    • Java version OpenJDK Runtime Environment (build 1.8.0_242-release-1644-b01)

[√] VS Code (version 1.52.1)
    • VS Code at C:\Users\***\AppData\Local\Programs\Microsoft VS Code
    • Flutter extension version 3.18.1

[√] Connected device (4 available)
    • AOSP on IA Emulator (mobile) • emulator-5554 • android-x86    • Android 9 (API 28) (emulator)
    • Windows (desktop)            • windows       • windows-x64    • Microsoft Windows [Version 10.0.19041.867]
    • Chrome (web)                 • chrome        • web-javascript • Google Chrome 89.0.4389.90
    • Edge (web)                   • edge          • web-javascript • Microsoft Edge 88.0.705.74

• No issues found!
```