Подтвердить что ты не робот

Могу ли я запустить Fastclick ReactJS в Кордове

Работает ли fastclick система событий ReactJS? Похоже, что это не происходит при запуске через Кордову на iOS или Android. Если нет, есть ли другой способ получить те же результаты. Мое приложение не имеет функций двойного касания, поэтому я хотел бы удалить эту задержку по всем направлениям, если это возможно...

4b9b3361

Ответ 1

Edit

Facebook решил не добавлять поддержку для определения настраиваемых типов событий и рекомендовать вам использовать что-то вроде react-tappable, чтобы вы могли написать что-то вроде <Tappable onTap={}>.


Facebook работает над решением в виде TapEventPlugin, но не будет доступен пока они не примут некоторые решения.

Если вы читаете это, вы, вероятно, работаете над проектом, который не может дождаться, пока не выяснит, как они хотят его опубликовать.

Это репо для вас: https://github.com/zilverline/react-tap-event-plugin

Когда Facebook решает # 436 и # 1170, это репо исчезнет.забастовкa >

Это решение работает для React 0.14.x и 15.x.

npm i -S react-tap-event-plugin

Пример использования:

var React = require("react");
var ReactDOM = require("react-dom");
injectTapEventPlugin = require("react-tap-event-plugin");
injectTapEventPlugin();

var Main = React.createClass({
  render: function() {
    return (
      <a
        href="#"
        onTouchTap={this.handleTouchTap}
        onClick={this.handleClick}>
        Tap Me
      </a>
    );
  },

  handleClick: function(e) {
    console.log("click", e);
  },

  handleTouchTap: function(e) {
    console.log("touchTap", e);
  }
});

ReactDOM.render(<Main />, document.getElementById("container"));

Обратите внимание, что с инжектором вам, вероятно, придется использовать только onTouchTap (а не onClick).

Ответ 2

Я получил FastClick для работы с React в проекте Webpack. Несколько вещей кажутся сложными, но в основном это работает. ( Обновить: только тумблер, который имитировал клики на скрытом флажке, был фиктивным - это было бы проблемой независимо от React). Вот как я включил его:

npm install -S fastclick

В main.jsx:

import FastClick from 'fastclick';

window.addEventListener('load', () => {
  FastClick.attach(document.body);
});

Итак, даже если вы не используете Webpack или Browserify, я предполагаю, что пока вы можете запустить прослушиватель событий загрузки, все будет в порядке.

Ответ 3

Недавно мы создали компонент React, похожий на fastclick, за исключением того, что он намного проще и требует ручного обратного вызова. Его довольно короткая, так что Ill опубликуйте ее здесь:

React.initializeTouchEvents(true)

var TouchClick = React.createClass({

  defaults: {
    touched: false,
    touchdown: false,
    coords: { x:0, y:0 },
    evObj: {}
  },

  getInitialState: function() {
    return this.defaults
  },

  handler: function() {
    typeof this.props.handler == 'function' && this.props.handler.apply(this, arguments)
  },

  getCoords: function(e) {
    if ( e.touches && e.touches.length ) {
      var touch = e.touches[0]
      return {
        x: touch.pageX,
        y: touch.pageY
      }
    }
  },

  onTouchStart: function(e) {
    this.setState({ 
      touched: true, 
      touchdown: true,
      coords: this.getCoords(e),
      evObj: e
    })
  },

  onTouchMove: function(e) {
    var coords = this.getCoords(e)
    var distance = Math.max( 
      Math.abs(this.state.coords.x - coords.x), 
      Math.abs(this.state.coords.y - coords.y) 
    )
    if ( distance > 6 )
      this.setState({ touchdown: false })
  },

  onTouchEnd: function() {
    if(this.state.touchdown)
      this.handler.call(this, this.state.evObj)
    setTimeout(function() {
      if ( this.isMounted() )
        this.setState(this.defaults)
    }.bind(this), 4)
  },

  onClick: function() {
    if ( this.state.touched )
      return false
    this.setState(this.defaults)
    this.handler.apply(this, arguments)
  },

  render: function() {
    var classNames = ['touchclick']

    this.props.className && classNames.push(this.props.className)
    this.state.touchdown && classNames.push('touchdown')

    return React.DOM[this.props.nodeName || 'button']({
      className: classNames.join(' '),
      onTouchStart: this.onTouchStart,
      onTouchMove: this.onTouchMove,
      onTouchEnd: this.onTouchEnd,
      onClick: this.onClick
    }, this.props.children)
  }
})

Просто передайте handler prop в качестве обратного вызова и оберните содержимое внутри. Это также работает для систем, которые имеют как события касания, так и щелчки (например, более новые ноутбуки с окнами 8). Пример:

 <TouchClick handler={this.clickHandler} className='app'>
   <h1>Hello world</h1>
 </TouchClick>

Ответ 4

У меня были проблемы с использованием метода Дэвида, так как в качестве альтернативы FastClick я реализовал mixin, используя HammerJs для события. Еще немного кода для настройки события, но отлично работает.

var HammerClickMixin = React.createClass({
    componentWillMount: function() {
        this.listeneres = [];

    },
    addTapEvent: function(element,callback) {
        var mc = new Hammer.Manager(element);
        mc.add(new Hammer.Tap({ event: 'doubletap', taps: 2 }));
        mc.add(new Hammer.Tap({ event: 'tap', taps: 1 }));
        mc.on('tap',callback);
        this.listeneres.push(mc);
    },
    addDoubleTap : function(element,callback){
        var mc = new Hammer.Manager(element);
        mc.add(new Hammer.Tap({ event: 'doubletap', taps: 2 }));
        mc.on('doubletap',callback);
        this.listeneres.push(mc);
    },
    componentWillUnmount: function() {
        for(var i= 0; i < this.listeneres.length; i++){
            this.listeneres[i].destroy();
        }
    }
});

Затем это можно использовать следующим образом:

 var Component = React.createClass({
          mixins: [HammerClickMixin],
          componentDidMount: function () {

              this.addTapEvent(this.refs.elementToClick.getDOMNode(),function(){
                  //Handle fast hammer tap!

              });
          },
          render: function () {
               return (
                        <div ref="elementToClick"/>                
                   );
          }
      });

Ответ 5

Казалось, он отлично работает в моем приложении "Кордова", но есть одна серьезная проблема, с которой я столкнулся.

Когда элемент кликается с помощью React + FastClick, а следующее визуализированное представление содержит элемент с кликабелем в той же позиции, событие onTouchEnd также регистрируется во втором элементе.

Я удалил FastClick, поскольку я не хочу выравнивать свои кнопки, чтобы избежать нежелательного поведения, но мне нужно что-то заменить, поскольку задержка нажатия кажется довольно плохим.

Ответ 6

Вы также можете использовать react-fastclick (https://github.com/JakeSidSmith/react-fastclick) из npm:

npm i react-fastclick --save

Используя его, вам не нужно менять какой-либо код, и он отлично работает! Вы должны только потребовать его один раз.

require('react-fastclick');