TuGordoBello
TuGordoBello

Reputation: 4509

CheckboxListTile has null value using Bloc and Stream on Flutter

I am creating register form on my flutter app (version 1.17.4). I am using CheckboxListTile in order to user accept the terms. This widget is validated by bloc and stream

CheckboxListTile

  Widget _createAcceptConditions(LoginBloc bloc) {
return StreamBuilder(
  stream: bloc.getAcceptCondition,
  builder: (BuildContext context, AsyncSnapshot snapshot) {
    return Container(
      child: Container(
          padding: EdgeInsets.only(left: 5, top: 10),
          child: CheckboxListTile(
              title: Text("I accept the terms"),
              value: bloc.acceptCondition,
              activeColor: Colors.deepPurple,
              controlAffinity: ListTileControlAffinity.leading,
              onChanged: (value) {
                bloc.setAcceptCondition(value);
              })),
    );
  },
);
}

LoginBloc class

  final _acceptCondition = BehaviorSubject<bool>();
  Stream<bool> get getAcceptCondition =>
  _acceptCondition.stream.transform(validAcceptCondition);
//Setter
  Function(bool) get setAcceptCondition => _acceptCondition.sink.add;
//Getter
  bool get acceptCondition => _acceptCondition.value;

This is the validator

final validAcceptCondition =
  StreamTransformer<bool, bool>.fromHandlers(handleData: (accept, sink) {
accept ? sink.add(accept) : sink.addError("You must accept the conditions");
});

When I restart the app an try to register I got

════════ Exception caught by widgets library ═══════════════════════════════════
The following assertion was thrown building StreamBuilder<bool>(dirty, state: _StreamBuilderBaseState<bool, AsyncSnapshot<bool>>#8f6de):
'package:flutter/src/material/checkbox_list_tile.dart': Failed assertion: line 269 pos 15: 'value != null': is not true.

The relevant error-causing widget was
    StreamBuilder<bool> 
package:neighbour_mobile/…/pages/register_page.dart:205
When the exception was thrown, this was the stack
#2      new CheckboxListTile 
package:flutter/…/material/checkbox_list_tile.dart:269
#3      RegisterPage._createAcceptConditions.<anonymous closure> 
package:neighbour_mobile/…/pages/register_page.dart:211
#4      StreamBuilder.build 
package:flutter/…/widgets/async.dart:509
#5      _StreamBuilderBaseState.build 
package:flutter/…/widgets/async.dart:127
#6      StatefulElement.build 
package:flutter/…/widgets/framework.dart:4619
...

It seem the bloc is waiting for any user acction in order to put true or false into CheckboxListTile, how ever the default value is null

Upvotes: 1

Views: 1549

Answers (1)

Luis Miguel Mantilla
Luis Miguel Mantilla

Reputation: 1748

The value in the CheckBox cannot be null, and when you create a BehaviorSubject or a Stream they doesn't have any data. So you can work with the snapshot value and defining a initialData property in you StreamBuilder to initialize a default value when the Stream is created, try the next:

Widget _createAcceptConditions(LoginBloc bloc) {
    return StreamBuilder(
      stream: bloc.getAcceptCondition,
      // Add a initialData 
      initialData: false,
      builder: (BuildContext context, AsyncSnapshot snapshot) {
         // In this point you can validate the snapshot to show the error you are getting
      
         /**if(snapshot.hasError){
           // Do or show something, for example a Snackbar
         }*/
        return Container(
          child: Container(
            padding: EdgeInsets.only(left: 5, top: 10),
            child: CheckboxListTile(
              title: Text("I accept the terms"),
              // You don't need to use the acceptCondition in this section, because you have the value in the snapshot
              // value: bloc.acceptCondition,
              // In this part the first time the snapshot will be false
              value: snapshot.hasData && snapshot.data ? true : false,
              activeColor: Colors.deepPurple,
              controlAffinity: ListTileControlAffinity.leading,
              onChanged: (value) {
                bloc.setAcceptCondition(value);
              },
            ),
          ),
        );
      },
    );
  }

Hope it helps.

Upvotes: 1

Related Questions