2017-09-19 32 views
0

我想知道如何根据动作(例如:onPressed)销毁/重新创建Widget如何在动作后处置/重新创建Widget

我想到这个的方法是让我的Widget在Opacity对象内被敲击,并根据用户在我的应用中的某处进行交互来控制对象的状态(即:隐藏/显示小部件而不是处理/重新创建)。但是,我在这里问的是,如何在单击按钮后销毁/重新创建Widget?

我已经创建了下面的虚拟示例来展示我的意思。

当我按下云Icon并按下RaisedButton时重新创建了红色Icon

enter image description here

Widget build(BuildContext context) { 
    return new Scaffold(
     appBar: new AppBar(
      title: new Text("Destroy/Recreate Example"), 
     ), 
     body: new Center(
      child: new Column(
       mainAxisAlignment: MainAxisAlignment.center, 
       children: <Widget>[ 
        new Stack(fit: StackFit.passthrough, 
        children: <Widget>[ 
         new IconButton(icon: new Icon(
         Icons.cloud_circle, size: 40.0, color: Colors.blue,), 
          onPressed: null /*_destroyWidget*/), 
         new Positioned(child: new DecoratedBox(
         decoration: new BoxDecoration(shape: BoxShape.circle), 
         child: new Icon(
          Icons.add_circle, size: 20.0, color: Colors.red,),), 
          top: 3.0, 
          left: 3.0) 
        ], 
       ), 
        new RaisedButton(onPressed: null /*_recreateWidget*/, 
        child: new Text("Recreate!"), 
       ), 
       ]) 
     ) 
    ); 
    } 

如何开始这个想法?

更新

下面的代码实现了同样的事情,但通过操纵红色Icon(显示/隐藏)的Opacity

var _myOpacity = 0.0; 

    @override 
    Widget build(BuildContext context) { 
    return new Scaffold(
     appBar: new AppBar(
      title: new Text("Destroy/Recreate Example"), 
     ), 
     body: new Center(
      child: new Column(
       mainAxisAlignment: MainAxisAlignment.center, 
       children: <Widget>[ 
        new Stack(fit: StackFit.passthrough, 
        children: <Widget>[ 
         new IconButton(icon: new Icon(
         Icons.cloud_circle, size: 40.0, color: Colors.blue,), 
          onPressed:()=>setState((){ 
         _myOpacity =0.0; 
          }) /*_destroyWidget*/), 
         new Positioned(child: new Opacity(
         opacity: _myOpacity, 
          child: 
         new DecoratedBox(
         decoration: new BoxDecoration(shape: BoxShape.circle), 
         child: new Icon(
          Icons.add_circle, size: 20.0, color: Colors.red,),),), 
          top: 3.0, 
          left: 3.0) 
        ], 
       ), 
        new RaisedButton(onPressed:()=> 
        setState((){ 
        _myOpacity = 1.0; 

     }) 
        /*_recreateWidget*/, 
        child: new Text("Recreate!"), 
       ), 
       ]) 
     ) 
    ); 
    } 
+0

目的是什么。你为什么要摧毁和重建?如果你想更新视图,调用'setState()'应该做你想要的。例如见https://codelabs.developers.google.com/codelabs/flutter/index.html#5 –

+0

真的出于好奇。但为了回答你的问题,我想到了用户在商店中订购某些东西的场景。将云图标视为您的购物车,并将其重新添加按钮称为“添加到购物车”,同时按下红色图标,就好像“您的购物车中有物品”一样。然后当你完成添加东西时,你点击购物车,一个应该删除红色图标的动作。 我明白如何通过操纵状态来实现相同的行为,我添加了一个更新的帖子,我通过操作“不透明度”来显示相同​​的行为。 – aziza

+0

如果下面的答案没有回答你的问题,那么给答案添加评论可能是一个好主意,以便Collin得到通知。 –

回答

2

您必须包装在StatefulWidget你的红色图标,如果你想,当它被初始化并设置通知。 A StatelessWidget没有这些回调。

您可以将StatefulWidget替换为setState中的空值,并且将丢弃其State。您可以在第二个setState回调中将其设置恢复正​​常,并且将创建一个新的State并调用其initState

如果你想disposeinitState没有通过具有小部件的中间步骤要与null更换,试着给你的StatefulWidget当按下按钮,重新创建一个新的UniqueKey。这将防止Flutter将旧的State与新的StatefulWidget联系起来。

看起来你似乎主要是出于好奇而不是真正的用例。您所描述的购物卡示例可能根本不需要使用initStatedispose,您应该只使用StatelessWidget

+0

我已经更新了一些代码,实现了我想到的同样的行为,但通过操纵'opacity'属性。这意味着图标仍然是用户界面的一部分,但用户无法看到它,所以这是一个好习惯吗? 对于你的答案,我不明白我怎样才能将'icon'属性设置为null并且仍然能够构建UI。如果你的意思是我需要将我的班级分成几个班级(例如:一个班级为重新创建和云,一个班级为红色图标)。那么,我该如何沟通这两个班级之间的状态。 – aziza

+0

即:当用户操作发生在我的主UI类上时,更改红色图标类的状态。我是否正确地得到你的答案? – aziza

+0

是的,如果你想在初始化和处置时收到通知,你应该将你的红色图标包裹在'StatefulWidget'中。一个'StatelessWidget'没有这些回调。我更新了我的答案以反映这一点。 –

相关问题