请问antd里如何设置Input焦点?

rockswang
  • 1.4k

比如:点击一个按钮后,自动把焦点设置到某个Input上,如果能做到自动选中输入内容就更好了。

回复
阅读 30.7k
3 个回答
✓ 已被采纳
const { Input } = antd;

class App extends React.Component {
  handleClick = () => {
    const input = this.refs.myInput.refs.input;
    input.focus();
    input.setSelectionRange(0, input.value.length);
  };
  
  render() {
    return (
      <div>
        <Input ref="myInput" defaultValue="foo" />
        <button onClick={this.handleClick}>Focus</button>
      </div>
    );
  }
}

http://codepen.io/yesmeck/pen...

用的antd的版本是3.2.2的,楼上的答案好像是没有用了,不知道什么版本开始换了新的方式。

class App extends React.Component {
  handleClick = () => {
    const { input } = this.inputRef; // 如果是textArea的话,const { textAreaRef } = this.inputRef;
    input.focus();
    input.setSelectionRange(0, input.value.length);
    // input.select(); // 可全部选中
  };
  
  render() {
    return (
      <div>
        <Input ref={(input) => { this.inputRef = input; }} defaultValue="foo" />
        <button onClick={this.handleClick}>Focus</button>
      </div>
    );
  }
}

把this.inputRef打印出来就可以发现

clipboard.png

谢谢yesmeck!
不过Input在ant design的表单里面时,情况好像有些不同,直接在作为Form.Item子元素的Input上面增加ref属性会报错,看了下rc-form的源码,它里面的ref是个参数为Dom Component的回调函数。可以在这一步把控件的引用保存下来。另外,必须在state修改生效后再调用focus等方法,否则无效果。
我做的是一个点击后变成可编辑状态的文本域控件,改成这样,目前是符合我的需求了:

import React, {PropTypes} from 'react'
import {
  Form,
  Input,
  Icon
} from 'antd'

const FormItem = Form.Item

const Span = React.createClass({

  inputRef: undefined,

  propTypes: {
    fieldKey: PropTypes.string.isRequired,
    label: PropTypes.string,
    value: PropTypes.string,
    required: PropTypes.bool,
    pattern: PropTypes.object,
    form: PropTypes.object.isRequired
  },

  getInitialState() {
    return {}
  },

  componentDidMount() {
    this.setState({value: this.props.value || '', editing: false})
  },

  componentDidUpdate(prevProps, prevState) {
    if (this.state.editing && !prevState.editing) {
      const input = this.inputRef.refs.input
      input.focus()
      input.setSelectionRange(0, input.value.length);
    }
  },

  startEdit() {
    this.setState({...this.state, editing: true})
  },

  endEdit() {
    this.props.form.validateFields([this.props.fieldKey], (errors, values) => {
      if (errors) return
      const value = values[this.props.fieldKey]
      this.setState({value, editing: false})
    })
  },

  render() {
    const k = this.props.fieldKey
    const message = '请输入' + this.props.label
    return (
      <span>
        <span style={{display: this.state.editing ? 'none' : '', background: '#eeeeff'}} onClick={this.startEdit}>
          {this.state.value || '未设定'}
        </span>
        <span style={{display: !this.state.editing ? 'none' : ''}}>
          <FormItem style={{marginBottom: 0}}>{
            this.props.form.getFieldDecorator(k, {
              initialValue: this.state.value,
              rules: [{required: this.props.required, message, pattern: this.props.pattern}]
            })(<Input size="default" placeholder={message} ref={c => this.inputRef = c}
                      addonAfter={<span onClick={this.endEdit}><Icon type="check"/></span>}
                      onPressEnter={this.endEdit}/>)
          }
          </FormItem>
        </span>
      </span>
    )
  }

})

export default Span
撰写回答
你尚未登录,登录后可以
  • 和开发者交流问题的细节
  • 关注并接收问题和回答的更新提醒
  • 参与内容的编辑和改进,让解决方法与时俱进
宣传栏