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

Flutter中OpenContainer同组件关闭时动画异常问题求助

Flutter OpenContainer 关闭动画错位问题解决办法

问题描述

我用Flutter的animations包实现Container Transform动画,配合story包开发类似Instagram的故事功能。通过水平ListView展示故事,每个列表项返回OpenContainer组件:closedBuilder返回自定义容器,openBuilder返回StoryPageView。目前除关闭动画外其他功能正常,具体问题:

  • 有3个故事容器时,点击第一个打开后,在第二个故事结束或主动关闭时,关闭动画会在第一个容器上执行
  • 点击第二个打开后,在第三个故事关闭时,动画会在第二个容器上执行
    已尝试给自定义容器设置Key,但未解决问题。

相关代码:

List<StoryModel> stories = state.storyList;
return ListView.separated(
  physics: const BouncingScrollPhysics(),
  separatorBuilder: (context, index) => 8.horizontalSpace,
  scrollDirection: Axis.horizontal,
  itemBuilder: (context, index) {
    return OpenContainer(
      useRootNavigator: true,
      closedBuilder: (context, action) {
        return HorizontalImagesItem(
          storyImageUrl: stories[index].stories[0].image,
        );
      },
      openBuilder: (context, action) => StoryPage(
        storyList: stories,
        storyPageIndex: index,
      ),
    );
  },
  itemCount: stories.length,
);

解决办法

问题根源是ListView复用item时,OpenContainer实例被复用,导致动画关联的组件错位。之前给子组件加Key没用,需要给每个OpenContainer绑定唯一Key,且Key要和故事数据的唯一标识挂钩,不能仅用列表index(index会随滚动复用)。

修改步骤

  1. 给每个OpenContainer设置唯一Key,比如用StoryModel的唯一id字段(假设模型有id属性):
return OpenContainer(
  key: ValueKey(stories[index].id), // 用故事的唯一ID作为Key
  useRootNavigator: true,
  closedBuilder: (context, action) {
    return HorizontalImagesItem(
      storyImageUrl: stories[index].stories[0].image,
    );
  },
  openBuilder: (context, action) => StoryPage(
    storyList: stories,
    storyPageIndex: index,
  ),
);
  1. 确保StoryModel的id是全局唯一的(比如后端返回的唯一标识,或本地生成的UUID)。

如果你的StoryModel没有id字段,也可以临时用ValueKey('story_${stories[index].stories[0].image}')(假设故事首图地址唯一),但更推荐用数据本身的唯一标识,避免列表数据更新时出现异常。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.07.02 20:01:16