首页 > 解决方案 > 在循环内被起诉时,不会为正确的项目调用 onLayout

问题描述

我在循环中渲染项目,我需要获取每个项目的 Y 位置,以便scrollTo()稍后在事件发生时滚动到该位置。
问题是它似乎onLayout没有正确调用,所以我得到了错误的项目位置。
示例项目:

A,B,C,D

但我有时会为 A 存储位置,有时为 C 等存储位置。
我怎样才能同步呢?

this.props.list.map((item, index) => {
   return (
      <TouchableOpacity
        onLayout={(event) => {
          let {x, y, width, height} = event.nativeEvent.layout;
....



更新

这是完整的代码。所以你看我设置了我找到的第一个国家索引onLayout。因此,当我按B时,它应该滚动到巴哈马的位置,但它有时会滚动到巴哈马,有时会滚动到巴巴多斯,有时会滚动到不丹......

const countries = ["Afghanistan", "Albania", "Algeria", "American Samoa", "Andorra", "Angola", "Anguilla", "Antarctica", "Antigua and Barbuda", "Argentina", "Armenia", "Aruba", "Australia", "Austria", "Azerbaijan", "Bahamas", "Bahrain", "Bangladesh", "Barbados", "Belarus", "Belgium", "Belize", "Benin", "Bermuda", "Bhutan"];

export default class App extends Component {

  constructor(props, context) {
    super(props, context);

    this.state = {
      currentLetter: "A",
    };

    this.sections = {}
  }

onLetter(letter) {
    this.setState({currentLetter: letter});
    if (this.sections[letter]) {
      this.scrollView.scrollTo({ y: this.sections[letter] });
    }
  }

<ScrollView ref={ref => this.scrollView = ref}>
          {
            countries.map((item) => {
              return (
                <View onLayout={(event) => {
                  var {x, y, width, height} = event.nativeEvent.layout;
                    if (!this.sections[item[0]]) {
                      this.sections[item[0]] = y;
                    }
                  }}
                  style={{backgroundColor: "#f0aabb", padding: 10, margin: 5}}>
                  <Text>{item}</Text>
                </View>
              )
            })
          }
        </ScrollView>

标签: react-native

解决方案


我认为onLayout没有按顺序进行。所以不确定巴哈马是否会先行。

我认为您应该为映射字母和起始/指向项目创建一个函数,例如:'A' = 'Afghanistan', 'B' = 'Bahamas'

您可以对其进行硬编码(不推荐,只是解释一下这个想法)

dataSource = { 'Afghanistan': 'A', 'Bahamas': 'B'}
// implement this func base on your rules for title and letter
getLetterFromTitle(title) {
  return dataSource[title];
} 

然后onLayout

const letter = getLetterFromTitle(item);
if (letter && !this.sections[letter]) {
  this.sections[letter] = y;
}

推荐阅读