【问题标题】:Stateless function components cannot hav refs无状态函数组件不能有 refs
【发布时间】:2018-03-29 02:43:03
【问题描述】:

我正在构建类似于 Facebook 或 instagram 的搜索页面。基本上,如果我们按下搜索按钮,它会导航到“搜索屏幕”。当它的组件被挂载时,我想设置搜索头是焦点(光标)。

我的问题是当我将 TextInput ref 设置为道具时。我收到Stateless function components cannot have refs 错误。这是正确的方法吗?为什么它不起作用?你知道除此之外还有什么更好的方法吗?

我在 FlatList 中的 renderHeader 属性中添加了 _renderHeader 私有函数。 这是_renderHeader

  _renderHeader = () => {
    return (
      <View style={styles.layoutheader}>
        <View style={styles.containerheader}>
          <RkTextInput
            rkType='row'
            ref="sbar"  /////////////////////HERE////////////
            autoCapitalize='none'
            autoCorrect={false}
            label={<RkText rkType='awesome' style={{color:'white'}}>{FontAwesome.search}</RkText>}
            placeholder='Search'
            underlineWidth="1"
            underlineColor="white"
            style={styles.searchBarheader}
            inputStyle={{color:'white'}}
            labelStyle={{marginRight:0}}
            value={this.state.inputText}
            onChangeText={(inputText)=>{this.setState({inputText})}}
          />
          <View style={styles.left}>
            <RkButton
              rkType='clear'
              style={styles.menuheader}
              onPress={() => {
                this.props.navigation.goBack()
              }}>
              <RkText style={styles.titleText} rkType='awesome hero'>{FontAwesome.chevronLeft}</RkText>
            </RkButton>
          </View>
        </View>
      </View>
    )
  }

componentDidMount() {
    this.refs.sbar.focus(); ////////// Here I want to focus RkTextInput when it's loaded
}

更新这是所要求的实际代码

class SearchScreen extends Component {
  static navigationOptions = ({navigation}) => ({
    header: null
  })

  state = {
    active: false,
    inputText: ''
  }
   ...
  _renderRow = (row) => {
    ...
    );
  }

  _renderHeader = () => {
    ...
  }

  render() {
    return (
      <FlatList
        data={null}
        renderItem={this._renderRow}
        renderHeader={this._renderHeader}
        keyExtractor={this._keyExtractor}
        ListHeaderComponent={this._renderHeader}
      />
    );
  }

  componentDidMount() {
    this.refs.sbar.focus();
  }
}

【问题讨论】:

  • Refs 通常用于更改组件的状态,因此如果没有为组件创建 ref 是没有意义的。
  • @GuilhermeCronemberger refs 在使用原生 TextInput 控制焦点时是有意义的。
  • 对不起,我不明白。那么如何引用TextInput呢?
  • 能贴出整个组件类,还是简化版的?

标签: reactjs react-native react-navigation


【解决方案1】:

在我看来,您没有以正确的方式使用 refs。您使用它们的方式已被弃用。您应该遵循以下语法:

<input
   type="text"
   ref={(input) => { this.textInput = input; }}
 />

当您想访问它时,您可以使用this.textInput。在你的情况下,this.textInput.focus()

【讨论】:

  • 您能详细说明一下吗?我需要更多解释。太棒了
  • 实际上,上下文没有问题,只是不推荐使用 ref 的字符串,这就是您现在的做法。供参考:reactjs.org/docs/refs-and-the-dom.html
  • 嗯,它只适用于 TextInput。不是 RkTextInput。奇怪
  • akveo.github.io/react-native-ui-kitten/#/docs/ui-components/… 在 props 部分下,您可以看到我们可以使用props 替换TextInput.props。我想你现在明白了。
  • 来自 React 文档:你不能在函数组件上使用 ref 属性,因为它们没有实例。 ** 要解决这个问题,只需通过导入添加一个 useRef 钩子:import React, {useRef} from "react"; 然后初始化:let typeAheadArrowDropdownRef = useRef(null);
【解决方案2】:

您正在使用 RkTextInput 这是一个功能组件,它不能有一个引用。这就是你无法集中注意力的原因。

除了包装组件、获取根的 ref 并找到您的输入元素以对其进行聚焦之外,没有其他方法可以聚焦输入。一个粗略的例子:

class RoughExample extends React.Component {
    componentDidMount() {
        //find the input from your root
        this.input = this.root.querySelector('input');
        //if it exists, focus
        this.input && this.input.focus();
    }
    render() {
        <div ref={ (node) => {this.root = node;} }>
            <RkTextInput />
        </div>
    }
}

【讨论】:

  • 哦,这听起来很棒。你能用 React Native 语法写吗?我不确定是否可以在 RN 中使用 this.root.querySelector。
  • 我不熟悉 ReactNative API,但我会试一试。
  • 我认为 Arslan Tariq 用与您相同的概念来回答它。 :) 它现在正在工作。不过谢谢,丹尼尔!!
猜你喜欢
  • 1970-01-01
  • 2021-05-26
  • 1970-01-01
  • 2017-01-21
  • 1970-01-01
  • 2018-09-29
  • 2020-10-20
  • 2020-01-15
  • 2020-08-10
相关资源
最近更新 更多