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

Flutter首次启动加载JSON文件时dataJsonObject返回null热重载后正常

问题原因

你遇到的现象本质是异步执行时序导致的:
你在initState中调用的getJsonProverb是异步函数,Dart执行异步函数时不会等待它执行完成,会直接继续走后续的生命周期流程,首次触发build方法时,JSON文件还没完成加载、解析,所以dataJsonObject还是初始的null值。
而热重载/热重启不会清空内存中已经缓存的变量,此时dataJsonObject已经在上次运行时完成赋值,所以能正常显示。

解决方案

Flutter官方针对异步资源渲染的标准方案是使用FutureBuilder组件,你可以按以下代码修改:

import 'package:flutter/material.dart';
import 'dart:convert'; 
import 'package:flutter/services.dart'; 
import 'package:flutter/foundation.dart'; 

class ProverbDisplay extends StatefulWidget {
  final int myId;
  final String myCountry;
  const ProverbDisplay(this.myId, this.myCountry);

  @override
  _ProverbDisplayState createState() => _ProverbDisplayState();
}

class _ProverbDisplayState extends State<ProverbDisplay> {
  // 获取JSON方法,明确返回值类型
  Future<Map<String, dynamic>> getJsonProverb() async {
    final String rawJson = await rootBundle.loadString('assets/json/data.json');
    // jsonDecode是同步方法,不需要加await
    Map<String, dynamic> dataJsonObject = jsonDecode(rawJson);
    return dataJsonObject;
  }

  @override
  void initState() {
    super.initState();
    // 不需要在这里调用异步方法
  }

  @override
  Widget build(BuildContext context) {
    return FutureBuilder<Map<String, dynamic>>(
      future: getJsonProverb(),
      builder: (context, snapshot) {
        // 加载中状态,展示加载指示器
        if (snapshot.connectionState == ConnectionState.waiting) {
          return const Center(child: CircularProgressIndicator(color: Colors.white,));
        }
        // 加载出错状态,展示错误提示
        if (snapshot.hasError) {
          return Center(child: Text('加载失败:${snapshot.error}'));
        }
        // 加载完成,取数据正常渲染
        Map<String, dynamic> dataJsonObject = snapshot.data!;
        debugPrint(' jsonData : $dataJsonObject');
        return Container(
          color: Colors.blue,
          height: 250,
          child: Row(
            children: [
              Container(
                width: 300,
                child: PageView.builder(itemBuilder: (context, index) {
                  return Text("$dataJsonObject");
                }),
              ),
            ],
          ),
        );
      },
    );
  }
}
核心修改说明
  • 用FutureBuilder包裹原有渲染逻辑,它会自动监听异步方法的执行状态,等异步执行完成后再触发渲染,不会出现首次运行拿空值的问题
  • 新增了加载中、加载出错的兜底状态,既避免空指针异常,也提升了用户体验
  • 移除了initState中的异步调用,也不需要再用全局变量存储JSON解析结果,直接从snapshot.data中取即可

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.10.06 17:36:03