javascript - 如何使用 lodash 用 1 个 throttle 来控制多个按钮?

标签 javascript reactjs lodash throttling debouncing

我想避免并发并将操作限制为每秒 1 次。

这是因为 onChange 事件还会触发 1 秒时长的幻灯片放映,触发两次会破坏 UI。

我最初使用 4 个 debounces 函数,但最终得到了这个:

import React from 'react';
import { css } from 'styled-components';
import PropTypes from 'prop-types';
import omit from 'lodash.omit';
import throttle from 'lodash.throttle';
import Img from '@bootstrap-styled/v4/lib/Img';

export default class ServicesAndSolutionImg extends React.PureComponent {
  static propTypes = {
    src: PropTypes.string.isRequired,
    alt: PropTypes.string.isRequired,
    onDigitalSolution: PropTypes.func.isRequired,
    onServices: PropTypes.func.isRequired,
    onHosting: PropTypes.func.isRequired,
    onAddons: PropTypes.func.isRequired,
  };

  state = {
    throttleFn: null,
  }

  componentWillMount() {
    this.setState({
      throttleFn: (e) => throttle(this.props[e.target.value], 1000, { leading: false, trailing: true })(),
    });
  }

  render() {
    const { src, alt } = omit(this.props, [
      'onDigitalSolution',
      'onServices',
      'onHosting',
      'onAddons',
    ]);

    return (
      <div css={css`position: relative`}>
        <Img fluid src={src} alt={alt} className="w-100 pt-3 pl-5 pr-5" />
        <div css={css`
          position: absolute;
          top: 0;
          right: 0;
          left: 0;
          right: 0;
          width: 100%;
          height: 100%;
        `}>
          <div css={css`
            position: relative;
            width: inherit;
            height: inherit;
            button {
              cursor: pointer;
              position: absolute;
              top: 23%;
              height: 51%;
              opacity: 0;
            }
            button:nth-child(1) {
              left: 15%;
              width: 16%;
            }
            button:nth-child(2) {
              left: 32%;
              width: 16%;
            }
            button:nth-child(3) {
              left: 48%;
              width: 16%;
            }
            button:nth-child(4) {
              left: 65%;
              width: 16%;
            }
          `}>
            <button onClick={this.state.throttleFn} value="onDigitalSolution" />
            <button onClick={this.state.throttleFn} value="onServices" />
            <button onClick={this.state.throttleFn} value="onHosting" />
            <button onClick={this.state.throttleFn} value="onAddons" />
          </div>
        </div>
      </div>
    );
  }
}

预计

无延迟,每秒1次点击,无并发

结果

1 秒延迟,最多 4 个并发操作。

有人知道为什么会失败吗?

最佳答案

Throttle是一个接受函数并返回 throttle 函数的函数。 throttle 函数仅在 x 毫秒的窗口中调用一次原始函数。

多次调用 throttle,返回多个你调用的 throttled 函数,并且它们中的每一个都是时间窗口中的唯一调用。

要解决此问题,请将回调中调用 throttle 的结果分配给组件的属性,并在注册点击事件时调用该函数。

export default class ServicesAndSolutionImg extends React.PureComponent {
  static propTypes = {
    src: PropTypes.string.isRequired,
    alt: PropTypes.string.isRequired,
    onDigitalSolution: PropTypes.func.isRequired,
    onServices: PropTypes.func.isRequired,
    onHosting: PropTypes.func.isRequired,
    onAddons: PropTypes.func.isRequired,
  };

  // create the throttled function
  throttleFn = throttle((e) => this.props[e.target.value], 1000, { leading: false, trailing: true })

  render() {
     // no need to omit anything - you know what you want
    const { src, alt } = this.props;

    return (
      <div css={css`position: relative`}>
        <Img fluid src={src} alt={alt} className="w-100 pt-3 pl-5 pr-5" />
        <div css={css`
          position: absolute;
          top: 0;
          right: 0;
          left: 0;
          right: 0;
          width: 100%;
          height: 100%;
        `}>
          <div css={css`
            position: relative;
            width: inherit;
            height: inherit;
            button {
              cursor: pointer;
              position: absolute;
              top: 23%;
              height: 51%;
              opacity: 0;
            }
            button:nth-child(1) {
              left: 15%;
              width: 16%;
            }
            button:nth-child(2) {
              left: 32%;
              width: 16%;
            }
            button:nth-child(3) {
              left: 48%;
              width: 16%;
            }
            button:nth-child(4) {
              left: 65%;
              width: 16%;
            }
          `}>
            <button onClick={this.throttleFn} value="onDigitalSolution" />
            <button onClick={this.throttleFn} value="onServices" />
            <button onClick={this.throttleFn} value="onHosting" />
            <button onClick={this.throttleFn} value="onAddons" />
          </div>
        </div>
      </div>
    );
  }
}

关于javascript - 如何使用 lodash 用 1 个 throttle 来控制多个按钮?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/53895676/

相关文章:

javascript - Selenium Webdriver 不会点击 Chrome 和 Firefox 中的“保存”按钮

javascript - 脚本标签内的 HTML - 无法识别宽度和高度

javascript - 如何将 React.memo 应用于数组中的所有组件?

android - React Native 中的 BackHandler 不工作

javascript - 用于 lodash 助手的 React 组件 Typescript

javascript - 如何在 Polymer 中强制更新模板?

javascript - 在 Angular 中使用 window.location.pathname.split()

javascript - 如何在任何 child 上使用相同的谷歌地图组件实例?

JavaScript 在数组中找到第一个 <= 给定数字的数字

javascript - 需要映射函数来运行另一个函数一次