callstack / callstack/react-native-pager-view

NSInternalInconsistencyException crashes app

Open
#507 6 comments 3 reactions 0 assignees View on GitHub
Dominant language
TypeScript
Stars
3.4k
Forks
476
Avg merge
10d 21h
Merged PRs (30d)
2

Description

## Environment

iOS

## Description

I have some fairly simple code that populates pages and then navigates to one of them. For some reason, if I am generating more than 20/30 pages on iOS, the app crashes with:

*** Terminating app due to uncaught exception 'NSInternalInconsistencyException', reason: 'Unexpected view controller: '

## Reproducible Demo

I populate maybe 20 pages, and then elsewhere in the app, asynchronously navigate to a page somewhere towards the end (but after the pages in theory have been populated). I can see for a split second that it's trying to land on a page that doesn't yet exist, then it crashes. I guess that it's trying to access this screen before it has time to generate it. Oddly, using a setTimeout to access the page does not help. I call the page with `setPage` on the ref.

The code of the component in question:

```
type Props = {
// Should always be in order
dates: SliderDate[]
onDateSelect: (date: Date) => void
}

function sliceIntoChunks(arr: any[], chunkSize: number) {
const res = []
for (let i = 0; i < arr.length; i += chunkSize) {
const chunk = arr.slice(i, i + chunkSize)
res.push(chunk)
}

return res
}

export const DateSlider = (props: Props) => {
const [weeks, setWeeks] = useState([])

const getWeeks = (dates: SliderDate[]): SliderDate[][] => {
const weekResult: SliderDate[] = []

/// Fill with blank dates
const dateTicker = new Date()
dateTicker.setHours(0, 0, 0, 0)
dateTicker.setDate(dateTicker.getDate() - 100) // <--- breaks it
// dateTicker.setDate(dateTicker.getDate() - 10) // <- this one is ok

// find closest monday
while (dateTicker.getDay() !== 1) {
dateTicker.setDate(dateTicker.getDate() + 1)
}

console.log("got here")
for (let i = -10; i < 30; i++) {
// console.log(dateTicker.getDay())
if (dateTicker.getDay() !== 0 && dateTicker.getDay() !== 6) {
weekResult.push({
date: new Date(dateTicker),
selected: false,
recurring: false,
ordered: false,
disabled: true,
})
}

dateTicker.setDate(dateTicker.getDate() + 1)
}

while (weekResult.length % 5 !== 0) {
console.log("got here2", weekResult.length)

if (dateTicker.getDay() !== 0 && dateTicker.getDay() !== 6) {
weekResult.push({
date: new Date(dateTicker),
selected: false,
recurring: false,
ordered: false,
disabled: true,
})
}

dateTicker.setDate(dateTicker.getDate() + 1)
}

/// Overwrite with dates from props
for (const date of props.dates) {
const realIndex = weekResult.findIndex(day => {
return day.date.toISOString() === date.date.toISOString()
})

weekResult[realIndex] = date
}

return sliceIntoChunks(weekResult, 5)
}

useEffect(() => {
const newWeeks = getWeeks(props.dates)
setWeeks(newWeeks)

const idx = newWeeks.findIndex(week => {
return !!week.find(day => day.selected)
})
if (idx < newWeeks.length) {
setTimeout(() => {
// @ts-ignore
pagerRef.current!.setPage(idx)
}, 500)
}
}, [props.dates])
const pagerRef = useRef(null)

return (


{weeks.map(week => {
return (







)
})}


)
}
```

Contributor guide

Open the contributing guide

Assessment

This issue has not been assessed yet.

Get new issues in your inbox

A short digest of beginner-friendly GitHub issues.