当前位置: 首页 > article >正文

鸿蒙交互事件开发07——手势竞争问题

 如果你也对鸿蒙开发感兴趣,加入“Harmony自习室”吧!扫描下方名片,关注公众号,公众号更新更快,同时也有更多学习资料和技术讨论群。

1、背景

在文章鸿蒙交互事件开发05——常用的6种手势类型中,有朋友留言,问“可不可以就文中提到的手势竞争,举例子讲一讲?”。

⭐️ 文中提到的手势竞争是什么呢?

是在讨论PanGesture拖动手势时,章节末尾有个tips,内容如下:

大部分可滑动组件,如List、Grid、Scroll、Tab等组件是通过PanGesture实现滑动,在组件内部的子组件绑定拖动手势(PanGesture)或者滑动手势(SwipeGesture)会导致手势竞争。

当在子组件绑定PanGesture时,在子组件区域进行滑动仅触发子组件的PanGesture。如果需要父组件响应,需要通过修改手势绑定方法或者子组件向父组件传递消息进行实现,或者通过修改父子组件的PanGesture参数distance使得拖动更灵敏。当子组件绑定SwipeGesture时,由于PanGesture和SwipeGesture触发条件不同,需要修改PanGesture和SwipeGesture的参数以达到所需效果。

这里主要想说明的是:鸿蒙原生组件中的内置滑动组件(List、Scroll等)的滑动是基于拖动手势或者滑动手势来实现,如果我们在这些系统组件中也用了类似的手势作为子组件,那么可能会导致父组件的功能异常。

实际业务场景非常复杂,我这边举一个简单的例子来抛砖引玉。

2、场景举例

有一个List列表,其中List列表的列表项是一个容器,其中这些容器中的内容是可以被拖动的。示意图如下:

图片

这里面我们可以看到有问题出现了。

  1.  List列表可以上下滑动;

  2. list列表项中的子元素也可以被拖动(包括上下拖动);

不出意外,我们在实现子元素拖动时,会使用到PanGesture拖动手势,此时,PanGesture手势将会和List容器的上下滑动冲突。

怎么解决这个问题呢?

跟随前文的tips思路,我们可以考虑在"灵敏度"上面做区分。

例如:

👉🏻 当我们在子项中点击某个按钮时,将子元素的distance设置大一些将事件让给父容器(List)

👉🏻 当我们再点击某个按钮时,将子元素的distance设置小一些,让子元素的事件触发更容易,从而起到子元素响应该手势。

按照上面的方式,我们就可以动态控制手势事件的消费目标了。

3、Demo

实现一个效果:

List列表中显示一系列列表项,每个列表项中包含一个按钮,通过这个按钮可以切换列表项的PanGesture的distance,从而让子容器的PanGesture灵敏度发生变化,达到切换滑动效果的目的。

演示如下:

图片

代码如下:

import util from '@ohos.util';@Entry@Componentstruct Demo {  gestureDistance: number = 20;  @State data: Array<string> = this.getData(20);  private getData(distance: number): Array<string> {    const arr = [];    for (let index = 0; index < 50; index++) {      arr.push(`内部可以处理拖动的容器 ${index}\n\n\ndistance ${distance}`);    }    return arr;  }  build() {    List() {      ForEach(this.data, (item: string, idx: number) => {        ListItem() {          Row() {            Row() {              Text(item)              Blank()              Button('切换distance')                .onClick(() => {                  this.gestureDistance = this.gestureDistance === 20 ? 4 : 20;                  console.log('切换 distance ', this.gestureDistance);                  this.data = this.getData(this.gestureDistance);                })            }            .padding(5)            .width('100%')            .height(150)            .stateStyles({              pressed: {                .backgroundColor(Color.Brown)                .borderRadius(30)                .animation({duration: 500, curve: Curve.Ease})              },              normal: {                .backgroundColor(Color.Pink)                .borderRadius(10)                .animation({duration: 500, curve: Curve.Ease})              }            })          }          .width('100%')          .padding(5)          .gesture(            PanGesture({              direction: PanDirection.Vertical,              distance: this.gestureDistance,            }).onActionStart((event: GestureEvent) => {              console.log('action start')            })          )        }      })    }    .width('100%')  }}

🥚彩蛋🥚:请注意demo中按压和释放的动画效果。


http://www.kler.cn/news/305815.html

相关文章:

  • 速通GPT:《Improving Language Understanding by Generative Pre-Training》全文解读
  • 前端开发的观察者模式
  • K8s 之Pod的定义及详细资源调用案例
  • NAT技术
  • 人工智能辅助汽车造型设计
  • 健身管理|基于java的健身管理系统小程序(源码+数据库+文档)
  • 数据结构与算法图论 并查集
  • 【Linux】调试和Git及进度条实现
  • 弹框调取阿里云播放器一直报错 TypeError: 没有为播放器指定容器
  • 注意!Facebook已移除细分定位排除受众的功能
  • 基于微信小程序的宠物之家的设计与实现
  • 备战软考Day02-数据结构与算法
  • 深度学习| 快速上手深度学习代码的阅读和改写
  • 6.1 溪降技术:绳结
  • 小阿轩yx-Zabbix企业级分布式监控环境部署
  • 期望极大算法(Expectation Maximization Algorithm,EM)
  • 基于SpringBoot的校园新闻网站设计与实现
  • 视觉SLAM ch5——相机与图像
  • AIGC-初体验
  • python 大模型验证码识别
  • C++11的部分新特性
  • Vue路由:Vue router
  • 使用ESP8266和OLED屏幕实现一个小型电脑性能监控
  • 优化深度学习模型训练过程:提升PASCAL VOC 2012数据集上Deeplabv3+模型训练效率的策略
  • 【leetcode-python】最接近的三数之和
  • Acrobat 9 安装教程
  • Redis入门2
  • 驾校预约学习系统的设计与实现
  • 关于决策树的一些介绍
  • 让孩子们动手又动脑,用学优马电子积木,探索电路的奥秘