dealing with ref within a loop in react
以下是我的父组件,但是如何选择关注哪个输入? 在这种情况下是否必须创建动态引用?
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 | class TestRef extends React.Component { ref = React.createRef(); state = { data: [ { name:"abc" }, { name:"def" } ] }; focusInput = () => this.ref.current.focus(); render() { return ( {this.state.data.map(o => { return <Hello placeholder={o.name} ref={this.ref} />; })} <button onClick={this.focusInput}>focus input 1</button> <button onClick={this.focusInput}>focus input 2</button> ); } } |
您可以使用回调引用来生成并将每个输入的动态引用存储在数组中。 现在,您可以使用ref的索引来引用它们:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 | const Hello = React.forwardRef((props, ref) => <input ref={ref} />); class Button extends React.Component { onClick = () => this.props.onClick(this.props.id); render() { return ( <button onClick={this.onClick}>{this.props.children}</button> ); } } class TestRef extends React.Component { state = { data: [ { name:"abc" }, { name:"def" } ] }; inputRefs = []; setRef = (ref) => { this.inputRefs.push(ref); }; focusInput = (id) => this.inputRefs[id].focus(); render() { return ( {this.state.data.map(({ name }) => ( <Hello placeholder={name} ref={this.setRef} key={name} /> ))} <Button onClick={this.focusInput} id={0}>focus input 1</Button> <Button onClick={this.focusInput} id={1}>focus input 2</Button> ); } } ReactDOM.render(<TestRef />, document.getElementById("root")); |
1 2 | <script crossorigin src="https://unpkg.com/react@16/umd/react.development.js"> <script crossorigin src="https://unpkg.com/react-dom@16/umd/react-dom.development.js"> |
使用一般用途焦点挂钩
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 | // General Focus Hook const useFocus = (initialFocus = false, id ="") => { const [focus, setFocus] = useState(initialFocus) return ([ (newVal=true) => setFocus(newVal), { autoFocus: focus, key: `${id}${focus}`, onFocus: () => setFocus(true), onBlur: () => setFocus(false), }, ]) } const data: [{ name:"abc" },{ name:"def" }] const TestRef = () => { const focusHelper = data.map( (_,i) => { const [setFocus, focusProps]= useFocus(false, i) return {setFocus, focusProps} }) return ( {data.map( (o,i) => ( <Hello placeholder={o.name} {...focusHelper[i].focusProps} />; ))} <button onClick={() => focusHelper[0].setFocus()}>focus input 1</button> <button onClick={() => focusHelper[1].setFocus()}>focus input 2</button> ); } |
您可以在此处找到更多信息:渲染后将焦点放在输入上
我发现了另一种解决方法:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 | let dataCount = 0; class TestRef extends React.Component { state = { data: [ { name:"abc" }, { name:"def" } ] }; focusInput = (thisHello) => this[`ref${thisHello}`].current.focus(); render() { return ( {this.state.data.map(o => { dataCount++ return <Hello placeholder={o.name} ref={(el) => { this[`ref${dataCount}`] = el; }} />; })} <button onClick={() => this.focusInput(1)}>focus input 1</button> <button onClick={() => this.focusInput(2)}>focus input 2</button> ); } } |
如果Hello元素具有用作变量的键或唯一ID,则不需要