react-native-worklets
Version:
The React Native multithreading library
62 lines (47 loc) • 1.58 kB
text/typescript
;
export function setupRequestAnimationFrame(animationQueuePollingRate: number) {
'worklet';
const timeoutInterval = animationQueuePollingRate;
let queuedCallbacks: ((timestamp: number) => void)[] = [];
let queuedCallbacksBegin = 0;
let queuedCallbacksEnd = 0;
let flushedCallbacks = queuedCallbacks;
let flushedCallbacksBegin = 0;
let flushedCallbacksEnd = 0;
let flushRequested = false;
function flushAnimationFrame() {
flushRequested = false;
const timestamp = performance.now();
flushedCallbacks = queuedCallbacks;
queuedCallbacks = [];
flushedCallbacksBegin = queuedCallbacksBegin;
flushedCallbacksEnd = queuedCallbacksEnd;
queuedCallbacksBegin = queuedCallbacksEnd;
for (const callback of flushedCallbacks) {
callback(timestamp);
globalThis.__flushMicrotasks();
}
flushedCallbacksBegin = flushedCallbacksEnd;
}
globalThis.requestAnimationFrame = (
callback: (timestamp: number) => void
): number => {
const handle = queuedCallbacksEnd++;
queuedCallbacks.push(callback);
if (!flushRequested) {
flushRequested = true;
setTimeout(flushAnimationFrame, timeoutInterval);
}
return handle;
};
globalThis.cancelAnimationFrame = (handle: number) => {
if (handle < flushedCallbacksBegin || handle >= queuedCallbacksEnd) {
return;
}
if (handle < flushedCallbacksEnd) {
flushedCallbacks[handle - flushedCallbacksBegin] = () => {};
} else {
queuedCallbacks[handle - queuedCallbacksBegin] = () => {};
}
};
}