Skip to content

Instantly share code, notes, and snippets.

View sueLan's full-sized avatar
🎯
Focusing

RY Zheng sueLan

🎯
Focusing
View GitHub Profile
const timestamp = e.timeStamp;
let visibleLength = this._selectLength(e.nativeEvent.layoutMeasurement);
let contentLength = this._selectLength(e.nativeEvent.contentSize);
let offset = this._selectOffset(e.nativeEvent.contentOffset);
let dOffset = offset - this._scrollMetrics.offset;
// ...
this._scrollMetrics = {
contentLength,
dt,
_viewabilityTuples: Array<ViewabilityHelperCallbackTuple> = [];
/**
* Called when the viewability of rows changes, as defined by the
* `viewabilityConfig` prop.
*/
onViewableItemsChanged?: ?(info: {
viewableItems: Array<ViewToken>,
changed: Array<ViewToken>,
...
}) => void,
if (this.props.viewabilityConfigCallbackPairs) {
this._viewabilityTuples = this.props.viewabilityConfigCallbackPairs.map(
pair => ({
viewabilityHelper: new ViewabilityHelper(pair.viewabilityConfig),
onViewableItemsChanged: pair.onViewableItemsChanged,
}),
);
} else if (this.props.onViewableItemsChanged) {
this._viewabilityTuples.push({
viewabilityHelper: new ViewabilityHelper(this.props.viewabilityConfig),
type ViewabilityHelperCallbackTuple = {
viewabilityHelper: ViewabilityHelper,
onViewableItemsChanged: (info: {
viewableItems: Array<ViewToken>,
changed: Array<ViewToken>,
...
}) => void,
...
};
class ViewabilityHelper {
_config: ViewabilityConfig;
_hasInteracted: boolean = false;
/* A set of `timeoutID`, used for memory management */
_timers: Set<number> = new Set();
// Indexs of the viewable items
_viewableIndices: Array<number> = [];
// A map for viewable items
_viewableItems: Map<string, ViewToken> = new Map();
}
_updateViewableItems(data: any) {
const {getItemCount} = this.props;
this._viewabilityTuples.forEach(tuple => {
tuple.viewabilityHelper.onUpdate(
getItemCount(data),
// contentOffset of the list
this._scrollMetrics.offset,
// 🌟 viewportHeight
this._scrollMetrics.visibleLength,
// The map storing the cell layout info
{ [cellKey]: {
// offset of the item cell
offset: number,
// length of the item cell. width or height determined by the direction of the VirtualizedList
length: number,
index: number,
inLayout: boolean,
}
}
type State = {
// The range of the rendered items,
// used for the optimization to reduce the scan size
first: number,
last: number,
...
};
for (let idx = first; idx <= last; idx++) {
const metrics = getFrameMetrics(idx);
if (!metrics) {
continue;
}
// The top of current item cell, relative to the screen
const top = metrics.offset - scrollOffset;
// The bottom of current item cell
const bottom = top + metrics.length;
if (top < viewportHeight && bottom > 0) {