【问题标题】:Add custom dropdown on stack flutter在 stack flutter 上添加自定义下拉菜单
【发布时间】:2023-01-21 01:04:12
【问题描述】:

我正在尝试添加一个自定义下拉菜单,其项目只是指向其他页面的链接

我尝试使用 DropdownButton

但是我没能把它的元素做成一个链接,它需要一个值,而我没有传递给它的值

请帮忙

【问题讨论】:

    标签: flutter


    【解决方案1】:

    对于这种情况,您可以使用OverlayEntry。下面是一个使用OverlayEntry 的下拉列表的简单工作示例:

    class TestDropdownWidget extends StatefulWidget {
      TestDropdownWidget({Key? key}) : super(key: key);
    
      @override
      _TestDropdownWidgetState createState() => _TestDropdownWidgetState();
    }
    
    class _TestDropdownWidgetState extends State<TestDropdownWidget>
        with TickerProviderStateMixin {
      final LayerLink _layerLink = LayerLink();
      late OverlayEntry _overlayEntry;
      bool _isOpen = false;
    
      //Controller Animation
      late AnimationController _animationController;
      late Animation<double> _expandAnimation;
    
      @override
      void dispose() {
        super.dispose();
        _animationController.dispose();
      }
    
      @override
      void initState() {
        super.initState();
        _animationController = AnimationController(
          vsync: this,
          duration: const Duration(milliseconds: 200),
        );
        _expandAnimation = CurvedAnimation(
          parent: _animationController,
          curve: Curves.easeInOut,
        );
      }
    
      @override
      Widget build(BuildContext context) {
        return CompositedTransformTarget(
          link: _layerLink,
          child: InkWell(
            onTap: _toggleDropdown,
            child: Text('Click Me'), //Define your child here
          ),
        );
      }
    
      OverlayEntry _createOverlayEntry() {
        return OverlayEntry(
          builder: (context) => GestureDetector(
            onTap: () => _toggleDropdown(close: true),
            behavior: HitTestBehavior.translucent,
            // full screen container to register taps anywhere and close drop down
            child: SizedBox(
              height: MediaQuery.of(context).size.height,
              width: MediaQuery.of(context).size.width,
              child: Stack(
                children: [
                  Positioned(
                    left: 100,
                    top: 100.0,
                    width: 250,
                    child: CompositedTransformFollower(
                      //use offset to control where your dropdown appears
                      offset: Offset(0, 20),
                      link: _layerLink,
                      showWhenUnlinked: false,
                      child: Material(
                        elevation: 2,
                        borderRadius: BorderRadius.circular(6),
                        borderOnForeground: true,
                        color: Colors.white,
                        child: Container(
                          decoration: BoxDecoration(
                            borderRadius: BorderRadius.circular(6),
                            border: Border.all(color: Colors.grey),
                          ),
                          child: SizeTransition(
                            axisAlignment: 1,
                            sizeFactor: _expandAnimation,
                            child: Column(
                              mainAxisAlignment: MainAxisAlignment.start,
                              crossAxisAlignment: CrossAxisAlignment.stretch,
                              children: [
                                //These are the options that appear in the dropdown
                                Text('Option 1'),
                                Text('Option 2'),
                                Text('Option 3'),
                                Text('Option 4'),
                                Text('Option 5'),
                              ],
                            ),
                          ),
                        ),
                      ),
                    ),
                  ),
                ],
              ),
            ),
          ),
        );
      }
    
      void _toggleDropdown({
        bool close = false,
      }) async {
        if (_isOpen || close) {
          _animationController.reverse().then((value) {
            _overlayEntry.remove();
            if (mounted) {
              setState(() {
                _isOpen = false;
              });
            }
          });
        } else {
          _overlayEntry = _createOverlayEntry();
          Overlay.of(context)!.insert(_overlayEntry);
          setState(() => _isOpen = true);
          _animationController.forward();
        }
      }
    }
    

    这是显示用户界面的 gif:

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2023-03-04
      • 2021-01-11
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2020-12-05
      • 2020-05-11
      相关资源
      最近更新 更多