gpt4 book ai didi

flutter - Flutter-小部件的状态未更改

转载 作者:行者123 更新时间:2023-12-03 03:37:02 24 4
gpt4 key购买 nike

我几乎是Flutter的新手,正在尝试开发聊天应用程序。每当用户发送消息时,都应更改StateWidget,并且消息应显示在Listview中。
这种情况是在按Widget StateButton不变。但是,如果我对应用程序进行Hot Reload更改,则会更改StateWidget并显示消息。我在 View 中使用两个Widgets,并且在setState()中调用了Child Widget方法。如何从State刷新WidgetChild Widget
请查看我的代码,并让我知道解决方案。提前致谢。

父小部件:

class ChatScreen extends StatefulWidget {

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

class ChatState extends State<ChatScreen> {

static const int _logout = 303;

@override
Widget build(BuildContext context) {

return Scaffold(

appBar: AppBar(
title: Text(Strings.appNameString),
actions: <Widget>[

//IconButton(icon: Icon(Icons.add), onPressed: () {}),

PopupMenuButton<int>(

icon: Icon(Icons.more_vert),
elevation: 10,
//padding: EdgeInsets.all(5),
offset: Offset(0, 100),
itemBuilder: (BuildContext context) => [

PopupMenuItem(child: Text("Logout"), value: _logout,),
//PopupMenuDivider(height: 5,),
],
onSelected: (value) {

switch(value) {

case _logout: {

MyClass.SignOutofGoogle();
} break;

default: break;
}
},
),
],
),
body: Column(
// crossAxisAlignment: CrossAxisAlignment.center,
// mainAxisSize: MainAxisSize.max,
// mainAxisAlignment: MainAxisAlignment.end,

children: <Widget>[

Flexible(child: ListView.builder(
padding: new EdgeInsets.all(8.0),
reverse: true,
itemBuilder: (_, int index) => MyClass.messages[index],
itemCount: MyClass.messages.length)),
Container(
child: ChatWidget()),
],
),
);
}

}

子小部件:
class ChatWidget extends StatefulWidget {

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

class ChatWidgetState extends State<ChatWidget> {

final TextEditingController _textController = new TextEditingController();

Widget _buildTextComposer() {
return Container(
margin: const EdgeInsets.symmetric(horizontal: 10.0),

child: Align(

child: Column(

children: <Widget>[
Divider(height: 5.0, color: Colors.lightBlue,),
Container(

height: 6.8 * SizeConfig.heightSizeMultiplier,
child: Row(

children: <Widget>[
Container(
child: IconButton(
icon: Icon(Icons.add_photo_alternate),
iconSize: 6.7 * SizeConfig.imageSizeMultiplier,
color: Colors.lightBlueAccent,
onPressed: () {}),
),
Flexible(
child: TextField(
controller: _textController,
onSubmitted: _handleSubmitted,
decoration: InputDecoration.collapsed(
hintText: "Send a message"),
),
),
Container(
margin: EdgeInsets.symmetric(horizontal: 4.0),

child: IconButton(
icon: Icon(Icons.send),
iconSize: 6.7 * SizeConfig.imageSizeMultiplier,
color: Colors.lightBlueAccent,
onPressed: () {
_handleSubmitted(_textController.text);
}),
),
],
),
),
],
),
),
);
}

void _handleSubmitted(String text) {

_textController.clear();

ChatMessage message = new ChatMessage(
text: text,
);

setState(() {
MyClass.messages.insert(0, message);
});
}

@override
Widget build(BuildContext context) {

return _buildTextComposer();
}
}


class ChatMessage extends StatelessWidget {

final String text;

ChatMessage( {
this.text
});

@override
Widget build(BuildContext context) {
return new Container(
margin: const EdgeInsets.symmetric(vertical: 10.0),

child: Row(
//crossAxisAlignment: CrossAxisAlignment.start,
mainAxisAlignment: MainAxisAlignment.end,

children: <Widget>[
Column(
crossAxisAlignment: CrossAxisAlignment.end,

children: <Widget>[
//Text(MyClass.loggeduser.userName, style: Theme.of(context).textTheme.subhead),
Text("Sajib", style: Theme.of(context).textTheme.subhead),
Container(
margin: const EdgeInsets.only(top: 5.0),
child: Text(text),
),
],
),
Container(
margin: const EdgeInsets.only(right: 6.0, left: 12.0),

child: CircleAvatar(
//backgroundImage: NetworkImage(MyClass.loggeduser.photoUrl)),
child: Icon(Icons.account_circle, color: Colors.lightBlueAccent,)),
),
],
),
);
}
}

最佳答案

首先,@ Darish是正确的,因为您可能应该使用另一种状态管理系统,但要问“如何从子窗口小部件刷新窗口小部件的状态”这一问题。我将提供两个简单的答案:

  • _handleSubmitted方法移至ChatState小部件,并将其传递给ChatWidget:
    class ChatState extends State<ChatScreen> {

    ...
    @override
    Widget build(BuildContext context) {
    ...
    Container(
    child: ChatWidget(onMessageSubmitted: this._handleSubmitted)),
    ...
    }

    void _handleSubmitted(String text) {
    ChatMessage message = new ChatMessage(
    text: text,
    );

    setState(() {
    MyClass.messages.insert(0, message);
    });
    }
    }

    然后从您的 child 小部件:
    class ChatWidget extends StatefulWidget {

    final Function(String) onMessageSubmitted;

    ChatWidget({this.onMessageSubmitted});

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

    class ChatWidgetState extends State<ChatWidget> {
    ...

    Widget _buildTextComposer() {
    ...
    TextField(
    controller: _textController,
    onSubmitted: _handleSubmitted,
    decoration: InputDecoration.collapsed(
    hintText: "Send a message"),
    ),
    ...
    IconButton(
    ...
    onPressed: () {
    _handleSubmitted(_textController.text);
    },
    ),
    ...
    }

    void _handleSubmitted(String text) {
    _textController.clear();

    widget.onMessageSubmitted(text);
    }
    ...
    }
  • 直接从ChatState访问您的ChatWidgetState:
    class ChatScreen extends StatefulWidget {

    ...

    static ChatState of(BuildContext context) => context.findAncestorStateOfType<ChatState>();
    }

    class ChatState extends State<ChatScreen> {

    ...

    void onMessageSubmitted(String text) {
    ChatMessage message = new ChatMessage(
    text: text,
    );

    setState(() {
    MyClass.messages.insert(0, message);
    });
    }
    }

    然后可以在ChatWidget中保持原样,但是在ChatWidgetState中,像下面这样更改_handleSubmitted方法:
    void _handleSubmitted(String text) {
    _textController.clear();

    ChatScreen.of(context).onMessageSubmitted(text);
    }

  • 数字2更接近于其他可以说是更好的状态管理方法,但是两者都是直接从子窗口小部件更新父窗口小部件的状态的示例。

    关于flutter - Flutter-小部件的状态未更改,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/60187297/

    24 4 0
    Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
    广告合作:1813099741@qq.com 6ren.com