StreamBuilder快照null几秒钟

问题描述 投票:0回答:1

我正在尝试使用RxDart的BLoC模式,我想通过StreamBuilder从列表中获取事件。

我的问题是,当我打开我的详细信息屏幕时,像1秒我有以下错误消息:The method 'firstWhere' was called on null.

有没有办法等待获取数据而不添加加载进度,因为我想将HeroAnimation保留在我的图像上?

class _EventsDetailsScreenState extends State<EventsDetailsScreen> {
  @override
  Widget build(BuildContext context) {
    final eventBloc = BlocProvider.of<EventsBloc>(context);
    //Event event = eventBloc.events.firstWhere((elmt) => elmt.id == widget.id, orElse:() => null);
    return StreamBuilder(
      stream : eventBloc.allEvents,
      builder: (context, snapshot){
        final Event event = snapshot.data.firstWhere((elmt) => elmt.id == widget.id, orElse:() => null);
        return Scaffold(
          body: Stack(
            children: <Widget>[
              Column(children: <Widget>[
                Expanded(
                    child: ListView(
                  shrinkWrap: true,
                  children: <Widget>[
                    _buildEventImage(context, event),
                    (event.description != null && event.description.trim().isNotEmpty) ? _buildDescriptionSection(context, event) : Container(),
                  ],
                ))
              ]),
              new Positioned(
                //Place it at the top, and not use the entire screen
                top: 0.0,
                left: 0.0,
                right: 0.0,
                child: AppBar(
                  actions: <Widget>[
                    IconButton(icon: Icon(Icons.create), onPressed: () async => print('Edit')),
                  ],
                  backgroundColor: Colors.transparent, //No more green
                  elevation: 0.0, //Shadow gone
                ),
              ),
            ],
          ),
        );
      },
    );
  }

  Widget _buildEventImage(BuildContext context, Event event) {
    return Hero(
      tag: 'eventImg${event.id}',
      child: Container(
          decoration: BoxDecoration(
            image: DecorationImage(
                image: AssetImage("images/croatia.jpg"),
                alignment: Alignment.topCenter,
                fit: BoxFit.fill),
          ),
          padding: EdgeInsets.only(left: 40.0, bottom: 250.0),
          alignment: Alignment.bottomLeft,
          height: MediaQuery.of(context).size.height - 30.0,
          child: Column(
            mainAxisAlignment: MainAxisAlignment.end,
            crossAxisAlignment: CrossAxisAlignment.start,
            children: <Widget>[
              Container(
                child: Material(
                    color: Colors.transparent,
                    child: Text(
                      event.name,
                      style: eventNameTextStyle,
                    )),
              ),
              Container(
                  child: Material(
                      color: Colors.transparent,
                      child: Text(
                          "In ${event.date.difference(DateTime.now()).inDays} days",
                          style: eventDateTextStyle)))
            ],
          )),
    );
  }
dart flutter rxdart
1个回答
0
投票

您可以添加if语句来检查快照是否包含数据,这样只有在快照中有数据时才会调用firstWhere函数:

 class _EventsDetailsScreenState extends State<EventsDetailsScreen> {
 @override
 Widget build(BuildContext context) {
  final eventBloc = BlocProvider.of<EventsBloc>(context);
  //Event event = eventBloc.events.firstWhere((elmt) => elmt.id == widget.id, orElse:() => null);
  return StreamBuilder(
  stream : eventBloc.allEvents,
  builder: (context, snapshot){
   if(snapshot.hasData){
     return Scaffold(
      body: Stack(
        children: <Widget>[
          Column(children: <Widget>[
            Expanded(
                child: ListView(
              shrinkWrap: true,
              children: <Widget>[
                _buildEventImage(context, event),
                (event.description != null && event.description.trim().isNotEmpty) ? _buildDescriptionSection(context, event) : Container(),
              ],
            ))
          ]),
          new Positioned(
            //Place it at the top, and not use the entire screen
            top: 0.0,
            left: 0.0,
            right: 0.0,
            child: AppBar(
              actions: <Widget>[
                IconButton(icon: Icon(Icons.create), onPressed: () async => print('Edit')),
              ],
              backgroundColor: Colors.transparent, //No more green
              elevation: 0.0, //Shadow gone
            ),
          ),
        ],
      ),
    );
  }else{
    return Scaffold();
  }
});
}
© www.soinside.com 2019 - 2024. All rights reserved.