React Native + TypeScript传递动态组件时'onPress'属性不存在错误
解决TypeScript类型错误:为可点击组件抽象添加正确类型约束
问题核心在于你没有给TriggerComponent和triggerProps添加正确的类型约束,TypeScript无法确认传入的组件支持onPress属性。以下是具体解决方案:
1. 定义可点击组件的基础Props类型
首先创建一个类型,描述所有支持onPress的组件共有的属性:
type PressableProps = { onPress?: () => void; // 可根据需要添加其他通用属性,比如style、testID等 };
2. 使用泛型关联组件与Props
通过泛型让Menu组件的TriggerComponent和triggerProps类型严格关联,确保triggerProps符合组件的Props要求,同时排除我们要手动传入的onPress:
修改IMenu接口和Menu组件:
import { ReactNode, FunctionComponent, useRef, ElementRef } from 'react'; import { Menu as PMMenu, MenuOptions, MenuTrigger, withMenuContext, } from 'react-native-popup-menu'; import { View } from 'react-native'; type PressableProps = { onPress?: () => void; }; interface IMenu<T extends PressableProps> { children: ReactNode; ctx: { menuActions: { toggleMenu: (name: string) => void; }; }; TriggerComponent: FunctionComponent<T>; triggerProps: Omit<T, 'onPress'>; // 排除onPress,避免与手动传入的冲突 } function Menu<T extends PressableProps>({ ctx: { menuActions: { toggleMenu } }, children, TriggerComponent, triggerProps, }: IMenu<T>) { const menuRef = useRef<ElementRef<typeof MenuTrigger>>(null); // ... 你的其他逻辑代码 return ( <View> <TriggerComponent {...triggerProps} onPress={() => toggleMenu(menuRef.current?.props?.menuName)} /> <PMMenu> <MenuTrigger ref={menuRef} /> <MenuOptions customStyles={optionsStyles}> {children} </MenuOptions> </PMMenu> </View> ); }
3. 为什么这样能解决问题?
- 泛型
T确保TriggerComponent的Props包含onPress,TypeScript不再质疑onPress的合法性 Omit<T, 'onPress'>让triggerProps自动排除onPress,避免重复传入的冲突,同时严格匹配组件的其他Props要求- 相比使用
any,这种方式保留了完整的类型检查,既能避免错误,又能获得TypeScript的类型提示
简化版(无需泛型)
如果不需要严格关联组件的具体Props,也可以直接约束TriggerComponent为支持onPress的函数组件:
type PressableComponent = FunctionComponent<PressableProps & Record<string, unknown>>; interface IMenu { children: ReactNode; ctx: { menuActions: { toggleMenu: (name: string) => void; }; }; TriggerComponent: PressableComponent; triggerProps: Record<string, unknown>; }
这种方式更灵活,但类型检查的严谨性稍弱,适合不需要严格校验triggerProps结构的场景。
内容的提问来源于stack exchange,提问作者usbToaster
相关产品推荐
相关产品推荐

