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

Flutter基于CustomPainter的带动画自定义单选按钮状态更新异常问题

问题原因

你的自定义Radio组件没有监听父组件传入的groupValue变化,仅在initState初始化时判断了一次选中状态,当父组件调用setState更新groupValue时,已经初始化的Radio子组件没有响应状态变化,所以原选中项不会触发取消动画。

修复步骤

1. 重写didUpdateWidget生命周期方法

在_MyRadioState类中添加这个方法,监听groupValue的变化,动态触发动画:

@override
void didUpdateWidget(covariant MyRadio<T> oldWidget) {
  super.didUpdateWidget(oldWidget);
  // 新旧groupValue发生变化时处理动画
  if (oldWidget.groupValue != widget.groupValue) {
    final isSelected = check();
    if (isSelected) {
      // 从非选中变为选中,正向播放动画
      radiusAnimationController.forward();
    } else {
      // 从选中变为非选中,反向播放动画
      radiusAnimationController.reverse();
      labelAnimationController.reverse();
    }
  }
}

2. 修正动画状态监听逻辑

原来的动画监听逻辑存在错误,会导致动画重复执行无响应,修改radiusAnimation和labelAnimation的状态监听代码:

radiusAnimation = _radiusTween.animate(radiusAnimationController)
  ..addListener(() => setState(() {}))
  ..addStatusListener((status) {
    if (status == AnimationStatus.completed) {
      labelAnimationController.forward();
    }
    if (status == AnimationStatus.dismissed) {
      // 取消选中时重置label动画
      labelAnimationController.reset();
    }
  });
labelAnimation = _labelTween.animate(labelAnimationController)
  ..addListener(() => setState(() {}));
// 删除原来labelAnimation多余的状态监听逻辑

3. 调整onTap逻辑(可选优化)

onTap中不需要额外判断选中状态,因为点击后父组件会更新groupValue,didUpdateWidget会统一处理动画逻辑:

onTap: () {
  widget.onChanged(widget.value);
},

修改完成后重新运行,点击其他选项时原选中项就会正常触发取消选中的动画效果。


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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.09.28 17:15:03