fetchNextPage method
void
fetchNextPage()
inherited
Fetches the next page.
If called while a page is fetching or no more pages are available, this method does nothing.
Implementation
void fetchNextPage() async {
// We are already loading a new page.
if (this.operation != null) return;
final operation = this.operation = Object();
value = value.copyWith(
isLoading: true,
error: null,
);
// we use a local copy of value,
// so that we only send one notification now and at the end of the method.
PagingState<PageKeyType, ItemType> state = value;
try {
// There are no more pages to load.
if (!state.hasNextPage) return;
final nextPageKey = _getNextPageKey(state);
// We are at the end of the list.
if (nextPageKey == null) {
state = state.copyWith(hasNextPage: false);
return;
}
final fetchResult = _fetchPage(nextPageKey);
List<ItemType> newItems;
// If the result is synchronous, we can directly assign it in the same tick.
if (fetchResult is Future) {
newItems = await fetchResult;
} else {
newItems = fetchResult;
}
// Update our state in case it was modified during the fetch operation.
// This beaks atomicity, but is necessary to allow users to modify the state during a fetch.
state = value;
state = state.copyWith(
pages: [...?state.pages, newItems],
keys: [...?state.keys, nextPageKey],
);
} catch (error) {
state = state.copyWith(error: error);
if (error is! Exception) {
// Errors which are not exceptions indicate that something
// went unexpectedly wrong. These errors are rethrown
// so they can be logged and investigated.
rethrow;
}
} finally {
if (operation == this.operation) {
value = state.copyWith(isLoading: false);
this.operation = null;
}
}
}