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

Flutter路由添加页面遇必填参数错误,寻求解决方案

Flutter路由注册时未传入必填参数报错解决

错误提示

The named parameter 'xyz' is required, but there's no corresponding argument. Try adding the required argument.

相关代码

主页面路由注册代码

class BMICalculator extends StatelessWidget {
  const BMICalculator({super.key});

  @override
  Widget build(BuildContext context) {
    return MaterialApp(
      theme: ThemeData.dark().copyWith(
        appBarTheme: const AppBarTheme(color: Color(0xFF0A0E21)),
        scaffoldBackgroundColor: const Color(0xFF0A0E21),
      ),
      initialRoute: '/',
      routes: {
        InputPage.routeName: (context) => const InputPage(),
        ResultsPage.routeName: (context) => const ResultsPage(), 
      },
    );
  }
}

ResultsPage代码

class ResultsPage extends StatefulWidget {
  const ResultsPage(
      {required this.bmiResult,
      required this.interpretation,
      required this.resultText,
      super.key});
  static const routeName = '/resultsPage';

  final String? bmiResult;
  final String? resultText;
  final String? interpretation;
  @override
  State<ResultsPage> createState() => _ResultsPageState();
}

class _ResultsPageState extends State<ResultsPage> {
  @override
  Widget build(BuildContext context) {
    return Scaffold(
      appBar: AppBar(
        title: const Center(
          child: Text('BMI Calculator'),
        ),
      ),
      body: SafeArea(
        child: Column(
          mainAxisAlignment: MainAxisAlignment.spaceEvenly,
          crossAxisAlignment: CrossAxisAlignment.stretch,
          children: [
            Expanded(
              child: Container(
                padding: const EdgeInsets.all(15.0),
                alignment: Alignment.bottomCenter,
                child: const Text(
                  'Your Result',
                  style: kTitleTextStyle,
                ),
              ),
            ),
            Expanded(
              flex: 6,
              child: ReusableCard(
                colour: kActiveCardColor,
                cardChild: Column(
                  mainAxisAlignment: MainAxisAlignment.spaceEvenly,
                  crossAxisAlignment: CrossAxisAlignment.center,
                  children: const [
                    Text(
                      'Normal',
                      style: kResultTextStyle,
                    ),
                    Text(
                      '18.3',
                      style: kBMITextStyle,
                    ),
                    Text(
                      'Your res is low. Eat more',
                      style: kBodyTextStyle,
                    ),
                  ],
                ),
              ),
            ),
            BottomButton(
              onTap: () {
                setState(() {
                  Navigator.pop(context);
                });
              },
              buttonTitle: 'RE-CALCULATE',
            ),
          ],
        ),
      ),
    );
  }
}

解决方案

方案1:直接通过Navigator.push传递参数

放弃在routes中注册ResultsPage,在需要跳转的位置(比如InputPage的计算按钮点击事件)直接传入必填参数:

// InputPage中触发跳转的示例代码
Navigator.push(
  context,
  MaterialPageRoute(
    builder: (context) => ResultsPage(
      bmiResult: calculatedBMI, // 替换为实际计算出的BMI值
      resultText: resultCategory, // 替换为实际结果分类(如"Normal")
      interpretation: resultMessage, // 替换为实际解释文本
    ),
  ),
);

同时移除主页面routes中ResultsPage的注册:

routes: {
  InputPage.routeName: (context) => const InputPage(),
  // 移除ResultsPage的路由注册项
},

方案2:用onGenerateRoute处理带参数路由

若想保留路由名称跳转的方式,可替换routes为onGenerateRoute来处理参数传递:

1. 修改主页面MaterialApp配置

class BMICalculator extends StatelessWidget {
  const BMICalculator({super.key});

  @override
  Widget build(BuildContext context) {
    return MaterialApp(
      theme: ThemeData.dark().copyWith(
        appBarTheme: const AppBarTheme(color: Color(0xFF0A0E21)),
        scaffoldBackgroundColor: const Color(0xFF0A0E21),
      ),
      initialRoute: '/',
      onGenerateRoute: (settings) {
        if (settings.name == InputPage.routeName) {
          return MaterialPageRoute(
            builder: (context) => const InputPage(),
          );
        } else if (settings.name == ResultsPage.routeName) {
          // 取出传递的参数
          final args = settings.arguments as Map<String, String?>;
          return MaterialPageRoute(
            builder: (context) => ResultsPage(
              bmiResult: args['bmiResult'],
              resultText: args['resultText'],
              interpretation: args['interpretation'],
            ),
          );
        }
        // 默认跳转路由(可选)
        return MaterialPageRoute(builder: (context) => const InputPage());
      },
    );
  }
}

2. 跳转时传递参数

// InputPage中触发跳转的代码
Navigator.pushNamed(
  context,
  ResultsPage.routeName,
  arguments: {
    'bmiResult': calculatedBMI,
    'resultText': resultCategory,
    'interpretation': resultMessage,
  },
);

额外优化建议

可以将参数封装为独立类,替代Map实现更安全的类型检查:

class ResultsArguments {
  final String? bmiResult;
  final String? resultText;
  final String? interpretation;

  ResultsArguments(this.bmiResult, this.resultText, this.interpretation);
}

传递参数时改为:

arguments: ResultsArguments(calculatedBMI, resultCategory, resultMessage),

在onGenerateRoute中取出参数:

final args = settings.arguments as ResultsArguments;

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.15 19:45:40