当前位置:网站首页>The textfield is encapsulated by the flutter itself, which causes the data display to be disordered when the data in the list is updated.

The textfield is encapsulated by the flutter itself, which causes the data display to be disordered when the data in the list is updated.

2022-06-25 16:00:00 Favorite grapes

demand

There is a list to enter , The input list will vary according to the selected options , And enter different content .

such as :

choice Vip When the customer , Need to enter : full name , cell-phone number , address ,Vip Duration , payment method

When selecting normal users , Need to enter : full name , cell-phone number , address .

Realization

Use ListView Show all input items , Because the input box is universal . So I made a simple package .

On the left is the title , On the right is the input , When empty content , Exhibition hint Tips Please enter .

It's probably like this

-----------------------------
 Customer type              ⊙Vip ⊙ Ordinary 
-----------------------------
 full name                       Please enter 
-----------------------------
 cell-phone number                     Please enter 
-----------------------------
 address                       Please enter 
-----------------------------

When the customer type changes , The following data needs to be changed by linkage .

problem

When switching customer types , There will be data confusion ( For example, the mobile phone number is displayed to the name ).

Trace the problem :

Because data sharing uses Provider+ChangeNotifier In the form of . therefore , When the data changes , actually , The quotation will be updated if it is worth mentioning .

So the first step is to judge , Whether the value is passed to the component encapsulated by itself .

Own encapsulated input box code ( Simple version , Mainly to illustrate the problem ):

// CustomInputTextField

class CustomInputTextField extends StatefulWidget {
	//  Tips 
	final String hint;
  //  Input change monitoring 
  final ValueChanged<String>? onValueChanged;	
  //  Initial value 
  final String? value;
  
  const CustomInputTextField(
      {Key? key,
      required this.hint,
      this.onValueChanged,
      this.value,})
      : super(key: key);

  @override
  State<StatefulWidget> createState() {
    return CustomInputTextFieldState();
  }
}

class CustomInputTextFieldState extends State<CustomInputTextField> {

	late TextEditingController _controller;
	@override
	void initState() {
		_controller = TextEditingController(text : widget.value??"");
	}

	@override
  Widget build(BuildContext context) {
    return TextField(
      controller: _controller,
      onChanged: onInputChanged,
    );
  }
}

Find the cause of the problem

Actually , When the data is updated , Every time Build Is the correct value , What then? , The displayed values are indeed out of order ?

because ,TextField The value in , What is shown is _controller Medium Text, And because of the use of State, and initState Method only executes once , So when the component value Time of change , actually ,_controller The data in does not change . So the display will be disordered .

Solution

Rough version

Directly create a new one each time controller, Because of this controller In the whole assembly , Didn't take the initiative to use .

controller: TextEditingController.fromValue(
        TextEditingValue(
          text: widget.value??'',
          selection: TextSelection.fromPosition(
            TextPosition(offset: widget.value?.length ?? 0),
          ),
        ),
      ),

Kind version

 Every time a component calls didChangeDependence when , Take again widget The value of _controller On assignment .

 Or in didUpdateWidget when , Take the new value to , Compare with the old value , And replace .
原网站

版权声明
本文为[Favorite grapes]所创,转载请带上原文链接,感谢
https://yzsam.com/2022/02/202202190538056916.html