如何从React Native可触摸事件currentTarget中读取道具?

时间:2017-02-08 21:03:00

标签: react-native

当用户点击图像时,我有以下React Native代码运行press()方法。我想从事件对象中获取itemIndex prop。我在press方法中设置了一个断点,并在Watch中添加了一些表达式。从Watch中我确定事件的目标(事件发起)是正确的图像。 itemIndex prop也可用。正在处理的元素是currentTarget,Watch看到它是" RCTView"我期待一个TouchableOpacity,所以也许在TouchableOpacity下面是一个视图? currentTarget itemIndex prop是未定义的,为什么?如何从currentTarget获取道具?

我想这样做是为了避免为每个渲染项创建添加方法。

FYI, ref={(c) => this._input = c}无效,因为它是在循环中运行的。 onPress={(e) => this.press(e, i)}创建了一个我试图避免使用的新功能。

观看

  1. target._currentElement.props.itemIndex:2
  2. target._currentElement.type.displayName:" RCTImageView"
  3. currentTarget._currentElement.props.itemIndex:undefined
  4. currentTarget._currentElement.type.displayName:" RCTView"

    press: function(event){
        var currentTarget = ReactNativeComponentTree.getInstanceFromNode(event.currentTarget);
        var target = ReactNativeComponentTree.getInstanceFromNode(event.target);
        var currentTargetIndex = currentTarget._currentElement.props.itemIndex;
        var targetIndex = target._currentElement.props.itemIndex;
        var url = this.state.data.items[currentTargetIndex].url;
        Linking.openURL(url).catch(err => console.error('An error occurred', err));
    },
    
    render: function() {
    return (
        <ScrollView horizontal={true} showsHorizontalScrollIndicator={false} style={styles.galleryView}>
            {
                this.state.data.items.map((data, i) =>
                    <TouchableOpacity itemIndex={i} key={i} activeOpacity={0.5} onPress={this.press} >
                        <Image itemIndex={i} key={i} source={{uri:data.previewImageUri}} style={styles.galleryImage} />
                    </TouchableOpacity>
                )
            }
        </ScrollView>
    );
    }
    

3 个答案:

答案 0 :(得分:2)

我最近遇到过同样的问题,我发现了两种不同的方法。更简单的方法是改变你的onPress以将索引传递给你的按键功能,这是第二种方式:

press: function(event, index){
  var url = this.state.data.items[index].url;
  Linking.openURL(url).catch(err => console.error('An error occurred', err));
},

render: function() {
  return (
    <ScrollView
      horizontal={true}
      showsHorizontalScrollIndicator={false}
      style={styles.galleryView}
    >
    {
      this.state.data.items.map((data, i) =>
        <Images data={data} key={i} index={i} press={this.press} />
      )
    }
    </ScrollView>
    );
}

const Images = (props) => {
  const imageClicked = (e) => {
    props.press(e, props.index);
  }
  return (
    <TouchableOpacity activeOpacity={0.5} onPress={imageClicked} >
      <Image source={{uri:props.data.previewImageUri}} style={styles.galleryImage} />
    </TouchableOpacity>
  )
}

答案 1 :(得分:0)

将所需信息绑定到回调并为每个子项分配一个回避可以避免在每个子渲染上重新创建回调。

class Hello extends React.Component{
  state = { names: this.props.names.map((name, i) => {
      return Object.assign({
        onClick: this._onClick.bind(this, i, this.props),
      }, name)
    }),
  };

  _onClick(ind, _props, e) {
    alert('props:' + JSON.stringify(_props));
  }

  render() {
    const { names } = this.state;
    return (
      <div>
        { names.map((name, i) => (
            <div key={i}>Name: <input value={ name.first } onClick={ name.onClick } /></div>
          ))}
      </div>
  )}
}

ReactDOM.render(
  <Hello names={[{first:'aaa'},{first:'bbb'},{first:'ccc'}]}/>,
  document.getElementById('container')
);

JS Fiddle

答案 2 :(得分:0)

您可以将事件处理程序设为接受额外参数的咖喱函数。

 //Curried function for onPress event handler
  handleOnPress = (someId, someProp) => event => {
    //USE someProp ABOVE TO ACCESS PASSED PROP, WHICH WOULD BE undefined IN THIS CASE
    //Use event parameter above to access event object if you need
    console.log(someProp)

    this.setState({
      touchedId: someId
    })
  }

在下面查看工作小吃

https://snack.expo.io/@prashand/accessing-props-from-react-native-touch-event