简体   繁体   English

在可扩展浮动操作按钮中,在颤动中未检测到子小部件中的手势

[英]In Expandable Floating action button the gestures in the child widget is not detected in flutter

Trying to implement a floating action button that extends in two dimension and then show some more option of floating action button.尝试实现一个在二维中扩展的浮动操作按钮,然后显示更多的浮动操作按钮选项。 Somehow able to animated the child widget of the floating action button to their correct position, using the Transform Widget, but when I try to press on the child widget, ie the widgets that come out on pressing the floating action button, they do not respond to the onPressed handler.以某种方式能够使用转换小部件将浮动操作按钮的子小部件动画到其正确位置,但是当我尝试按下子小部件时,即按下浮动操作按钮时出现的小部件,它们没有响应到 onPressed 处理程序。 Tried many different thing like IgnorePointer, stacked rows and Columns, AnimatedBuilder,etc.尝试了很多不同的东西,比如 IgnorePointer、堆积的行和列、AnimatedBuilder 等。 but was unable to find the correct solution.但无法找到正确的解决方案。 It was like sometimes used to get the UI correct then the gesture was not detected and if the gesture were detected the UI got distorted.就像有时用于使 UI 正确,然后未检测到手势,如果检测到手势,则 UI 会失真。 And I am somewhat new to flutter.我对颤振有点陌生。 Any help in sorting out this issue would be appreciated.对解决此问题的任何帮助将不胜感激。

Here is my Code:这是我的代码:

main.dart main.dart

import "package:flutter/material.dart";
import 'myhome.dart';

void main() => runApp(MyApp());

class MyApp extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return MaterialApp(
      theme: ThemeData(
        primaryColor: Colors.blue,
      ),
      title: "Custom Expandable FAB",
      home: MyHome(),
    );
  }
}

myhome.dart我的家.dart

import 'package:flutter/material.dart';
import 'package:tester_project/customFAB.dart';

class MyHome extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return Scaffold(
      extendBody: true,
      backgroundColor: Colors.white,
      floatingActionButton: CustomFab(),
      floatingActionButtonLocation: FloatingActionButtonLocation.centerDocked,
      bottomNavigationBar: BottomAppBar(
        color: Colors.blue,
        shape: CircularNotchedRectangle(),
        child: Container(
          height: 55,
          child: Row(
            mainAxisAlignment: MainAxisAlignment.spaceBetween,
            children: [
              IconButton(
                icon: Icon(Icons.search),
                onPressed: () {},
              ),
              IconButton(
                icon: Icon(Icons.menu),
                onPressed: () {},
              ),
            ],
          ),
        ),
      ),
      appBar: AppBar(
        title: Text("Custom FAB"),
      ),
      body: Container(
        alignment: Alignment.center,
        child: Text("Click on Fab to expand"),
        color: Colors.white,
      ),
    );
  }
}

CustomFab.dart CustomFab.dart

import 'package:flutter/material.dart';
import 'package:permission_handler/permission_handler.dart';

class CustomFab extends StatefulWidget {
  @override
  _CustomFabState createState() => _CustomFabState();
}

class _CustomFabState extends State<CustomFab>
    with SingleTickerProviderStateMixin {
  AnimationController _animationController;
  Animation<double> _translateAnimation;
  Animation<double> _rotationAnimation;

  Animation<double> _iconRotation;

  bool _isExpanded = false;

  void animate() {
    if (!_isExpanded) {
      _animationController.forward();
    } else {
      _animationController.reverse();
    }

    _isExpanded = !_isExpanded;
  }

  Widget fab1() {
    return Container(
      height: 60,
      width: 60,
      child: FittedBox(
        child: FloatingActionButton(
          heroTag: "btn3",
          backgroundColor: Color(0xffFFC852),
          elevation: 0,
          onPressed: () {
            print("pressed");
          },
        ),
      ),
    );
  }

  Widget fab2() {
    return Container(
      height: 60,
      width: 60,
      child: FittedBox(
        child: FloatingActionButton(
          heroTag: "btn4",
          child: Transform.rotate(
            angle: _iconRotation.value,
            child: Icon(Icons.home),
          ),
          elevation: _isExpanded ? 5 : 0,
          backgroundColor: Color(0xffE5E4F4),
          onPressed: () {
            print("Pressed");
          },
        ),
      ),
    );
  }

  Widget fab3() {
    return Container(
      height: 60,
      width: 60,
      child: FittedBox(
        child: FloatingActionButton(
          heroTag: "btn5",
          child: Transform.rotate(
            angle: _rotationAnimation.value,
            child: Icon(Icons.add),
          ),
          backgroundColor: Color(0xffFFC852),
          onPressed: () async {
            await Permission.contacts.request();
            if (await Permission.contacts.status.isGranted) {
              animate();
            }
          },
        ),
      ),
    );
  }

  @override
  void initState() {
    _animationController =
        AnimationController(vsync: this, duration: Duration(milliseconds: 400))
          ..addListener(() {
            setState(() {});
          });
    _translateAnimation = Tween<double>(begin: 0, end: 80)
        .chain(
          CurveTween(
            curve: _isExpanded ? Curves.fastOutSlowIn : Curves.bounceOut,
          ),
        )
        .animate(_animationController);

    _iconRotation = Tween<double>(begin: 3.14 / 2, end: 0)
        .chain(
          CurveTween(curve: Curves.bounceInOut),
        )
        .animate(_animationController);
    _rotationAnimation = Tween<double>(begin: 0, end: 3 * 3.14 / 4)
        .chain(
          CurveTween(
            curve: Curves.bounceInOut,
          ),
        )
        .animate(_animationController);
    super.initState();
  }

  @override
  void dispose() {
    _animationController.dispose();
    super.dispose();
  }

  @override
  Widget build(BuildContext context) {
    return Stack(
      clipBehavior: Clip.none,
      children: [
        Transform(
          transform:
              Matrix4.translationValues(0, -_translateAnimation.value, 0),
          child: fab1(),
        ),
        Transform(
          transform:
              Matrix4.translationValues(-_translateAnimation.value, 0, 0),
          child: fab2(),
        ),
        fab3(),
      ],
    );
  }
}

Floating action button before and after expansion展开前后浮动动作按钮

Look at this.看这个。https://api.flutter.dev/flutter/widgets/Transform-class.htmlhttps://api.flutter.dev/flutter/widgets/Transform-class.html

Unlike RotatedBox, which applies a rotation prior to layout, this object applies its transformation just prior to painting, which means the transformation is not taken into account when calculating how much space this widget's child (and thus this widget) consumes.与在布局之前应用旋转的 RotatedBox 不同,此对象在绘制之前应用其变换,这意味着在计算此小部件的子级(以及此小部件)消耗的空间量时不考虑变换。

So, your fab1(),fab2(),fab3() have the same position.所以,你的fab1(),fab2(),fab3()有相同的位置。 Although you animate them, it just move at painting , their real position wont change.尽管您为它们设置动画,但它只是在painting移动,它们的实际位置不会改变。 Just give a color to your fabs, you will know what I mean.只要给你的晶圆厂一种颜色,你就会明白我的意思。

        Container(
          color:Colors.green,
          child: Transform(
            transform:
                Matrix4.translationValues(-_translateAnimation!.value, 0, 0),
            child: fab2(),
          ),
        ),

Now you know why, and you need to know how.现在你知道为什么了,你需要知道怎么做。 So I hope you can look at this.所以我希望你能看看这个。 https://api.flutter.dev/flutter/animation/animation-library.html https://api.flutter.dev/flutter/animation/animation-library.html
You can use Stack&&Positioned ,and with Tween , caculate each button's position, or other way.您可以使用Stack&&PositionedTween ,计算每个按钮的位置,或其他方式。 I will leave you to explore.我会让你去探索。

Here's some code of CustomFab.dart这是 CustomFab.dart 的一些代码


  @override
  Widget build(BuildContext context) {
    return Container(
      // color: Colors.green, // Give this area a background color, then you know why.
      height: 150,// You need to give your "action area" a bigger size.
      width: 150,// make these bigger have a problem, your bar will have a bigger circle.
                // if you need this effect, you need to change all your fabs "Stack on the appbar"
                // or just remove `shape: CircularNotchedRectangle(),` in myhome.dart
      child: Stack(
        clipBehavior: Clip.none,
        children: [
          Positioned(// These numbers just for example, you can make your own size or position.
            left: 150 / 2 - 30,
            bottom: _translateAnimation.value + 40,
            child: fab1(),
          ),
          Positioned(
            left: 150 / 2 - 30 -_translateAnimation.value,
            bottom: 40,
            child: fab2(),
          ),
          Positioned(
            left: 150 / 2 - 30,
            bottom: 40,
            child: fab3(),
          ),
        ],
      ),
    );
  }

Try Speed Dial using this package https://pub.dev/packages/flutter_speed_dial使用此软件包尝试快速拨号https://pub.dev/packages/flutter_speed_dial

    SpeedDial(
    marginBottom: 25,
    marginEnd: 25,
    backgroundColor: Colors.blue,
    activeBackgroundColor: Colors.white,
    activeForegroundColor: Colors.blue,
    animatedIcon: AnimatedIcons.menu_close,
    children: [
      SpeedDialChild(
          child: Icon(
            Icons.filter_alt,
          ),
          label: 'ABC',
          onTap: () {
            
          }),
      SpeedDialChild(
          labelBackgroundColor: Colors.white,
          backgroundColor: Colors.blue,
          foregroundColor: Colors.white,
          child: Icon(Icons.add),
          label: 'ABC',
          onTap: () {
            
          }),
    ],
  ),

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM