资讯专栏INFORMATION COLUMN

如何在React中优雅的处理doubleClick

aaron / 1869人阅读

摘要:解决办法解决办法也很简单延迟事件的处理,直到判断这个不在中。原理这个延迟的事件会放在一个队列中,并处于状态。当事件触发之后,就取消所有的这些事件也就不会执行。

背景

上午楼主遇到一个需要处理双击事件的需求,在这里介绍下如何在触发doubleCLick时间的时候, 不触发click事件的解决办法, 顺便分享给大家。

问题阐述

首先, 我们的DOM 是天然支持dbClick 事件的, 线上demo:

https://codepen.io/scaukk/pen...

可以清晰的看到, 双击之后, 触发处理双击事件的逻辑, 但是同时也触发了两次click事件:

这个副作用不是我们预期的, 需要处理一下。

解决办法

解决办法也很简单: 延迟 click事件的处理, 直到判断这个click 不在 doubleClick 中。

原理

这个延迟的click事件会放在一个 Promise 队列中, 并处于pending状态。

当doubleClick事件触发之后, 就取消所有的Pending Promises, 这些事件也就不会执行。

可取消的Promise

要处理这些处于 penging 状态的Promise, 我们需要用到可取消的Promise, 这个话题我在另一片文章中讨论过, 有兴趣的可以看一下。

下面是一个可以cancel的Promise的简单实现:

export const cancellablePromise = promise => {
  let isCanceled = false;

  const wrappedPromise = new Promise((resolve, reject) => {
    promise.then(
      value => (isCanceled ? reject({ isCanceled, value }) : resolve(value)),
      error => reject({ isCanceled, error }),
    );
  });

  return {
    promise: wrappedPromise,
    cancel: () => (isCanceled = true),
  };
};

要解决开头提到的这个问题, 我们就需要用到这个大杀器。

先看下最终的结果,双击一下:

主要代码:

const EnhancedClickableBox = stopTriggerClicksOnDoubleClick(ClickableBox)

const DoubleClickExample = () => (
   console.log("on click")}
    onDoubleClick={() => console.log("on double click")}
  />
);

const App = () => {
  return (
    
  )
}

ReactDOM.render(, document.getElementById("app"));

线上Demo:

https://codepen.io/scaukk/pen...

Hooks 版本
const ClickableBox = ({ onClick, onDoubleClick }) => {
  const [handleClick, handleDoubleClick] = useClickPreventionOnDoubleClick(onClick, onDoubleClick);

  return (
    
  );
};


const DoubleClickExample = () => (
   console.log("on click")} 
    onDoubleClick={() => console.log("on double click")}/>
);



const App = () => {
  return (
   
  )
}

ReactDOM.render(, document.getElementById("app"));

https://codepen.io/scaukk/pen...

是不是很简单, 学到了吧 XD

结语

处理双击事件的时候, 最好还是处理掉不必要的click调用, 免得产生bug.

如果文章对你有帮助, 点个赞支持一下呗。

文中若有错误,欢迎指出, 欢迎留言交流。

文章版权归作者所有,未经允许请勿转载,若此文章存在违规行为,您可以联系管理员删除。

转载请注明本文地址:https://www.ucloud.cn/yun/116247.html

相关文章

  • 如何React优雅处理doubleClick

    摘要:解决办法解决办法也很简单延迟事件的处理,直到判断这个不在中。原理这个延迟的事件会放在一个队列中,并处于状态。当事件触发之后,就取消所有的这些事件也就不会执行。 背景 上午楼主遇到一个需要处理双击事件的需求,在这里介绍下如何在触发doubleCLick时间的时候, 不触发click事件的解决办法, 顺便分享给大家。 问题阐述 首先, 我们的DOM 是天然支持dbClick 事件的, 线上...

    doodlewind 评论0 收藏0
  • [前端][自定义DOM事件]不使用setTimeout实现双击事件或n击事件

    摘要:使用实现双击事件例如,这样双击省略参数合法性的判断自定义双击事件可以使用携带数据双击事件监听双击事件触发是否已经点击过一次事件分发使用数组实现双击事件或击事件灵感来自于系统多击触发彩蛋的源码用前端的方式实现长这样双击省略参数合法性的判断创建 使用setTimeout实现双击事件 例如,这样: let div = document.getElementById(div); doubleC...

    Kerr1Gan 评论0 收藏0
  • [前端][自定义DOM事件]不使用setTimeout实现双击事件或n击事件

    摘要:使用实现双击事件例如,这样双击省略参数合法性的判断自定义双击事件可以使用携带数据双击事件监听双击事件触发是否已经点击过一次事件分发使用数组实现双击事件或击事件灵感来自于系统多击触发彩蛋的源码用前端的方式实现长这样双击省略参数合法性的判断创建 使用setTimeout实现双击事件 例如,这样: let div = document.getElementById(div); doubleC...

    Cobub 评论0 收藏0
  • 如何优雅React处理事件响应

    摘要:处理事件响应是应用中非常重要的一部分。中,处理事件响应的方式有多种。关于事件响应的回调函数,还有一个地方需要注意。不管你在回调函数中有没有显式的声明事件参数,都会把事件作为参数传递给回调函数,且参数的位置总是在其他自定义参数的后面。 React中定义一个组件,可以通过React.createClass或者ES6的class。本文讨论的React组件是基于class定义的组件。采用cla...

    buildupchao 评论0 收藏0
  • [ 一起学React系列 -- 5 ] 如何优雅得使用表单控件

    摘要:假如我们从后台拉取一个数据要填入输入框,那么必须得使用受控组件,因为非受控组件只能被用户输入。不影响正常输入填充该输入框的默认值,此时不显示内容。 网页中使用的form表单大家肯定都再熟悉不过了,它主要作用是用来收集和提交信息。React中的表单组件与我们普通的Html中的表单及其表现形式没有什么不同,所以如何使用表单我觉得再拿出来说可能是画蛇添足、毫无意义。不过再怎么样也不能辜负大家...

    Charlie_Jade 评论0 收藏0

发表评论

0条评论

aaron

|高级讲师

TA的文章

阅读更多
最新活动
阅读需要支付1元查看
<