【问题标题】:Add or focus to next input field when press keyboard ENTER button按键盘 ENTER 按钮时添加或聚焦到下一个输入字段
【发布时间】:2019-01-31 09:58:13
【问题描述】:

我正在学习 React 和 Material-ui。

我想在一个组件中创建几个输入字段,这些字段的数量和值作为 props 从父组件接收。我添加了一个功能,可以在用户按下 Enter 按钮时移动焦点,或者在最后一个字段时创建新字段。

当前代码有 15 个引用(我知道这很愚蠢,但我认为不会超过 15 个)。问题是焦点在创建时不会移动到新字段。你能推荐一个更好的方法吗?

class ResponseInput extends Component {
    componentWillMount() {
        this.refs = [...Array(15)].map(r => React.createRef())
    }

    changeFocus = index => {
        if (index < this.props.inputs.length - 1) {
            this.refs[index + 1].current.focus();
        } else {
            this.props.addInput();
        }
    }

    render() {
        const { inputs, addInput, handleChangeInput } = this.props;

        return (
            <List>
                {inputs.map((item, index) => (
                    <ListItem key={index} >
                        <Input
                            value={item}
                            inputRef={this.refs[index]}
                            onChange={(event) => handleChangeInput (index, event)}
                            onKeyPress= {(event) => {
                                if (event.key === 'Enter') {
                                    this.changeFocus(index);
                                }
                            }}
                            // autoFocus
                        />
                    </ListItem>
                ))}
            </List>
        );
    }
}

【问题讨论】:

    标签: reactjs material-ui


    【解决方案1】:

    https://codesandbox.io/s/7wojmxv0oq

    &lt;Input autoFocus={index+1&gt;originalInputsLength} .../&gt;

    使用autoFocus={index+1&gt;originalInputsLength} 检查这意味着如果输入长度超过原始输入长度(用户添加列表),则将自动对焦设置为新创建的&lt;Input/&gt;

    originalInputsLength 在 App 的构造函数中初始化为 state,然后作为 props 传递给&lt;ResponseInput inputs={inputs} addInput={this.addInput} originalInputsLength={originalInputsLength}/&gt;

    class App extends React.Component {
      constructor(props){
        super(props);
        const inputs = [1, 2, 3, 4, 5];
        this.state = {
          inputs: inputs,
          originalInputsLength: inputs.length,
        };
      }
    

    【讨论】:

      【解决方案2】:

      autoFocus={true} 添加到Input 应该可以解决它。

      render() {
          const { inputs, addInput, handleChangeInput } = this.props;
      
          return (
              <List>
                  {inputs.map((item, index) => (
                      <ListItem key={index} >
                          <Input
                              autoFocus={true}
                              value={item}
                              inputRef={this.refs[index]}
                              onChange={(event) => handleChangeInput (index, event)}
                              onKeyPress= {(event) => {
                                  if (event.key === 'Enter') {
                                      this.changeFocus(index);
                                  }
                              }}
                              // autoFocus
                          />
                      </ListItem>
                  ))}
              </List>
          );
      }
      

      https://codesandbox.io/s/10089vq54l的演示

      【讨论】:

      • 非常感谢。但是,我已经尝试过这个,并且我已经放弃了这个,因为我不希望刷新时焦点移动到最后一个字段。如果您能提出其他方法,我将不胜感激。
      • 这有点复杂,因为你需要保持一些状态并使用getDerivedStateFromProps 来处理它何时应该允许焦点。见codesandbox.io/s/8kppllw1z8
      猜你喜欢
      • 1970-01-01
      • 2021-08-07
      • 1970-01-01
      • 2013-09-20
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多