假设我有一个包含多个输入字段的表单。在正常的ES6 / React中,我将创建一个单个方法,所有输入字段都将指向其onChange
处理程序。像这样:
handleChange(e) {
e.preventDefault();
this.setState({[e.target.name]: e.target.value});
}
这有助于您拥有大量表单元素并且不必创建特定方法来处理每个表单元素。
这在TypeScript中是否可行?即使它不是类型安全的吗?
答案 0 :(得分:8)
如评论中所述,您在JavaScript中可以执行的所有操作也都是有效的TypeScript。
但是,我猜你会从TypeScript编译器中获得错误(取决于你设置的编译器选项)。
假设您的组件看起来像这样:
noImplicitAny
我收到了这个错误:
==外部:(30,19):错误TS2345:类型'{[x:number]的参数:any; }'不能赋值给'ComponentState'类型的参数。
==外部:类型'{[x:number]中缺少属性'name':any; }”。
使用handleChange
编译器选项(我喜欢使用)时,这个附加错误:
==外部:(28,16):错误TS7006:参数'e'隐式具有'any'类型。
如果您确定自己的代码是正确的,可以通过显式转换setState
的参数和 handleChange(e: any) {
e.preventDefault()
this.setState({ [e.target.name]: e.target.value } as ComponentState)
}
val filledForm = userForm.fill(User("Bob", 18))
答案 1 :(得分:4)
我这样解决了这个问题:
handleChange = (field: string) => (event) => {
this.setState({ [field]: event.target.value } as Pick<State, any>);
};
...
<Input onChange={this.handleChange('myField')} />
“接受的答案”对我不起作用。
答案 2 :(得分:1)
import React, { useState } from 'react';
const Form = () => {
const [inputValues, setInputValues] = useState<{ [x: string]: string }>()
const handleFormSubmit = async (e: React.MouseEvent<HTMLElement>) => {
e.preventDefault()
const data = {
name: inputValues?.name,
email: inputValues?.email,
phone: inputValues?.phone,
income: inputValues?.name
}
const requestOptions = {
method: 'POST',
headers: { 'Content-Type': 'application/json' },
body: JSON.stringify(data)
};
try {
const response = await fetch('https://xyz/form-submit', requestOptions)
const res = await response.json()
console.log(res)
} catch (error) {
console.log(error)
}
}
const handleInputChange = (e: React.FormEvent<HTMLInputElement>) => {
const { name, value } = e.currentTarget
setInputValues(prevState => ({ ...prevState, [name]: value }))
}
return (
<div className="Form">
<div className="form-wrapper">
<h1>Demo Form for React</h1>
<form className="form">
<input
className="form-input"
name="name"
value={inputValues?.name || ''}
onChange={handleInputChange}
placeholder="Your Name"
type="text"
data-testid="form-input-name"
/>
<input
className="form-input"
name="phone"
value={inputValues?.phone || ''}
onChange={handleInputChange}
placeholder="Your Phone"
type="tel"
data-testid="form-input-phone"
/>
<input
className="form-input"
name="email"
value={inputValues?.email || ''}
onChange={handleInputChange}
placeholder="Your Email"
type="email"
data-testid="form-input-email"
/>
<input
className="form-input"
name="income"
value={inputValues?.income || ''}
onChange={handleInputChange}
placeholder="Your Annual Income"
type="number"
data-testid="form-input-income"
/>
<button
className='form-submit'
data-testid="form-submit"
onClick={handleFormSubmit}
>
Submit
</button>
</form>
</div>
</div>
);
}
export default Form;
示例 Typescript 表单。它的特点:
onChange
处理程序此外,使用这种方法,您不必使用 @ts-ignore
、any
或更改您的 tsconfig
。
请随心所欲地使用它。
答案 3 :(得分:0)
在界面中,您必须调整状态值,即[e.target.name]和e.target.value类型的字符串或根据您的代码指定的任何值。
interface formState {
//it can be (name: string address: string)
[key: string]: string;
}
handleChange(e: any) {
this.setState({
[e.target.name]: e.target.value
});
}
例如
interface LoginFormState {
//can be
//email: string
//password: string
[key: string]: string;
}
interface Props {}
class LoginForm extends React.Component<Props, LoginFormState> {
constructor(props: Props) {
super(props);
this.state = {
email: "",
password: ""
};
this.handleChange = this.handleChange.bind(this);
}
handleChange(e: any) {
this.setState({
[e.target.name]: e.target.value
});
// console.log("email", this.state.email);
}
希望获得帮助