Flutter不会重建具有不同参数的相同小部件

raf*_*tta 7 dart flutter flutter-layout

我正在使用类似的子窗口小部件进行底部导航,其中仅更改了参数。仅当小部件为StatefulWidget时才发生此问题,否则没有问题,bottomnavbar中的指示正在更改,但主体没有更改。

儿童1: 在此处输入图片说明

儿童2: 在此处输入图片说明

实际结果: 在此处输入图片说明

class MyHomePage extends StatefulWidget {
MyHomePage({Key key, this.title}) : super(key: key);
final String title;

@override
_MyHomePageState createState() => _MyHomePageState();
}

class _MyHomePageState extends State<MyHomePage> {
int _counter = 0;
Widget body;
@override
void initState() {
//    body = getBody(0);
super.initState();
}

@override
Widget build(BuildContext context) {
return Scaffold(
  appBar: AppBar(
    title: Text(widget.title),
    elevation: 0,
  ),
  body: body,
  bottomNavigationBar: BottomNavigationBar(
    currentIndex: _counter,
    onTap: (index){
      _counter = index;
      setState(() {
        body = getBody(index);
      });
    },items: [
    BottomNavigationBarItem(icon: Icon(Icons.language),title: 
 Text('HELLO')),
    BottomNavigationBarItem(icon: Icon(Icons.security),title: 
Text('BYE'))
  ]),
 );
}
Widget getBody(int pos){
if(pos==0){
//      return new Mx(category: 'ALPHA',type: '@',);
  return new MyTAbs(category: 'ALPHA',type: '@',);
}
else{
//      return new Mx(category:'BETA',type: '#',);
  return new MyTAbs(category:'BETA',type: '#',);
  }
 }
}
class Mx extends StatelessWidget{
final String type,category;
Mx({this.type,this.category});
@override
Widget build(BuildContext context) {
 return new Scaffold(
  backgroundColor: getColor(),
  body: new Center(
    child: Text(category+' '+type),
  ),
 );
}
Color getColor(){
if(category=='ALPHA'){
  return Colors.red;
}
else{
  return Colors.green;
  }
 }
}
class MyTAbs extends StatefulWidget{
final String type,category;
MyTAbs({this.type,this.category});
Tabs createState() => new Tabs(title: category,type: type);
}
class Tabs extends State<MyTAbs>{
final String title,type;
Tabs({this.title,this.type});
@override
Widget build(BuildContext context) {
// TODO: implement build
return new Scaffold(
  backgroundColor: getColor(),
  appBar: AppBar(
    title: Text(title+' '+type),
  ),
);
}
Color getColor(){
if(title=='ALPHA'){
  return Colors.red;
}
else{
  return Colors.green;
  }
 }
}
Run Code Online (Sandbox Code Playgroud)

而且我不能使用statelessWidget,因为里面有一个动态选项卡部分。

raf*_*tta 21

通过添加新的Key作为参数解决了这个问题,并通过一个唯一键

return new MyTAbs(category: 'ALPHA',type: '@',key: UniqueKey(),);
Run Code Online (Sandbox Code Playgroud)

MyTAbs 类

class MyTAbs extends StatefulWidget{
  final String type,category;
  final Key key;
  MyTAbs({@required this.key,this.type,this.category});
  Tabs createState() => new Tabs(title: category,type: type,key: key);
}
Run Code Online (Sandbox Code Playgroud)

标签类

class Tabs extends State<MyTAbs>{
  final String title,type;
  final Key key;
  Tabs({this.title,this.type,@required this.key});
  @override
  @override
  Widget build(BuildContext context) {
    // TODO: implement build
    return new Scaffold(
      backgroundColor: getColor(),
      appBar: AppBar(
        title: Text(title+' '+type),
      ),
    );
  }
  Color getColor(){
    if(title=='ALPHA'){
      return Colors.red;
    }
    else{
      return Colors.green;
    }
  }
}
Run Code Online (Sandbox Code Playgroud)

一点关于钥匙

当小部件重建时,您可以使用键来控制框架与其他小部件匹配的小部件。默认情况下,框架根据它们的 runtimeType 和它们出现的顺序匹配当前和先前构建中的小部件。对于键,框架要求两个小部件具有相同的键以及相同的运行时类型。 颤振文档中的更多内容