0

Here is the problem: I have a list of items displayed in a list view. I can edit these items with the dialogs displayed by clicking on them. After editing and closing the dialog, I also need to update the items on the list view. I'm currently doing this with the following code snippet in my list view item widget:

showDialog(
  context: context,
  builder: (context) {
    return UpdateItemDialog(item: _item);
  },
).then((updatedItem) {
  if (updatedItem != null) {
    setState(() => _item = updatedItem);
  }
});

and by calling Navigator.of(context).pop(_item); from my dialog.

It works perfectly fine when there are no rebuilds occur until the dialog is dismissed. However, for example, if the orientation is changed when the dialog is open, I get Unhandled Exception: setState() called after dispose() error since the list view also rebuilt because of the orientation change and the then clause in my code runs on the destroyed widget.

Is there a way to access the rebuilt widget from a destroyed widget?

Or should I use a different approach to this problem?

By the way, changes should only be accepted after the dialog is dismissed, so I should return the item from the dialog.

rasitayaz
  • 400
  • 2
  • 16

1 Answers1

1

I believe your best bet would be to introduce even a simple state management solution (Provider would be good) to handle communication between a dialog and other widgets.

Check out the Gist below (Run it on Dartpad.dev) as an example how you can keep it simple, yet clean and decoupled https://gist.github.com/romanejaquez/8aed8d699fba8fdfff4b0966dfe47663

in which I show that instead of passing data from a dialog back to another widget, a State Management solution would allow you for a decoupled way of passing data back and forth, notifying each other and triggering rebuilds (which is kind of calling setState() since pretty much that's what you want - trigger a rebuild on the other widget. In this example, I'm sending a value back to the originating widget and triggering a rebuild (thanks to the Consumer widget listening to the changes triggered in the common service. That'd be my honest suggestion.

Roman Jaquez
  • 2,499
  • 1
  • 14
  • 7
  • Thank you, I have a question though. If I wrap every item in the list view with a `Consumer`, then when an item will updated every single one of them will detect that change. How am I supposed to notify only the clicked item? – rasitayaz Feb 28 '22 at 12:55
  • I solved the problem by storing the list of items in my `ChangeNotifier` class and making the necessary changes there. – rasitayaz Feb 28 '22 at 16:27
  • 1
    you got it, bro! Making the changes in the ChangeNotifier keeps your logic clean and decoupled from the rendering logic. Well done – Roman Jaquez Feb 28 '22 at 16:45