仅在第一次构建时出现意外行为,然后出现错误Flutter

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

当我从SQLLite DB中读取保存的Erros is type 'List<dynamic>' is not a subtype of type 'List<LatLng>'时收到此错误UserRoute。我首先尝试使用json编码器/解码器直接对列表进行编码/解码,然后添加了一个额外的步骤,即在对列表进行编码之前分别对每个坐标进行编码,但是当读回时会出现错误。怪异的行为是,我仅在第一次构建时得到错误,在热重启时会读取db fine。我在BlocListener中打印加载的路由

state received
I/flutter (17812): saved route are 4
I/flutter (17812): [Route: {RO-f3c86115-3f85-4542-88e2-ad374991bbf7,ffff,0.22044000000000002,0.22044000000000002,[LatLng(latitude:44.500714, longitude:11.335623), LatLng(latitude:44.500714, longitude:11.335623),

但是屏幕的ListView中没有显示任何元素。另外,仍然仅在第一次构建时发生,仅在弹出SelectRouteScreen时才会调度bloc事件,而在加载时不会调度。你能看到我做错了吗?这是模型类:

class UserRoute {
  final String routeId;
  final String routeName;
  final String routeDistance;
  final String routeDuration;
  final List<LatLng> coordinates;
  const UserRoute(
      {@required this.routeId,
      @required this.routeName,
      @required this.routeDistance,
      @required this.routeDuration,
      @required this.coordinates});
  @override
  List<Object> get props =>
      [routeId, routeName, routeDistance, routeDuration, coordinates];
  @override
  String toString() =>
      'Route: {$routeId,$routeName,$routeDistance,$routeDuration,$coordinates}';

  factory UserRoute.fromMap(Map<String, dynamic> map) => new UserRoute(
        routeId: map["routeId"],
        routeName: map["routeName"],
        routeDistance: map["routeDistance"],
        routeDuration: map["routeDuration"],
//      coordinates: json
//          .decode(map["coordinates"])
        coordinates: latLngFromJson(map["coordinates"]),
      ); //todo check if correct

  Map<String, dynamic> toMap() => {
        "routeId": routeId,
        "routeName": routeName,
        "routeDistance": routeDistance,
        "routeDuration": routeDuration,
//        "coordinates": json.encode(coordinates)
        "coordinates": latLngToJson(coordinates)
      };
}

List<LatLng> latLngFromJson(String str) {
  final jsonData = json.decode(str);
  return new List<LatLng>.from(jsonData.map((x) => fromJson(x)));
}

String latLngToJson(List<LatLng> data) {
  final dyn = new List<dynamic>.from(data.map((x) => toJson(x)));
  return json.encode(dyn);
}

LatLng fromJson(Map<String, dynamic> json) => new LatLng(
      json["lat"].toDouble(),
      json["lng"].toDouble(),
    );

Map<String, dynamic> toJson(LatLng coordinate) => {
      "lat": coordinate.latitude,
      "lng": coordinate.longitude,
    };

这是存储库中的方法:

Future<List<UserRoute>> loadRoutes() async {
    final db = await database;
    var res = await db.query("Route");
    List<UserRoute> list =
        res.isNotEmpty ? res.map((c) => UserRoute.fromMap(c)).toList() : [];
    return list;
  }

这是屏幕:

class SelectRouteScreen extends StatefulWidget {
  bool isIOS = Platform.isIOS ? true : false;

  User user;
  String routeName;
  SelectRouteScreen({@required this.user});
  @override
  _SelectRouteScreenState createState() => _SelectRouteScreenState();
}

class _SelectRouteScreenState extends State<SelectRouteScreen> {
  @override
  Widget build(BuildContext context) {
    AudioCache cache = new AudioCache();
    List<UserRoute> routes = [];
    List<RouteCell> cells = [];
    cache.loadAll(['click.mp3', 'tableViewOpen.mp3', 'tableViewClose.mp3']);
    return BlocListener<RouteBloc, RouteState>(
      listener: (BuildContext context, RouteState state) {
        if (state is RoutesLoaded) {
          print('state received');
          setState(() {
            routes.clear();
            cells.clear();
            routes = state.userRoutes;
            print('saved route are ${state.userRoutes.length}');
            print(routes);
            cells = state.schedulerCells;
          });
        }
      },
      child: Scaffold(
        appBar: AppBar(
          backgroundColor: Colors.transparent,
          elevation: 0,
          centerTitle: true,
          leading: IconButton(
              icon: widget.isIOS
                  ? Icon(CupertinoIcons.back)
                  : Icon(Icons.arrow_back),
              color: Colors.redAccent,
              onPressed: () {
                cache.play('tableViewClose.mp3');
                Navigator.pop(context, widget.routeName);
              }),
          title: Text(
            'Seleziona tragitto',
            style: TextStyle(
                color: Colors.orange,
                fontSize: 22,
                fontWeight: FontWeight.w500,
                letterSpacing: 1),
          ),
        ),
        body: Container(
          padding: EdgeInsets.all(20),
          color: Colors.redAccent,
          child: ListView.builder(
            itemCount: routes.length,
//          itemBuilder: (BuildContext context, int index) => Container(
//            padding: EdgeInsets.all(10),
//            color: Colors.red,
//            child: cells[index],
//          ),
            itemBuilder: (BuildContext context, int index) => RouteCell(
              routeName: '${routes[index].routeName}',
              isSelected: false,
              onTap: () {
                widget.routeName = routes[index].routeName;
              },
              onTapCancel: () {
                widget.routeName = null;
              },
            ),
          ),
        ),
      ),
    );
  }
}

这是到屏幕的导航:

IconButton(
                              icon: isIOS
                                  ? Icon(CupertinoIcons.forward)
                                  : Icon(Icons.arrow_forward),
                              iconSize: 20,
                              color: Colors.redAccent,
                              onPressed: () async {
                                cache.play('tableViewOpen.mp3');
                                Timer(Duration(milliseconds: 200), () {
                                  BlocProvider.of<RouteBloc>(context).add(
                                      LoadRoutes(userName: widget.user.name));
                                });

//                                routeName = await Navigator.push(
                                Navigator.push(
                                  context,
                                  MaterialPageRoute(
                                    builder: (_) => BlocProvider.value(
                                      value:
                                          BlocProvider.of<RouteBloc>(context),
                                      child:
                                          SelectRouteScreen(user: widget.user),
                                    ),
                                  ),
                                );
                              },
                            )
json flutter
1个回答
0
投票

这似乎发生在使用模型结构的列表中,请尝试更改

final List<LatLng> coordinates;

to

final List<dynamic> coordinates;

和来自

List<LatLng> latLngFromJson(String str) {
  final jsonData = json.decode(str);
  return new List<LatLng>.from(jsonData.map((x) => fromJson(x)));
}

to

List<dynamic> latLngFromJson(String str) {
  final jsonData = json.decode(str);
  return new List<dynamic>.from(jsonData.map((x) => fromJson(x)));
}

在您的模型课程中。

© www.soinside.com 2019 - 2024. All rights reserved.