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

如何将硬编码Flutter widget改造为支持函数参数的可复用模块化组件

实现方案

核心改造思路

你要实现的是Flutter列表类组件的通用封装逻辑,只需要给自定义组件暴露列表项构建函数入参,把内部固定的列表项渲染逻辑替换为外部传入的逻辑即可,具体改动如下:

  1. 给PageOne组件新增两个必传参数:
  • indexCount:列表总项数,直接传给SliverChildBuilderDelegate的childCount属性
  • itemBuilder:类型为Widget Function(BuildContext context, int index),由外部使用时传入,接收当前上下文和下标参数,返回对应下标的列表项Widget
  1. 将SliverChildBuilderDelegate内部固定的列表项代码,替换为调用传入的itemBuilder方法

完整改造后代码

import 'package:flutter/material.dart';
import 'package:flutter_riverpod/flutter_riverpod.dart';
import 'package:easy_refresh/easy_refresh.dart';

// 提前定义builder类型,让代码可读性更高
typedef SliverItemBuilder = Widget Function(BuildContext context, int index);

class PageOne extends StatelessWidget {
  final int indexCount;
  // 列表项构建函数入参
  final SliverItemBuilder itemBuilder;
  // 可按需扩展下拉刷新、上拉加载的回调入参,适配不同场景的交互逻辑
  final Future<void> Function()? onRefresh;
  final Future<void> Function()? onLoad;

  const PageOne({
    Key? key,
    required this.indexCount,
    required this.itemBuilder,
    this.onRefresh,
    this.onLoad,
  }) : super(key: key);

  @override
  Widget build(BuildContext context) {
    return SafeArea(
      child: Row(
        children: [
          const SizedBox(width: 40.0),
          Consumer(builder: (context, ref, child) {
            return Expanded(
              child: EasyRefresh.custom(
                onRefresh: onRefresh,
                onLoad: onLoad,
                slivers: [
                  SliverList(
                    delegate: SliverChildBuilderDelegate(
                      (BuildContext context, int index) {
                        // 直接调用外部传入的构建函数生成对应下标的列表项
                        return itemBuilder(context, index);
                      },
                      childCount: indexCount,
                    ),
                  ),
                ],
              ),
            );
          }),
        ],
      ),
    );
  }
}

使用示例

改造完成后可以在任意场景传入不同的参数复用组件,示例如下:

// 场景1:渲染蓝色卡片列表
PageOne(
  indexCount: 10,
  onRefresh: () async => print('触发下拉刷新'),
  itemBuilder: (context, index) {
    return Card(
      margin: const EdgeInsets.all(15),
      child: Container(
        color: Colors.blue[100 * (index % 9 + 1)],
        height: 80,
        alignment: Alignment.center,
        child: Text(
          '场景1 项 $index',
          style: const TextStyle(fontSize: 30),
        ),
      ),
    );
  },
)

// 场景2:渲染纯文本列表
PageOne(
  indexCount: 20,
  itemBuilder: (context, index) {
    return Padding(
      padding: const EdgeInsets.all(20),
      child: Text(
        '场景2 第$index项',
        style: const TextStyle(fontSize: 16, color: Colors.red),
      ),
    );
  },
)

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.09.26 06:45:01