From ea897c5c85f19abb5d217abd114409af4a634035 Mon Sep 17 00:00:00 2001 From: blue sea <1063461427@qq.com> Date: Sun, 16 Jan 2022 02:15:21 +0800 Subject: [PATCH 1/7] Update raf.ts From 0ad9e5f04b52e9770ed968fea5c97515518f5b7a Mon Sep 17 00:00:00 2001 From: blue sea <1063461427@qq.com> Date: Sun, 16 Jan 2022 09:23:35 +0800 Subject: [PATCH 2/7] refactor: support weakset --- src/raf.ts | 69 ++++++++++++++++++++++++++++++++++++++++++++++-------- 1 file changed, 59 insertions(+), 10 deletions(-) diff --git a/src/raf.ts b/src/raf.ts index 40e0ae6e..d09c8d8a 100644 --- a/src/raf.ts +++ b/src/raf.ts @@ -1,7 +1,11 @@ +const hasWin = typeof window !== 'undefined'; +const hasRaf = hasWin && typeof window.requestAnimationFrame !== 'undefined'; +const hasWeakSet = hasWin && typeof window.WeakSet !== 'undefined'; + let raf = (callback: FrameRequestCallback) => +setTimeout(callback, 16); let caf = (num: number) => clearTimeout(num); -if (typeof window !== 'undefined' && 'requestAnimationFrame' in window) { +if (hasRaf) { raf = (callback: FrameRequestCallback) => window.requestAnimationFrame(callback); caf = (handle: number) => window.cancelAnimationFrame(handle); @@ -9,19 +13,18 @@ if (typeof window !== 'undefined' && 'requestAnimationFrame' in window) { let rafUUID = 0; const rafIds = new Map(); +const rafKeys = new WeakSet(); -function cleanup(id: number) { - rafIds.delete(id); -} +const cleanupByMap = (id: number) => rafIds.delete(id); -export default function wrapperRaf(callback: () => void, times = 1): number { +const useRafByMap = (callback: () => void, times = 1): number => { rafUUID += 1; const id = rafUUID; function callRef(leftTimes: number) { if (leftTimes === 0) { // Clean up - cleanup(id); + cleanupByMap(id); // Trigger callback(); @@ -39,10 +42,56 @@ export default function wrapperRaf(callback: () => void, times = 1): number { callRef(times); return id; -} +}; -wrapperRaf.cancel = (id: number) => { - const realId = rafIds.get(id); - cleanup(realId); +useRafByMap.cancel = (key: number) => { + const realId = rafIds.get(key); + cleanupByMap(key); return caf(realId); }; + +const cleanupByWeakSet = (key: number[]) => { + const [timeId] = key || []; + let oldKey = key; + if (timeId) { + caf(timeId); + rafKeys.delete(oldKey); + const bool = !!rafKeys.has(oldKey); + oldKey = null; + return bool; + } else { + return false; + } +}; + +const useRafByWeakSet = (callback: () => void, times = 1): number => { + let key: number[]; + + function callRef(leftTimes: number) { + if (leftTimes === 0) { + // Clean up + cleanupByWeakSet(key); + + // Trigger + callback(); + } else { + // Next raf + key = [ + raf(() => { + callRef(leftTimes - 1); + }), + ]; + + // Bind real raf id + rafKeys.add(key); + } + } + + callRef(times); + + return +key; +}; + +useRafByWeakSet.cancel = (key: number[]) => cleanupByWeakSet(key); + +export const useRaf = hasWeakSet ? useRafByWeakSet : useRafByMap; From 8b5c9211e6bc89176b3496588db55bdb84763532 Mon Sep 17 00:00:00 2001 From: blue sea <1063461427@qq.com> Date: Sun, 16 Jan 2022 12:01:52 +0800 Subject: [PATCH 3/7] Update raf.ts --- src/raf.ts | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/src/raf.ts b/src/raf.ts index d09c8d8a..943d8547 100644 --- a/src/raf.ts +++ b/src/raf.ts @@ -50,9 +50,9 @@ useRafByMap.cancel = (key: number) => { return caf(realId); }; -const cleanupByWeakSet = (key: number[]) => { - const [timeId] = key || []; - let oldKey = key; +const cleanupByWeakSet = (key: number[] | number) => { + let oldKey = typeof key === "number" ? [+key] : key; + const [timeId] = oldKey || [+oldKey]; if (timeId) { caf(timeId); rafKeys.delete(oldKey); From 630aa02a6a133ac5b337a68147a0aa7d87440239 Mon Sep 17 00:00:00 2001 From: blue sea <1063461427@qq.com> Date: Sun, 16 Jan 2022 12:02:35 +0800 Subject: [PATCH 4/7] Update raf.ts --- src/raf.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/raf.ts b/src/raf.ts index 943d8547..8294c537 100644 --- a/src/raf.ts +++ b/src/raf.ts @@ -52,7 +52,7 @@ useRafByMap.cancel = (key: number) => { const cleanupByWeakSet = (key: number[] | number) => { let oldKey = typeof key === "number" ? [+key] : key; - const [timeId] = oldKey || [+oldKey]; + const [timeId] = oldKey || []; if (timeId) { caf(timeId); rafKeys.delete(oldKey); From 5c2c1bf81ffd82e12580bd490d5654dea31a9642 Mon Sep 17 00:00:00 2001 From: blue sea <1063461427@qq.com> Date: Sun, 16 Jan 2022 13:18:32 +0800 Subject: [PATCH 5/7] Update raf.ts --- src/raf.ts | 6 +----- 1 file changed, 1 insertion(+), 5 deletions(-) diff --git a/src/raf.ts b/src/raf.ts index 8294c537..9c459f47 100644 --- a/src/raf.ts +++ b/src/raf.ts @@ -54,14 +54,10 @@ const cleanupByWeakSet = (key: number[] | number) => { let oldKey = typeof key === "number" ? [+key] : key; const [timeId] = oldKey || []; if (timeId) { - caf(timeId); rafKeys.delete(oldKey); - const bool = !!rafKeys.has(oldKey); oldKey = null; - return bool; - } else { - return false; } + return timeId; }; const useRafByWeakSet = (callback: () => void, times = 1): number => { From 64050f8a7ec83bcfb09882b17a878474cc066981 Mon Sep 17 00:00:00 2001 From: blue sea <1063461427@qq.com> Date: Sun, 16 Jan 2022 13:35:18 +0800 Subject: [PATCH 6/7] Update raf.ts --- src/raf.ts | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/src/raf.ts b/src/raf.ts index 9c459f47..9e5e964c 100644 --- a/src/raf.ts +++ b/src/raf.ts @@ -50,10 +50,11 @@ useRafByMap.cancel = (key: number) => { return caf(realId); }; -const cleanupByWeakSet = (key: number[] | number) => { +const cleanupByWeakSet = (key: number[] | number): number => { let oldKey = typeof key === "number" ? [+key] : key; const [timeId] = oldKey || []; if (timeId) { + caf(timeId); rafKeys.delete(oldKey); oldKey = null; } From 4e39e7cc222d3df5a0409ed4c0f24a4e7ae04e0c Mon Sep 17 00:00:00 2001 From: blue sea <1063461427@qq.com> Date: Sun, 16 Jan 2022 13:49:10 +0800 Subject: [PATCH 7/7] Update raf.ts --- src/raf.ts | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/src/raf.ts b/src/raf.ts index 9e5e964c..533bf448 100644 --- a/src/raf.ts +++ b/src/raf.ts @@ -90,5 +90,6 @@ const useRafByWeakSet = (callback: () => void, times = 1): number => { }; useRafByWeakSet.cancel = (key: number[]) => cleanupByWeakSet(key); +const useRaf = hasWeakSet ? useRafByWeakSet : useRafByMap; -export const useRaf = hasWeakSet ? useRafByWeakSet : useRafByMap; +export default useRaf;