自定义组件中的 Props React Native + TypeScript
我在自定义组件中访问 onChangeText 时遇到了问题。以下是我的组件代码:
import React from 'react';
import {TextInput, StyleSheet} from 'react-native';
type Props=
{
style:any
}
const Input = (props:Props) =>
{
return <TextInput {...props} style = {{...styles.input, ...props.style}} blurOnSubmit autoCorrect = {false} keyboardType = "number-pad" maxLength = {2} />
}
const styles = StyleSheet.create({
input:{
height:30,
borderBottomColor: 'grey',
borderBottomWidth: 1,
marginVertical: 10
}
})
export default Input;`
这是我在另一个文件中使用它的代码部分:
<Input style = {styles.input} onChangeText = {numberInputHandler} value = {enteredValue} />
OnChangeText 被加下划线,错误是属性 'onChangeText' 在类型 'IntrinsicAttributes & Props' 上不存在。我在一个教程中看到,在自定义组件中输入 {...props} 后可以访问它的 props,但那个人是在写 JS,而我是在写 TS。谢谢帮助!
答案#1
你的 Input 组件会将它的所有属性传递给底层的 TextInput,所以你可能希望它接受 TextInput 的所有属性。目前它只接受 style 属性,因为这是 Props 中唯一的属性。
你想要的 props 是从 react-native 导出的,名称为 TextInputProps,所以你可以导入这个 interface。
import { TextInput, TextInputProps, StyleSheet } from "react-native";
TextInputProps 已经包含一个 style 属性,其类型比你的 any 更准确,所以你可以完全删除你的 Props 接口。
const Input = (props: TextInputProps) => {
现在当你将两种样式结合时会出现错误,因为 props.style 可能是一个样式数组。在 react-native 中,你可以将多个样式放在一个数组中,即使这些样式本身可能也是数组。所以你可以这样组合:
style={[styles.input, props.style]}
由于我们允许了所有的 TextInputProps,如果你使用 <Input maxLength={5}/> 调用你的 Input,你不会收到错误。目前,由于顺序原因,这个 maxLength 属性会被忽略并被 maxLength={2} 覆盖——后面的属性会覆盖前面的属性。如果这是你想要的,那么这个组件是可以的:
const Input = (props: TextInputProps) => {
return (
<TextInput
{...props}
style={[styles.input, props.style ]}
blurOnSubmit
autoCorrect={false}
keyboardType="number-pad"
maxLength={2}
/>
);
};
如果你想让自定义属性覆盖默认属性,那么你需要更改顺序:
const Input = (props: TextInputProps) => {
return (
<TextInput
blurOnSubmit
autoCorrect={false}
keyboardType="number-pad"
maxLength={2}
{...props}
style={[styles.input, props.style]}
/>
);
};
答案#2
您可以在组合中同时使用自定义属性和 TextInput 属性,请参阅下面的代码,
import { TextInput, TextInputProps } from 'react-native';
interface OwnProps {
style?: ViewStyle;
password?: boolean;
error?: string;
}
export type CustomInputProps = TextInputProps & OwnProps;
export const CustomInput = (props: CustomInputProps) => {
const { style, password, error, ...restProps } = props;
return (
<TextInput
secureTextEntry={password ? hidePassword : false}
{...restProps}
/>
);
}
