【问题标题】:Clip Stack children剪辑堆栈儿童
【发布时间】:2021-11-30 11:13:30
【问题描述】:

如何在其大小范围内剪辑 Stack 子级。

在这张图片中,有 3 个网格项using orange color,每个项目使用InkWell 使用悬停方法在堆栈上对齐。虽然hover:false Pop PoP 小部件对 UI 不可见。使用 align 属性它可以工作,但是您可以看到右上 GridItem 的 item:2 pop POp 小部件在 Stack<Griditem> 之外可见,我想让它在堆栈之外不可见。我已经使用clipBehavior: 对每个Clip enums 进行了测试。

我想在 Stack 之外隐藏 Pop POp 小部件,是的,我需要这个弹出效果。

对于 Flutter web,我使用的是 Flutter V2.5.2

存在问题的当前布局

重现问题的完整代码

import 'package:flutter/material.dart';
void main() => runApp(
      const MaterialApp(
        home: Appp(),
      ),
    );

class Appp extends StatelessWidget {
  const Appp({Key? key}) : super(key: key);

  @override
  Widget build(BuildContext context) {
    return const BodyX();
  }
}

class BodyX extends StatelessWidget {
  const BodyX({Key? key}) : super(key: key);

  @override
  Widget build(BuildContext context) {
    return Scaffold(body: LayoutBuilder(
      builder: (context, constraints) {
        return GridView.count(
          crossAxisCount: 2,
          children: [
            ...List.generate(
              3,
              (index) => GridItem(
                key: UniqueKey(),
                maxWidth: constraints.maxWidth / 2,
              ),
            ),
          ],
        );
      },
    ));
  }
}

class GridItem extends StatefulWidget {
  const GridItem({
    Key? key,
    required this.maxWidth,
  }) : super(key: key);
  final double maxWidth;
  @override
  State<GridItem> createState() => _AppXState();
}

class _AppXState extends State<GridItem> {
  bool _isHovered = false;

  @override
  Widget build(BuildContext context) {
    print("ItemWidth : ${widget.maxWidth}");
    return SizedBox(
      //though it wont effect here,
      // just finding the size of Grid because it will 1x1
      width: widget.maxWidth,
      height: widget.maxWidth,
      child: InkWell(
        onTap: () {},
        hoverColor: Colors.black,
        onHover: (value) {
          setState(() {
            _isHovered = value;
          });
        },
        child: Stack(
          clipBehavior: Clip.antiAliasWithSaveLayer,
          children: [
            Container(
              color: Colors.deepOrange.withOpacity(.2),
            ),
            AnimatedAlign(
              alignment: Alignment(0, _isHovered ? .7 : 2),
              child: Container(
                padding: const EdgeInsets.all(22),
                color: Colors.greenAccent,
                child: const Text(
                  "Pop POp",
                ),
              ),
              duration: const Duration(
                milliseconds: 200,
              ),
            )
          ],
        ),
      ),
    );
  }
}

【问题讨论】:

    标签: flutter flutter-layout flutter-web


    【解决方案1】:

    如果您不希望 Widget 绘制超出其布局大小,可以使用 ClipRect 对其进行剪辑。

    在您的情况下,您可以将 ClipRect 包装在您的 Stack 上,如下所示:

    ClipRect(
      child: Stack(
        children: ...
      ),
    )
    

    此外,您可以使用ClipRRect 剪裁圆角矩形(圆形边框)或使用ClipPath 剪裁自定义形状,例如三角形。您可以在官方文档中阅读有关这些小部件的更多信息。

    【讨论】:

    • 谢谢,它解决了问题,但我以为我们有 overflow,现在已弃用,建议使用 clipBehavior,但无法使用它存档。
    • 是的,overflow 属性已被弃用,如果您希望堆栈超出其大小,您可以使用clipBehavior: Clip.none。使用ClipRect 小部件是剪裁任何子小部件的更通用的解决方案。
    • clipBehavior: Clip.none 不起作用,但任何像 ClipRect.... 这样的 Clip 小部件都能解决我的问题。
    猜你喜欢
    • 1970-01-01
    • 2017-10-24
    • 2011-07-22
    • 1970-01-01
    • 1970-01-01
    • 2013-01-27
    • 2015-12-28
    • 1970-01-01
    相关资源
    最近更新 更多