label
s 가있는 양식 요소가 있고 s label
를 htmlFor
속성 이있는 요소 에 연결하는 고유 ID를 갖고 싶습니다 . 이 같은:
React.createClass({
render() {
const id = ???;
return (
<label htmlFor={id}>My label</label>
<input id={id} type="text"/>
);
}
});
나는 기반으로 ID를 생성 this._rootNodeID
했지만 React 0.13 이후로는 사용할 수 없습니다. 지금 가장 좋고 / 또는 가장 간단한 방법은 무엇입니까?
답변
이 솔루션은 저에게 잘 작동합니다.
utils/newid.js
:
let lastId = 0;
export default function(prefix='id') {
lastId++;
return `${prefix}${lastId}`;
}
그리고 다음과 같이 사용할 수 있습니다.
import newId from '../utils/newid';
React.createClass({
componentWillMount() {
this.id = newId();
},
render() {
return (
<label htmlFor={this.id}>My label</label>
<input id={this.id} type="text"/>
);
}
});
그러나 동형 앱에서는 작동하지 않습니다.
추가됨 17.08.2015 . 사용자 정의 newId 함수 대신 lodash 에서 uniqueId 를 사용할 수 있습니다 .
업데이트 : 2016 년 1 월 28 일 . .NET에서 ID를 생성하는 것이 좋습니다 componentWillMount
.
답변
ID는 .NET이 아닌 componentWillMount (2018 년 업데이트) 내에 있어야합니다 . 그것을 넣으면 불필요하게 새 ID가 다시 생성됩니다.constructor
render
render
밑줄이나 lodash를 사용하는 경우 uniqueId
함수가 있으므로 결과 코드는 다음과 같아야합니다.
constructor(props) {
super(props);
this.id = _.uniqueId("prefix-");
}
render() {
const id = this.id;
return (
<div>
<input id={id} type="checkbox" />
<label htmlFor={id}>label</label>
</div>
);
}
2019 Hooks 업데이트 :
import React, { useState } from 'react';
import _uniqueId from 'lodash/uniqueId';
const MyComponent = (props) => {
// id will be set once when the component initially renders, but never again
// (unless you assigned and called the second argument of the tuple)
const [id] = useState(_uniqueId('prefix-'));
return (
<div>
<input id={id} type="checkbox" />
<label htmlFor={id}>label</label>
</div>
);
}
답변
2019-04-04에 이어 React Hooks ‘로이 작업을 수행 할 수있는 것 같습니다 useState
.
import React, { useState } from 'react'
import uniqueId from 'lodash/utility/uniqueId'
const Field = props => {
const [ id ] = useState(uniqueId('myprefix-'))
return (
<div>
<label htmlFor={id}>{props.label}</label>
<input id={id} type="text"/>
</div>
)
}
export default Field
내가 이해했듯이, 당신은 업데이트를 허용하는 배열 분해의 두 번째 배열 항목을 무시 id
하고 이제 구성 요소의 수명 동안 다시 업데이트되지 않는 값을 얻었습니다.
의 값이 id
될 것이다 myprefix-<n>
곳 <n>
에서 리턴 증분 정수 값이다 uniqueId
. 그것이 당신에게 충분히 독특하지 않다면, 당신 만의 것을 만드는 것을 고려하십시오.
function gen4() {
return Math.random().toString(16).slice(-4)
}
function simpleUniqueId(prefix) {
return (prefix || '').concat([
gen4(),
gen4(),
gen4(),
gen4(),
gen4(),
gen4(),
gen4(),
gen4()
].join(''))
}
또는 https://github.com/rpearce/simple-uniqueid 에서 게시 한 라이브러리를 확인 하십시오 . 또한 수백 또는 수천 개의 다른 고유 ID가 있지만 uniqueId
접두사가있는 lodash 는 작업을 완료하기에 충분합니다.
업데이트 2019-07-10
@Huong Hk에게 게으른 초기 상태 를 연결 하도록 알려 주셔서 감사합니다. 이의 합계 useState
는 초기 마운트에서만 실행 되는 함수를 전달할 수 있다는 것입니다.
// before
const [ id ] = useState(uniqueId('myprefix-'))
// after
const [ id ] = useState(() => uniqueId('myprefix-'))
답변
이를 위해 node-uuid 와 같은 라이브러리를 사용하여 고유 한 ID를 얻을 수 있습니다.
다음을 사용하여 설치 :
npm install node-uuid --save
그런 다음 반응 구성 요소에 다음을 추가하십시오.
import {default as UUID} from "node-uuid";
import {default as React} from "react";
export default class MyComponent extends React.Component {
componentWillMount() {
this.id = UUID.v4();
},
render() {
return (
<div>
<label htmlFor={this.id}>My label</label>
<input id={this.id} type="text"/>
</div>
);
}
}
답변
체크섬 문제가 처음부터 나를 이끈 이유이기 때문에 범용 / 동형 솔루션을 찾는 모든 사람에게 도움이되기를 바랍니다.
위에서 말했듯이 순차적으로 새 ID를 만드는 간단한 유틸리티를 만들었습니다. ID는 서버에서 계속 증가하고 클라이언트에서 0부터 다시 시작하기 때문에 SSR이 시작될 때마다 증가분을 재설정하기로 결정했습니다.
// utility to generate ids
let current = 0
export default function generateId (prefix) {
return `${prefix || 'id'}-${current++}`
}
export function resetIdCounter () { current = 0 }
그런 다음 루트 구성 요소의 생성자 또는 componentWillMount에서 재설정을 호출합니다. 이것은 본질적으로 각 서버 렌더링에서 서버의 JS 범위를 재설정합니다. 클라이언트에서는 효과가 없습니다.
답변
label
및 의 일반적인 사용법의 경우 다음 과 input
같이 입력을 레이블로 래핑하는 것이 더 쉽습니다.
import React from 'react'
const Field = props => (
<label>
<span>{props.label}</span>
<input type="text"/>
</label>
)
또한 체크 박스 / 라디오 버튼에서 패딩을 루트 요소에 적용하고 여전히 입력에 대한 클릭 피드백을받을 수 있습니다.
답변
다음과 같은 쉬운 해결책을 찾았습니다.
class ToggleSwitch extends Component {
static id;
constructor(props) {
super(props);
if (typeof ToggleSwitch.id === 'undefined') {
ToggleSwitch.id = 0;
} else {
ToggleSwitch.id += 1;
}
this.id = ToggleSwitch.id;
}
render() {
return (
<input id={`prefix-${this.id}`} />
);
}
}
