Flutter State won't update

Viewed 264

I'm trying to create a listview of cards whose images get displayed in the listview only if the card is selected. The selection widget is the PopupSubscription() where I'm choosing which cards (SubscriptionCard) to display by setting the bool of that particular image to be true. But when the selections are applied, the selected images don't appear immediately even after doing setState(). However, they do appear when I switch tabs and return the screen again. What should I do in order to change the state of an object that's not in my current state class? I tried using Provider but it left me confused as to what I'm supposed to do.

This is the SubscriptionCard where the bool is set on tapping it:

return InkWell(
  radius: 1.0,
  borderRadius: BorderRadius.circular(8.0),
  highlightColor: buttonBackground,
  onTap: () {
    setState(() {
      widget.currentSubscription.selected = !widget.currentSubscription.selected;
    });
  },
  child: Card(
    elevation: 1.0,
    borderOnForeground: true,
    shape: widget.currentSubscription.selected ? RoundedRectangleBorder(
      borderRadius: BorderRadius.circular(3.0),
      side: BorderSide(color: buttonBackground, width: 2.0),
    ) : ContinuousRectangleBorder(),
    color: bgDarkColor,
    child: SizedBox(
      width: SizeConfig.blockSizeHorizontal * 30,
      child: Stack(
        alignment: Alignment.topRight,
        children: [
          Row(
            mainAxisSize: MainAxisSize.max,
            children: [
              Image.asset(this.widget.currentSubscription.logo, height: 35.0,),
              Text(
                '  ${this.widget.currentSubscription.name}',
                style: TextStyle(fontFamily: 'Muli', fontSize: 16.0)
              ),
            ],
          ),
          widget.currentSubscription.selected ? Container(
            decoration: BoxDecoration(
              shape: BoxShape.circle,
              color: buttonBackground,
            ),
            child: Padding(
              padding: const EdgeInsets.all(2.0),
              child: Icon(
                Icons.check,
                size: 10.0,
                color: Colors.white,
              ),
            ),
          ) : Container()
        ],
      ),
    ),
  ),
);

This is the ListView where the selected cards' images are rendered:

Container(
      height: 50,
      width: 350,
      child: ListView(
        scrollDirection: Axis.horizontal,
        children: [
          IconButton(
            onPressed: () {
              showDialog(
                context: context,
                builder: (BuildContext context) {
                  return PopupSubscription();
                }
              );
            },
            icon: Icon(Icons.add_box_rounded, size: 30.0,),
          ),
          StatefulBuilder(
            builder: (context, setState) {
              return ListView.builder(
                scrollDirection: Axis.horizontal,
                shrinkWrap: true,
                itemCount: subscriptionsList.length,
                itemBuilder: (context, index) {
                  return Container(
                    margin: EdgeInsets.symmetric(horizontal: 5.0),
                    child: ClipRRect(
                      borderRadius: BorderRadius.circular(25.0),
                      child: Image.asset(
                        subscriptionsList[index].selected ? subscriptionsList[index].logo
                        : "assets/elements/streaming-services/netflix.jpeg",
                      ),
                    ),
                  );
                },
              );
            }
          ),
        ],
      )
    ),
1 Answers

Based on your current code, I'm guessing you've added the currentSubscription variable as final in the StatefulWidget above the actual State, like:

class MyClass extends StatefulWidget{
    final currentSubscription;
    // Rest of the code
}
class _MyClassState extends State<MyClass> {
    // Your ListView Code and other stuff.
}

This wont work when you want to change the state onTap, I recommend making the variable you use in setState within the _MyClassState class and use setState in that. Something like:

class _MyClassState extends State<MyClass> {
    bool _isSelected = false; 

    // And in your onTap method, something like:
    setState(() {
      _isSelected = !_isSelected;
    });
}
Related