原始指针事件监听-Pointer、手势识别-GestureDetector

原始指针事件监听-Pointer、手势识别-GestureDetector

原始指针事件监听-Pointer

在Android中,我们的事件可以拆分为三点,down、move、up,然后由这三点来决定是否移动,是否长按,是否双击等等功能,在flutter中也是一样

Listener({
  Key key,
  this.onPointerDown,
  this.onPointerMove,
  this.onPointerEnter,
  this.onPointerExit,
  this.onPointerHover,
  this.onPointerUp,
  this.onPointerCancel,
  this.onPointerSignal,
  this.behavior = HitTestBehavior.deferToChild,
  Widget child,
})

onPointer监听系列的参数

  • Down :手指按下时调用
  • Move: 手指移动时调用
  • Enter:手指进入widget时调用
  • Exit:手指离开widget时调用
  • Hover:没有触发down,但是手指位置改变了—该条目前我无法理解
  • Up:手指抬起的时候调用
  • Cancel:当手指滑出了这个监听范围的时候调用,前提是已经调用了down的时候
  • Signal:当手指刚放上去的时候调用
  • behavior:子widget如何响应点击事件,这里有三个选项HitTestBehavior.deferToChild(默认的)、HitTestBehavior.opaque、HitTestBehavior.translucent
    • HitTestBehavior.deferToChild表示子widget会一个接一个的进行命中测试,这里父widget也会接收到该事件,这个参数会精确到一个widget
    • HitTestBehavior.opaque表示Listener中的child整体都会响应该事件,这个参数不会精确到一个widget,会响应到一片区域
    • HitTestBehavior.translucent表示可视区域或者底层的widget都会被响应到

忽略onPointer:
如果需要忽略某个widget的点击事件我们可以使用IgnorePointer和AbsorbPointer来实现,区别是IgnorePointer本身不参与命中测试,而AbsorbPointer会参与命中测试,但是不会响应事件

手势识别-GestureDetector

上面说的Listener能完成的事情,我们用GestureDetector也可以做到,而且更方便,GestureDetector是Listener的语义化封装,上面我们说的单击,双击长按这些功能,在GestureDetector中能够很方便的使用,但是在Listener中还需要自己计算
单击:onTap
双击:onDoubleTap (用户点击ontap时会有200ms的延迟来判断是否时双击)
长按:onLongPress
拖动(滑动):flutter的拖动效果很好做,如果用Android来做就没这么舒服了

Stack(
  children: [
    Positioned(
      top: _top,
      left: _left,
      child: GestureDetector(
        child: Container(
          child: Text(
            "更多",
            style: TextStyle(color: Colors.white),
          ),
          decoration: BoxDecoration(color: Colors.blue),
          padding: EdgeInsets.all(10.0),
        ),
        onTapDown: (event){
          print("点击下了");
        },
        onPanUpdate: (DragUpdateDetails event){
          print(event.delta.dx);
          setState(() {
            _left+=event.delta.dx;
            _top+=event.delta.dy;
          });
        },
      ),
    )
  ],
)

效果如下:

单一滑动:单一滑动就是指定一个方向去滑动,我们把上面的方法改动一下,换一个回调,onVerticalDragUpdate这个回调限制垂直滑动,当然有限制垂直滑动就会有限制水平滑动

Stack(
  children: [
    Positioned(
      top: _top,
      left: _left,
      child: GestureDetector(
        child: Container(
          child: Text(
            "更多",
            style: TextStyle(color: Colors.white),
          ),
          decoration: BoxDecoration(color: Colors.blue),
          padding: EdgeInsets.all(10.0),
        ),
        onTapDown: (event){
          print("点击下了");
        },
        onVerticalDragUpdate: (DragUpdateDetails event){
          print(event.delta.dy);
          setState(() {
            _left+=event.delta.dx;
            _top+=event.delta.dy;
          });
        },
      ),
    )
  ]

效果如下,你会发现我在setState中去设置了left也没有用,因为我接收到的event.delta.dx就是0.0

缩放:我们如果想要达到widget缩放可以使用onScaleUpdate回调,然后在回调中去重新刷新widget的宽高

Center(
  child: GestureDetector(
    child: Image.asset(
      "./images/lake.jpg",
      width: _widget,
      height: _height,
    ),
    onScaleUpdate: (ScaleUpdateDetails details) {
      setState(() {
        _widget = 200.0 * details.scale.clamp(.5, 10.0);//设置其最小缩放倍数和最大放大倍数
        _height = 300.0 * details.scale.clamp(.5, 10.0);
        print(_widget);
      });
    },
  ),
)

效果如下:

Flutter还给我们提供了很多其他的手势识别器,我们如果有需要可以直接去看GestureDetector的构造

  • GestureRecognizer:记录一下GestureRecognizer的作用,GestureDetector内部就是利用GestureRecognizer来识别各种手势,GestureRecognizer将Listener转化为语义手势,一个GestureRecognizer对应一个手势识别器,所以要记住一点,如果一个widget中有参数可以接收GestureRecognizer,那他就是可以执行手势识别事件;记得GestureRecognizer需要在dispose中dispose掉,释放掉资源

你可能感兴趣的:(Flutter,Flutter)