文章详情

短信预约-IT技能 免费直播动态提醒

请输入下面的图形验证码

提交验证

短信预约提醒成功

Flutter runApp GestureBinding如何使用

2023-07-04 19:00

关注

这篇文章主要介绍“Flutter runApp GestureBinding如何使用”,在日常操作中,相信很多人在Flutter runApp GestureBinding如何使用问题上存在疑惑,小编查阅了各式资料,整理出简单好用的操作方法,希望对大家解答”Flutter runApp GestureBinding如何使用”的疑惑有所帮助!接下来,请跟着小编一起来学习吧!

GestureBinding介绍

想去了解一个类最好的方法无外乎去阅读它的注释,我们可以从它的注释中去了解它是为了做什么,做了些什么, 能够做什么.

原文汉译
A binding for the gesture subsystem.

## Lifecycle of pointer events and the gesture arena

### [PointerDownEvent]

When a [PointerDownEvent] is received by the [GestureBinding] (from [dart:ui.PlatformDispatcher.onPointerDataPacket], as interpreted by the [PointerEventConverter]), a [hitTest] is performed to determine which [HitTestTarget] nodes are affected. (Other bindings are expected to implement [hitTest] to defer to [HitTestable] objects. For example, the rendering layer defers to the [RenderView] and the rest of the render object hierarchy.)

The affected nodes then are given the event to handle ([dispatchEvent] calls [HitTestTarget.handleEvent] for each affected node). If any have relevant [GestureRecognizer]s, they provide the event to them using [GestureRecognizer.addPointer]. This typically causes the recognizer to register with the [PointerRouter] to receive notifications regarding the pointer in question.

Once the hit test and dispatching logic is complete, the event is then passed to the aforementioned [PointerRouter], which passes it to any objects that have registered interest in that event.

Finally, the [gestureArena] is closed for the given pointer ([GestureArenaManager.close]), which begins the process of selecting a gesture to win that pointer.

### Other events

A pointer that is [PointerEvent.down] may send further events, such as [PointerMoveEvent], [PointerUpEvent], or [PointerCancelEvent]. These are sent to the same [HitTestTarget] nodes as were found when the [PointerDownEvent] was received (even if they have since been disposed; it is the responsibility of those objects to be aware of that possibility).

Then, the events are routed to any still-registered entrants in the [PointerRouter]'s table for that pointer.

When a [PointerUpEvent] is received, the [GestureArenaManager.sweep] method is invoked to force the gesture arena logic to terminate if necessary.
手势子系统的绑定。

## 指针事件和手势竞技场的生命周期

### [PointerDownEvent]

当 [GestureBinding] 接收到 [PointerDownEvent](来自[dart:ui.PlatformDispatcher.onPointerDataPacket],由[PointerEventConverter]), 执行[hitTest]以确定哪个[HitTestTarget] 节点受到影响。 (其他Bindings预计实现 [hitTest] 以推迟到 [HitTestable] 对象。例如,渲染层遵从 [RenderView] 和渲染对象的其余部分。)

然后给受影响的节点处理事件([dispatchEvent] 调用每个受影响节点的 [HitTestTarget.handleEvent])。如有相关[GestureRecognizer]s,他们使用[GestureRecognizer.addPointer]。这通常会导致识别器向 [PointerRouter] 注册以接收有关有问题的指针。

一旦命中测试和调度逻辑完成,事件就会发生传递给前面提到的 [PointerRouter],它将它传递给任何对象已经注册了对该事件的兴趣。

最后,[gestureArena] 为给定的指针关闭([GestureArenaManager.close]),它开始选择一个赢得该指针的手势。

### 其他事件

[PointerEvent.down] 的指针可能会发送更多事件,例如[PointerMoveEvent]、[PointerUpEvent] 或 [PointerCancelEvent]。这些是发送到相同的 [HitTestTarget] 节点
[PointerDownEvent] 已收到(即使它们已被处置;它是这些对象有责任意识到这种可能性)。

然后,事件被路由到[PointerRouter] 的指针表。

当接收到 [PointerUpEvent] 时,[GestureArenaManager.sweep] 方法被调用以强制手势竞技场逻辑在必要时终止。

methods

了解完GestureBinding大致是做什么的, 我们再了解一下它有哪些方法.

Flutter runApp GestureBinding如何使用

其中initInstances()不知道大家有没有印象, 在BindingBase的构造方法中有调用这个方法, 那自然在初始的时候会调用这个方法.

{    // 保存实例    _instance = this;    // 平台分发, 这里接受native传来的手势信息作分发    platformDispatcher.onPointerDataPacket = _handlePointerDataPacket;}

实际上也就是在开始的时候注册了手势的接收分发.那么手势是如何分发的呢?我们不如看一下_handlePointerDataPacket 的具体实现:

{    // 这里会将指针数据转换为逻辑像素,同时保存    _pendingPointerEvents.addAll(PointerEventConverter.expand(packet.data,    window.devicePixelRatio));    // 首先,我们要了解下locked是从什么地方来的,    // 可以看到它最终的改变地只有*lockEvents()*方法中,而*lockEvents()*方法    // 由*reassembleApplication()*或scheduleWarmUpFrame()调用,    // 前者属于例如热重载之类时调用, 而后者我们在runApp时也有过介绍.    // 这里看起来更像是一个异步回调的锁.也就是在重启界面的时候不用去刷新指针队列    if (!locked) _flushPointerEventQueue();}

这里又引出来一个_flushPointerEventQueue()的概念,这里会真正的去分发手势事件:

{    // 只有我们接收到了手势队列中还有对象就会持续运行    while (_pendingPointerEvents.isNotEmpty){        // 这里删除了第一个元素并返回第一个元素,也就是队列的fifo.        // 我们会依次处理接受到的手势事件        handlePointerEvent(_pendingPointerEvents.removeFirst());       }}

那么,*handlePointerEvent()*做了什么呢?

// 断言之类代码已经去掉{    // 如果这个开关打开,我们可以获取更平滑到手势事件,    // 比如90hz、120hz的屏幕. 我们在一些界面处理上就可以打开这个开关,    // 同样这个值也是可以动态开关的    if (resamplingEnabled) {        // 重采样这里不过多介绍,有兴趣可以自行探索一下哦!        _resampler.addOrDispatch(event);        _resampler.sample(samplingOffset, _samplingClock);        return;    }    _resampler.stop();    // 这里去处理指针事件,从名字上来看是非常迫切了,hhh    _handlePointerEventImmediately(event);}
// 这里会对每一个指针事件进行判断,是否点中widget或者说命中了哪个widget{    HitTestResult? hitTestResult;    if (event is PointerDownEvent || event is PointerSignalEvent || event is PointerHoverEvent) {      hitTestResult = HitTestResult();      hitTest(hitTestResult, event.position);      if (event is PointerDownEvent) {        _hitTests[event.pointer] = hitTestResult;      }    } else if (event is PointerUpEvent || event is PointerCancelEvent) {      hitTestResult = _hitTests.remove(event.pointer);    } else if (event.down) {      hitTestResult = _hitTests[event.pointer];    }    if (hitTestResult != null ||        event is PointerAddedEvent ||        event is PointerRemovedEvent) {      dispatchEvent(event, hitTestResult);    }}

这里的代码比较简单, 如果事件是down、signal或者hover之中的任何事件,则会通过hitTest()添加到HitTestResult中,假如是down事件还需要增加到_hitTests结果中.如果是up或者cancel事件,那说明用户取消了当时到滑动事件,我们自然而然需要去除相应的事件.最后去分发手势.

  void dispatchEvent(PointerEvent event, HitTestResult? hitTestResult) {    if (hitTestResult == null) {      try {        // 分发指针时, 会把所有通过条件的event都注册到手势路由里面        pointerRouter.route(event);      } catch (exception, stack) {        ...      }      return;    }    for (final HitTestEntry entry in hitTestResult.path) {      try {        // 这里回调一下结果判断有没有命中        entry.target.handleEvent(event.transformed(entry.transform), entry);      } catch (exception, stack) {        ...      }    }  }

到此,关于“Flutter runApp GestureBinding如何使用”的学习就结束了,希望能够解决大家的疑惑。理论与实践的搭配能更好的帮助大家学习,快去试试吧!若想继续学习更多相关知识,请继续关注编程网网站,小编会继续努力为大家带来更多实用的文章!

阅读原文内容投诉

免责声明:

① 本站未注明“稿件来源”的信息均来自网络整理。其文字、图片和音视频稿件的所属权归原作者所有。本站收集整理出于非商业性的教育和科研之目的,并不意味着本站赞同其观点或证实其内容的真实性。仅作为临时的测试数据,供内部测试之用。本站并未授权任何人以任何方式主动获取本站任何信息。

② 本站未注明“稿件来源”的临时测试数据将在测试完成后最终做删除处理。有问题或投稿请发送至: 邮箱/279061341@qq.com QQ/279061341

软考中级精品资料免费领

  • 历年真题答案解析
  • 备考技巧名师总结
  • 高频考点精准押题
  • 2024年上半年信息系统项目管理师第二批次真题及答案解析(完整版)

    难度     813人已做
    查看
  • 【考后总结】2024年5月26日信息系统项目管理师第2批次考情分析

    难度     354人已做
    查看
  • 【考后总结】2024年5月25日信息系统项目管理师第1批次考情分析

    难度     318人已做
    查看
  • 2024年上半年软考高项第一、二批次真题考点汇总(完整版)

    难度     435人已做
    查看
  • 2024年上半年系统架构设计师考试综合知识真题

    难度     224人已做
    查看

相关文章

发现更多好内容

猜你喜欢

AI推送时光机
位置:首页-资讯-后端开发
咦!没有更多了?去看看其它编程学习网 内容吧
首页课程
资料下载
问答资讯