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

移除Flutter中ReorderableListView拖拽时的矩形阴影

Flutter ReorderableListView拖拽时圆角元素出现矩形阴影问题解决

我在TODO应用中使用ReorderableListView实现了可拖拽排序的ListaItem元素,该元素本身带有圆角边框,但拖拽时会出现难看的矩形阴影,目标是移除这个阴影。

正常显示效果

正常显示的ListaItem
选中状态的ListaItem

ListaItem代码

@override
Widget build(BuildContext context) {
  return Container(
    margin: EdgeInsets.only(left:10.0, right: 10.0, top: 7,bottom: 7),
    decoration: BoxDecoration(
      boxShadow: [BoxShadow(
          color: Color.fromRGBO(50, 50, 50, 0.21),
          offset: Offset(2, 2),
          blurRadius: 10.0
        )],
        borderRadius: BorderRadius.all(Radius.circular(100.0))
    ),
    child: ElevatedButton(
      onPressed: () {
        setState(() {
          widget.checkValue = !widget.checkValue;
        });
      }, 
      style: ElevatedButton.styleFrom(
        primary: Colors.white,
        onPrimary: Color.fromARGB(0, 59, 59, 59),
        shape: StadiumBorder(),             
      ),
      child: AnimatedContainer(
        duration: Duration(milliseconds: 100),
        height: 55,
        padding: EdgeInsets.only(left: 10, right: 2),
        child: Row(
          crossAxisAlignment: CrossAxisAlignment.center,
          mainAxisAlignment: MainAxisAlignment.spaceBetween,
          children: [
            Text(
              widget.product,
              style: TextStyle(
                color: widget.checkValue ? Color.fromARGB(120, 37, 37, 37) : Color.fromARGB(200, 37, 37, 37),
                fontSize: 20,
                fontWeight: FontWeight.w300,
                decoration: widget.checkValue ? TextDecoration.lineThrough : TextDecoration.none
                ),
              ),
            newCheck(value: widget.checkValue)//自定义样式复选框
          ],
        ),
      )
    ),
  );
}

拖拽时的问题效果

拖拽时的阴影效果

ReorderableListView代码

@override
Widget build(BuildContext context) {
  var Items = new List<Item>.generate(10, (i) => Item(i, i.toString()));
  return Scaffold(
    appBar: AppBar(
      title: Text(widget.title),
    ),
    body: Center(
      child: Container(
        color: Colors.transparent,
        child: Expanded(
          child: ReorderableListView(
          padding: EdgeInsets.only(top:20),
          onReorder: ((oldIndex, newIndex) {
            
          }),
          children: [
            for(int i = 0; i < Items.length; i++)
              ListaItem(checkValue: Items[i].state, product: Items[i].title,key: Key(i.toString()),)
          ],
        )
      )
    ),
  ),
  // 尾部逗号使build方法自动格式化更美观
  );
}

解决方案

问题根源是ReorderableListView在拖拽时会默认给选中元素添加一个未适配圆角的矩形阴影,可通过以下两种方式解决:

方法一:自定义拖拽代理样式(推荐)

在ReorderableListView中添加proxyDecorator参数,自定义拖拽时的元素外观,覆盖默认阴影:

ReorderableListView(
  padding: EdgeInsets.only(top:20),
  onReorder: ((oldIndex, newIndex) {
    // 实现你的排序逻辑
  }),
  // 自定义拖拽代理样式
  proxyDecorator: (Widget child, int index, Animation<double> animation) {
    return Material(
      color: Colors.transparent,
      child: child,
    );
  },
  children: [
    for(int i = 0; i < Items.length; i++)
      ListaItem(checkValue: Items[i].state, product: Items[i].title,key: Key(i.toString()),)
  ],
)

proxyDecorator允许你完全控制拖拽时显示的元素,这里用透明背景的Material包裹原元素,直接消除默认的矩形阴影。

方法二:裁剪阴影适配圆角

通过ClipRRect包裹ListaItem的Container,确保阴影跟随圆角裁剪:

@override
Widget build(BuildContext context) {
  return ClipRRect(
    borderRadius: BorderRadius.all(Radius.circular(100.0)),
    child: Container(
      margin: EdgeInsets.only(left:10.0, right: 10.0, top: 7,bottom: 7),
      decoration: BoxDecoration(
        boxShadow: [BoxShadow(
            color: Color.fromRGBO(50, 50, 50, 0.21),
            offset: Offset(2, 2),
            blurRadius: 10.0
          )],
          borderRadius: BorderRadius.all(Radius.circular(100.0))
      ),
      child: ElevatedButton(
        // 原按钮代码不变
      ),
    ),
  );
}

这种方式会裁剪Container的阴影,使其贴合圆角,但不如第一种方法直接解决拖拽时的默认阴影问题。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.26 00:09:24