Search code examples
flutterdartsetstate

Why I use setState in async funtion not update state (Flutter)?


Why my _image not update?

I need _image properties update when user pick new image from gallery or camera, but when user pick new images I use setState for set new value to _image but it didn't work(didn't update UI).

Here my code I have problem: Sorry I cant full source because editor of stackoverflow complain to many code.

Statefull Class: enum ChooseMedia { camera, gallery }

  File _image;

  void getImage(ChooseMedia media) async {
    if (media == ChooseMedia.camera) {
      var image = await ImagePicker.pickImage(source: ImageSource.camera);
      var pathLocal = await getApplicationDocumentsDirectory();
      await image.copy('${pathLocal.path}/profileImage.jpg').then((_) {
        setState(() {
          _image = image;
        });
      });
    }
    if (ChooseMedia.gallery == media) {
      var image = await ImagePicker.pickImage(source: ImageSource.gallery);
      var pathLocal = await getApplicationDocumentsDirectory();

      await image.copy('${pathLocal.path}/profileImage.jpg').then((_) {
        setState(() {
          _image = image;
        });
      });
    }
  }



  @override
  Widget build(BuildContext context) {

        return PopupMenuButton(
          elevation: 5,
          shape: RoundedRectangleBorder(
              borderRadius: BorderRadius.all(Radius.circular(15))),
          onSelected: (ChooseMedia media) {
            getImage(media);
          },
          itemBuilder: (BuildContext context) => <PopupMenuEntry<ChooseMedia>>[
            const PopupMenuItem<ChooseMedia>(
              value: ChooseMedia.gallery,
              child: ListTile(
                leading: Icon(
                  Icons.picture_in_picture,
                ),
                title: Text('From galaxy'),
              ),
            ),
            const PopupMenuItem<ChooseMedia>(
              value: ChooseMedia.camera,
              child: ListTile(
                leading: Icon(Icons.camera),
                title: Text('Take picture'),
              ),
            ),
          ],
          child: Container(
              decoration: BoxDecoration(),
              padding: EdgeInsets.all(7),
              child: CircleAvatar(
                  backgroundImage: _image == null
                      ? AssetImage('assets/images/profile.jpg')
                      : FileImage(_image))),
        );
  }


Solution

  • You are mixing 'await' and 'then' Just do

    var copiedImage = await image.copy('${pathLocal.path}/profileImage.jpg');
    setState(() {
        _image = copiedImage;
    });