我对react/react-native还比较陌生,我认为我正在做一些react在渲染中不喜欢的事情,尽管它并不能帮助我理解错误。
这是一个 expo/react-native typescript 项目。
我想在 CalendarEventItem 上定义一个 getStartDateTime() 方法,因为我想将 startTime 属性重构为数字而不是日期。
错误:
Render Error: event.getStartDateTime is not a function (it is undefined)
Typescript 没有任何抱怨,显然只有反应/反应本机渲染器。直接访问 startTime 属性效果很好,调用方法会导致此错误。
最低代码:
const Component = () => {
const events: CalendarEventItem[] = useCalendarStore((state) => state.events); // Zustand store
const calculatePositionOffset(startTime: Date, gap: number, rowHeight: number) => {
return (startTime.getHours() + startTime.getMinutes() / 60) * rowHeight + gap;
}
return (
{events.length &&
events.map((event) => (
<EventContainer
event={event}
position={{
top: calculatePositionOffset(event.getStartDateTime(), 3, 30), // <-- Error occurs here
left: 100,
}}
key={"event-" + event.id}
/>
))}
);
}
// Probably can ignore mixins, including just for completeness
abstract class CalendarEvent extends extendSchedulableItem(extendAgendaObject(class {})) {
abstract getStartDateTime(): Date; // this is here because I ultimately want to define
// this method on a grandparent class, removing does not
// affect the error
}
class CalendarEventItem extends CalendarEvent {
startTime: Date; // want to refactor this to number, hence the need for a method
constructor(params) {
super(params); // this.startTime is initialized by a grandparent constructor in SchedulableItem
}
getStartDateTime() {
return new Date(this.startTime);
}
}
export { CalendarEvent, CalendarEventItem }
对我来说有趣的部分是:
top: calculatePositionOffset(event.startTime, 3, 30), // <-- Works absolutely fine
top: calculatePositionOffset(event.getStartDateTime(), 3, 30), // <-- Produces the render error
我做错了什么?
我尝试了各种方法来重新定义方法,包括在祖父母类和 mixin 中。即使只是在最终类中独立定义,它似乎也不起作用。事实证明,AI 助手对于理解或解决问题没有帮助。
我还尝试用 useCallback 包装calculatePositionOffset,以防这对渲染器更友好,但最终结果相同(错误略有不同,但仍然源于未定义的 startTime 参数)。
所以,显然,问题不在于 React/React-native,而在于更基本的 JavaScript 语义知识。
将方法定义为箭头函数完全解决了所有错误,因为
this
上下文,而箭头函数保留 this
的词法范围,而常规函数 may
根据其绑定方式保留范围。
getStartDateTime = () => {
return new Date(this.startTime);
}
你知道的越多!