본문 바로가기
Flutter/Flutter FAQ

Flutter에서 다른 StatefulWidget에서 StatefulWidget의 상태를 설정/업데이트하는 방법은 무엇인가요?, How to Set/Update State of StatefulWidget from other StatefulWidget in Flutter?

by 베타코드 2023. 6. 1.
반응형

질문


  1. 예를 들어 아래 코드에서는 더하기 버튼이 작동하여 텍스트를 업데이트할 수 있지만, 마이너스 버튼은 그렇지 않습니다.
  2. 하지만 FloatingActionButton을 누르면 상태가 새로 고침됩니다.
  3. 마이너스 버튼은 변수의 값을 변경하지만 부모 위젯의 상태를 업데이트하지 않습니다.

enter image description here

여기 코드가 있습니다...

import 'package:flutter/material.dart';

void main() => runApp(new MyApp());

class MyApp extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return new MaterialApp(
      title: 'Flutter Demo',
      theme: new ThemeData(
        primarySwatch: Colors.blue,
      ),
      home: new MyHomePage(title: 'Flutter Demo Home Page'),
    );
  }
}

int number;

EdgeInsets globalMargin = const EdgeInsets.symmetric(horizontal: 20.0, vertical: 20.0);
TextStyle textStyle = const TextStyle(
  fontSize: 100.0,
  color: Colors.black,
);

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

  final String title;

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

class _MyHomePageState extends State<MyHomePage> {
  @override
  void initState() {
    super.initState();
    number = number ?? 0;
  }

  @override
  Widget build(BuildContext context) {
    return new Scaffold(
      appBar: new AppBar(
        title: new Text(widget.title),
      ),
      body: new Column(
        children: <Widget>[
          new Text(
            number.toString(),
            style: textStyle,
          ),
          new GridView.count(
            crossAxisCount: 2,
            shrinkWrap: true,
            scrollDirection: Axis.vertical,
            children: <Widget>[
              new InkResponse(
                child: new Container(
                    margin: globalMargin,
                    color: Colors.green,
                    child: new Center(
                      child: new Text(
                        "+",
                        style: textStyle,
                      ),
                    )),
                onTap: () {
                  setState(() {
                    number = number + 1;
                  });
                },
              ),
              new Sub(),
            ],
          ),
        ],
      ),
      floatingActionButton: new FloatingActionButton(
        onPressed: () {
          setState(() {});
        },
        child: new Icon(Icons.update),
      ),
    );
  }
}

class Sub extends StatefulWidget {
  @override
  _SubState createState() => new _SubState();
}

class _SubState extends State<Sub> {
  @override
  Widget build(BuildContext context) {
    return new InkResponse(
      child: new Container(
          margin: globalMargin,
          color: Colors.red,
          child: new Center(
            child: new Text(
              "-",
              style: textStyle,
            ),
          )),
      onTap: () {
        setState(() {
          number = number - 1;
        });
      },
    );
  }
}

답변


1. Child Widget에 매개변수 함수 추가하기

class ChildWidget extends StatefulWidget {
  final Function() notifyParent;
  ChildWidget({Key key, @required this.notifyParent}) : super(key: key);
}

2. Parent Widget에서 Child 콜백 함수 생성하기

refresh() {
  setState(() {});
}

3. Parent Widget에서 parentFunction을 Child Widget에 전달하기

new ChildWidget( notifyParent: refresh );  

4. Child Widget에서 Parent 함수 호출하기

  widget.notifyParent();
반응형

댓글