React:多个状态值改变组合 parent 的值?
React: multiple state values changing a composed parent's value?
我很难在 React 中引入 UrlInput
组件。主要思想是获取 props,例如 url
及其 setter(来自 parent)并将其在内部拆分为 3 UrlInput
状态值,例如protocol
、host
和 port
。 UrlInput
应该使用 3 个表单字段并在 parent 中更改一个 url
。
简化版:
export const UrlInput = ({ url, parentSetter }) => {
const [fields, setFields] = useState({ protocol: "", host: "", port: 0 });
useEffect(() => {
const urlRegex = /(https?):\/\/([a-z]+):([0-9]{4,6})/;
const [, protocol, host, port] = url.match(urlRegex);
setFields({ protocol, host, port });
}, [url]);
const onChange = e => {
setFields({ ...fields, [e.target.name]: e.target.value });
parentSetter(`${fields.protocol}://${fields.host}:${fields.port}`);
};
return (
<>
<input type="text" name="protocol" value={fields.protocol} onChange={onChange} />
://
<input type="text" name="host" value={fields.host} onChange={onChange} />
:
<input type="number" name="port" value={fields.port} onChange={onChange} />
<p>{JSON.stringify(fields)}</p>
</>
);
};
function App({ url: initialUrl }) {
const [url, setUrl] = useState(initialUrl);
const [age, setAge] = useState(0);
return (
<>
<input type="number" name="age" value={age} onChange={e => setAge(e.target.value)} />
<br />
<UrlInput url={url} parentSetter={setUrl} />
<p>{JSON.stringify({ url, age })}</p>
</>
);
}
当前行为:
- 第一次更改,例如
protocol
:UrlInput
状态改变,parent的状态没有改变
- 第二次更改,例如
host
:Parent 将 protocol
与 UrlInput
同步,UrlInput
更改无效
- 同 1
- 同 2
等等。您可以验证行为 here.
我想要一个简单的 API - 只是 url
和 setter
,但也许不应该这样做?
使用此代码:
const onChange = e => {
const data = { ...fields, [e.target.name]: e.target.value };
setFields(data);
parentSetter(`${data.protocol}://${data.host}:${data.port}`);
};
我很难在 React 中引入 UrlInput
组件。主要思想是获取 props,例如 url
及其 setter(来自 parent)并将其在内部拆分为 3 UrlInput
状态值,例如protocol
、host
和 port
。 UrlInput
应该使用 3 个表单字段并在 parent 中更改一个 url
。
简化版:
export const UrlInput = ({ url, parentSetter }) => {
const [fields, setFields] = useState({ protocol: "", host: "", port: 0 });
useEffect(() => {
const urlRegex = /(https?):\/\/([a-z]+):([0-9]{4,6})/;
const [, protocol, host, port] = url.match(urlRegex);
setFields({ protocol, host, port });
}, [url]);
const onChange = e => {
setFields({ ...fields, [e.target.name]: e.target.value });
parentSetter(`${fields.protocol}://${fields.host}:${fields.port}`);
};
return (
<>
<input type="text" name="protocol" value={fields.protocol} onChange={onChange} />
://
<input type="text" name="host" value={fields.host} onChange={onChange} />
:
<input type="number" name="port" value={fields.port} onChange={onChange} />
<p>{JSON.stringify(fields)}</p>
</>
);
};
function App({ url: initialUrl }) {
const [url, setUrl] = useState(initialUrl);
const [age, setAge] = useState(0);
return (
<>
<input type="number" name="age" value={age} onChange={e => setAge(e.target.value)} />
<br />
<UrlInput url={url} parentSetter={setUrl} />
<p>{JSON.stringify({ url, age })}</p>
</>
);
}
当前行为:
- 第一次更改,例如
protocol
:UrlInput
状态改变,parent的状态没有改变 - 第二次更改,例如
host
:Parent 将protocol
与UrlInput
同步,UrlInput
更改无效 - 同 1
- 同 2
等等。您可以验证行为 here.
我想要一个简单的 API - 只是 url
和 setter
,但也许不应该这样做?
使用此代码:
const onChange = e => {
const data = { ...fields, [e.target.name]: e.target.value };
setFields(data);
parentSetter(`${data.protocol}://${data.host}:${data.port}`);
};