Flutter 輸入框 TextField、表單 Form 圖文示例

輸入框 TextField

TextField用於文本輸入,它提供了很多屬性:

  const TextField({
    Key key,
    this.controller,// 控制器
    this.focusNode, // 控制TextField是否佔有當前鍵盤的輸入焦點
    this.decoration = const InputDecoration(), // 控制TextField的外觀顯示
    TextInputType keyboardType,// 輸入框默認的鍵盤輸入類型
    this.textInputAction,
    this.textCapitalization = TextCapitalization.none,
    this.style,//輸入文本的樣式
    this.strutStyle,
    this.textAlign = TextAlign.start,//文本對齊方式
    this.textAlignVertical,
    this.textDirection,
    this.readOnly = false,
    ToolbarOptions toolbarOptions,
    this.showCursor,// 顯示光標
    this.autofocus = false,//是否自動對焦
    this.obscureText = false,//是否隱藏輸入的內容
    this.autocorrect = true,//是否自動更正
    this.enableSuggestions = true,
    this.maxLines = 1,// 最大行數
    this.minLines,//最小行數
    this.expands = false,
    this.maxLength,//最大長度
    this.maxLengthEnforced = true,
    this.onChanged,// 輸入框變化回調
    this.onEditingComplete,// 編輯完成回調
    this.onSubmitted,// 提交回調
    this.inputFormatters,//允許的輸入格式
    this.enabled,//是否禁用textfield
    this.cursorWidth = 2.0,// 光標寬度
    this.cursorRadius,//光標半徑
    this.cursorColor,//光標顏色
    this.keyboardAppearance,
    this.scrollPadding = const EdgeInsets.all(20.0),
    this.dragStartBehavior = DragStartBehavior.start,
    this.enableInteractiveSelection = true,
    this.onTap,
    this.buildCounter,
    this.scrollController,
    this.scrollPhysics,
  }) 

字段太多了,我們從幾個示例來了解主要字段的使用。

默認效果

只有一條下劃線,也沒有自動獲取焦點。

TextField();

在這裏插入圖片描述

監聽內容變化,獲取輸入框的內容

如果我們要獲取輸入的內容,這時候可以通過onChange, onSubmitted,僞代碼如下:

Widget _buildTextField(){
    return TextField(
      onChanged: (text) {
        //內容改變的回調
        print('change $text');
      },
      onEditingComplete:(){
        print('editing ');
      },
      onSubmitted: (text) {
        //內容提交(按回車)的回調
        print('submit $text');
      },
    );
}

在這裏插入圖片描述

在這裏插入圖片描述

和鍵盤的交互

默認獲取焦點
只需要將autofocus設置爲true即可。

Widget _buildTextField(){
        return TextField(
          autofocus: true,
        );
    }

改變鍵盤右下角的功能鍵

Widget _buildTextField(){
        return TextField(
          autofocus: true,
          keyboardType: TextInputType.text,
          // 右下角按鈕變爲:前往或者Go
          textInputAction:TextInputAction.go,
        );
    }

在這裏插入圖片描述
在這裏插入圖片描述

改變鍵盤的輸入類型

Widget _buildTextField(){
        return TextField(
          autofocus: true,
          keyboardType: TextInputType.number,
          // 將鍵盤顯示類型設置爲數字鍵盤
          keyboardType: TextInputType.number,
        );
    }

在這裏插入圖片描述
在這裏插入圖片描述
如何自適應屏幕彈起

目前來看TextField已滿足一個輸入框的功能了。
但是它太醜了,這不符合Flutter構建一個漂亮App的目標

美化 TextField 樣式

主要是使用TextField自帶的字段修改,或者使用InputDecoration修改樣式。
TextField的常用字段我們在上面已經給出註釋了,接下來查看InputDecoration的常見字段:

字段基本釋義來源:Flutter文本輸入框TextField屬性(InputDecoration、textInputAction、inputFormatters等等)詳解

const InputDecoration({
    this.icon, //位於裝飾器外部和輸入框前面的圖片
    this.labelText,//用於描述輸入框,當輸入框獲取焦點時默認會浮動到上方,
    this.labelStyle,// 控制labelText的樣式
    this.helperText,//輔助文本,位於輸入框下方,如果errorText不爲空的話,則helperText不會顯示
    this.helperStyle,//helperText的樣式
    this.helperMaxLines,//提示信息最大行數
    this.hintText,//提示文本,位於輸入框內部
    this.hintStyle,//hintText的樣式
    this.hintMaxLines,//提示信息最大行數
    this.errorText,//errorText的信息
    this.errorStyle,//errorText的樣式
    this.errorMaxLines, //errorText的最大行數
    this.hasFloatingPlaceholder = true, //labelText是否浮動,默認爲true
    this.isDense,//改變輸入框是否爲密集型
    this.contentPadding,//內間距
    this.prefixIcon,//位於輸入框內部起始位置的圖標。
    this.prefix,//預先填充的Widget,跟prefixText同時只能出現一個
    this.prefixText,//預填充的文本,例如手機號前面預先加上區號等
    this.prefixStyle,//prefixText的樣式
    this.suffixIcon,//位於輸入框後面的圖片
    this.suffix, //位於輸入框尾部的控件,同樣的不能和suffixText同時使用
    this.suffixText,//位於尾部的填充文字
    this.suffixStyle, //suffixText的樣式
    this.counter,//位於輸入框右下方的小控件,不能和counterText同時使用
    this.counterText,//位於右下方顯示的文本,常用於顯示輸入的字符數量
    this.counterStyle,//counterText的樣式
    this.filled,//如果爲true,則輸入使用fillColor指定的顏色填充
    this.fillColor,//輸入框的背景顏色
    this.focusColor,//輸入框有焦點時的邊框顏色
    this.hoverColor,//輸入框被懸浮時的邊框顏色
    this.errorBorder,//errorText不爲空,輸入框沒有焦點時要顯示的邊框
    this.focusedBorder,//輸入框有焦點時的邊框
    this.focusedErrorBorder,//errorText不爲空時,輸入框有焦點時的邊框
    this.disabledBorder,//輸入框禁用時顯示的邊框
    this.enabledBorder,//輸入框可用時顯示的邊框
    this.border,//正常情況下的border
    this.enabled = true,//輸入框是否可用
    this.semanticCounterText,
    this.alignLabelWithHint,
  })

接下來我們通過幾個例子來看看實現的效果圖。

遊標顏色、粗細,控制輸入長度

    Widget _buildTextField(){
        return TextField(
          autofocus: true,
          cursorColor: Colors.deepOrange,
          cursorRadius: Radius.circular(20.0),
          cursorWidth: 10.0,
          maxLength: 10,
        );
    }

在這裏插入圖片描述

密碼框
增加obscureText: true,屬性即可實現輸入的內容是隱藏的。
在這裏插入圖片描述
改變下劃線顏色
默認下劃線是跟隨主題的紅色,這裏將其改爲橘色700。
在這裏插入圖片描述

 Widget _buildTextField(){
        return Container(
          child: TextField(
              autofocus: true,
              decoration: InputDecoration(
                  border: InputBorder.none //隱藏下劃線
              )
          ),
          decoration: BoxDecoration(
            // 下滑線橘色700,寬度3像素
              border: Border(bottom: BorderSide(color: Colors.orange[700], width: 3.0))
          ),
        );
    }

圓角輸入框
在這裏插入圖片描述

    Widget _buildTextField(){
        return TextField(
          autofocus: true,
          cursorColor: Colors.deepOrange,
          cursorRadius: Radius.circular(20.0),
          cursorWidth: 10.0,
          maxLength: 10,
          obscureText: true,
          decoration: InputDecoration(
          	 //  文本內容的內邊距
              contentPadding: EdgeInsets.all(10.0),
              // 圓角矩形的輸入框樣式
              border: OutlineInputBorder(
                // 圓角半徑 10
                borderRadius: BorderRadius.circular(10.0),
              )),
        );
    }

帶有圖標輸入框
使用InputDecoration常見的一些屬性完成了以下的效果圖:
在這裏插入圖片描述

Widget _buildTextField(){
        return Column(
          children: <Widget>[
            TextField(
              decoration: InputDecoration(
                icon: Icon(Icons.supervised_user_circle),
                  suffixIcon: Icon(Icons.search),
                  prefixText: 'prefixText ',
                  suffixText: 'suffixText',
                  labelText: "用戶名",
                  helperText: '請輸入用戶名、手機號',
                  hintText: "用戶名或手機號",
                  prefixIcon: Icon(Icons.person)
              ),
            ),
            TextField(
              decoration: InputDecoration(
                  prefixIcon: Icon(Icons.lock),
                  suffixIcon: Icon(Icons.remove_red_eye),
                  labelText: "密碼",
                  hintText: "您的登錄密碼",
                  hintStyle: TextStyle(color: Colors.grey, fontSize: 13.0)
              ),
              obscureText: true,
            )
          ],
        );
    }

表單 Form 驗證

Flutter提供了一個Form 組件,它可以對輸入框進行分組。Form對應的狀態類爲FormState,可以通過Form.of()GlobalKey獲得。獲得狀態類之後就可以做統一操作了如:

  • FormState.validate():調用此方法後,會調用子孫FormFieldvalidate回調,如果有一個校驗失敗,則返回false,所有校驗失敗項都會返回用戶返回的錯誤提示。
  • FormState.save():調用此方法後,會調用子孫FormFieldsave回調,用於保存表單內容
  • FormState.reset():調用此方法後,會將子孫FormField的內容清空。

在這裏插入圖片描述

輸入框內容校驗

  • 自動校驗

autovalidate: true, //開啓自動校驗,在 Form 組件下設置該屬性爲true

  • 手動校驗

通過點擊按鈕來校驗Form中所有TextField的信息。

  1. 定義全局的 key,用於獲取state
  2. TextField中做驗證判斷
  3. 點擊按鈕時獲取FormState,調用validate()方法。

由於代碼過多,粘貼閱讀體驗不好,相關代碼可參考:dongxi346/Flutter-WanAndroid

輸入框內容重置

  • 通過FormState去調用
 var _formState = _formKey.currentState as FormState;
 // Form 裏面的所有TextField輸入框內容都被清空
 _formState.reset();	

由於代碼過多,粘貼閱讀體驗不好,相關代碼可參考:dongxi346/Flutter-WanAndroid

輸入內容保存

  • TextField中使用 onSave字段

例如:

onSaved: (value){
  _passWord = value;
},
  • 通過FormState去調用
 var _formState = _formKey.currentState as FormState;
 // Form 裏面的所有TextField onSave 方法都被調用
 _formState.save();

由於代碼過多,粘貼閱讀體驗不好,相關代碼可參考:dongxi346/Flutter-WanAndroid

登錄頁面例子

原來的效果圖來源忘記了,好像是在一個第三方庫中出現的效果,當時覺得UI超級好看就直接複製了作者的源碼在 現有的項目 Flutter-WanAndroid-login-page 中使用 ,如有侵權聯繫。

通過前面幾篇文章以及本篇文章的分析,實現這個登錄效果圖應該是相當容易了。
這裏暫不實現,待後面學習了佈局的擺放後再來實現這個例子。
在這裏插入圖片描述

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章