You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Dart命令行应用中Bloc不发射状态的问题求助

问题:Dart命令行中Bloc无法发射新状态

在Dart命令行应用中使用Bloc框架时,添加JugadorAgregado事件后无法触发Lobby状态切换,程序始终停留在EstadoInicial状态,无法进入porHacer函数。以下是问题代码:

import 'dart:io';

import 'package:dart_console/dart_console.dart';
import 'dart:async';
import 'package:bloc/bloc.dart';

sealed class Estado {}

class EstadoInicial extends Estado {}

class Lobby extends Estado {}

sealed class Evento {}

class JugadorAgregado extends Evento {}

class JuegoBloc extends Bloc<Evento, Estado> {
  JuegoBloc() : super(EstadoInicial()) {
    on<JugadorAgregado>(_onJugadorAgregado);
  }

  FutureOr<void> _onJugadorAgregado(event, emit) {
    emit(Lobby());
  }
}

final consola = Console();
final bloc = JuegoBloc();

void main(List<String> arguments) {
  do {
    var estado = bloc.state;
    // ignore: unused_local_variable
    var noImporta = switch (estado) {
      (EstadoInicial _) => estadoInicial(),
      _ => porHacer(),
    };
  } while (true);
}

void estadoInicial() {
  print('entré al estado inicial');
  bloc.add(JugadorAgregado());
  Future.delayed(Duration(seconds: 2));
}

void porHacer() {
  print('Aún no implementado');
  exit(0);
}

问题原因

  1. 同步死循环阻塞状态更新:主函数的do-while是同步循环,会持续读取Bloc的初始状态,完全没有给Bloc异步处理事件、更新状态的机会。
  2. 未正确等待异步操作:estadoInicial中的Future.delayed没有使用await,代码会直接跳过延迟继续执行,循环立刻再次读取初始状态。
  3. 错误的状态读取方式:主动读取bloc.state无法感知Bloc的异步状态变化,需要通过监听状态流来响应更新。

修复方案

改用监听Bloc的state流来响应状态变化,同时正确处理异步操作:

import 'dart:io';
import 'dart:async';
import 'package:bloc/bloc.dart';

sealed class Estado {}
class EstadoInicial extends Estado {}
class Lobby extends Estado {}

sealed class Evento {}
class JugadorAgregado extends Evento {}

class JuegoBloc extends Bloc<Evento, Estado> {
  JuegoBloc() : super(EstadoInicial()) {
    on<JugadorAgregado>(_onJugadorAgregado);
  }

  FutureOr<void> _onJugadorAgregado(event, emit) {
    emit(Lobby());
  }
}

final bloc = JuegoBloc();

void main(List<String> arguments) async {
  // 监听Bloc状态变化
  final subscription = bloc.stream.listen((estado) {
    switch (estado) {
      case EstadoInicial _:
        estadoInicial();
        break;
      case Lobby _:
        porHacer();
        break;
    }
  });

  // 初始状态触发处理
  estadoInicial();

  // 保持程序运行,直到手动退出
  await Forever().future;
}

void estadoInicial() async {
  print('entré al estado inicial');
  bloc.add(JugadorAgregado());
  // 正确等待延迟
  await Future.delayed(const Duration(seconds: 2));
}

void porHacer() {
  print('Aún no implementado');
  exit(0);
}

// 用于保持程序运行的辅助类
class Forever {
  Completer<void> completer = Completer<void>();
  Future<void> get future => completer.future;
}

关键修改点

  • 通过bloc.stream.listen监听状态流,状态更新时自动触发对应逻辑。
  • main函数改为async,使用辅助类Forever保持程序运行,避免提前退出。
  • estadoInicial中添加await等待Future.delayed,确保异步操作完成。

内容的提问来源于stack exchange,提问作者Juan Algara

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.05 12:06:15