kinetic-slider
Version:
A WebGL-powered kinetic slider component using PIXI.js
324 lines (319 loc) • 10.9 kB
JavaScript
;
Object.defineProperty(exports, '__esModule', { value: true });
var react = require('react');
var gsap = require('gsap');
var RenderScheduler = require('../managers/RenderScheduler.cjs');
var UpdateTypes = require('../managers/UpdateTypes.cjs');
var AnimationCoordinator = require('../managers/AnimationCoordinator.cjs');
const isDevelopment = false;
const useIdleTimer = ({
sliderRef,
cursorActive,
bgDispFilterRef,
cursorDispFilterRef,
cursorImgEffect,
defaultBgFilterScale,
defaultCursorFilterScale,
idleTimeout = 300,
resourceManager
}) => {
const idleTimerRef = react.useRef(null);
const animationStateRef = react.useRef({
isAnimating: false,
activeAnimations: [],
pendingBatchAnimations: []
});
const isUnmountingRef = react.useRef(false);
const lastAnimationOpRef = react.useRef(0);
const animationCoordinator = AnimationCoordinator.AnimationCoordinator.getInstance();
react.useCallback(() => {
try {
if (isUnmountingRef.current || !resourceManager) return;
const { pendingBatchAnimations } = animationStateRef.current;
if (pendingBatchAnimations.length > 0) {
if (isDevelopment) ;
resourceManager.trackAnimationBatch(pendingBatchAnimations);
pendingBatchAnimations.length = 0;
const now = performance.now();
const opTime = now - lastAnimationOpRef.current;
if (isDevelopment && lastAnimationOpRef.current > 0) ;
lastAnimationOpRef.current = now;
}
} catch (error) {
animationStateRef.current.pendingBatchAnimations = [];
}
}, [resourceManager]);
react.useCallback((animation) => {
try {
if (isUnmountingRef.current) return animation;
animationStateRef.current.pendingBatchAnimations.push(animation);
return animation;
} catch (error) {
return animation;
}
}, []);
const createFilterAnimations = react.useCallback((targetScale, duration = 0.5, onComplete) => {
try {
if (isUnmountingRef.current) return [];
lastAnimationOpRef.current = performance.now();
if (isDevelopment) ;
const animations = [];
if (bgDispFilterRef.current) {
const actualTargetScale = targetScale === 0 ? 0 : defaultBgFilterScale;
if (targetScale > 0 && (bgDispFilterRef.current.scale.x === 0 || bgDispFilterRef.current.scale.y === 0)) {
bgDispFilterRef.current.scale.x = actualTargetScale;
bgDispFilterRef.current.scale.y = actualTargetScale;
if (isDevelopment) ;
}
const bgTween = gsap.gsap.to(bgDispFilterRef.current.scale, {
x: actualTargetScale,
y: actualTargetScale,
duration,
ease: "power2.out",
onComplete: () => {
if (resourceManager && bgDispFilterRef.current) {
resourceManager.trackFilter(bgDispFilterRef.current);
}
if (isDevelopment) ;
}
});
animations.push(bgTween);
}
if (cursorImgEffect && cursorDispFilterRef.current) {
const cursorScale = targetScale === 0 ? 0 : defaultCursorFilterScale;
if (targetScale > 0 && (cursorDispFilterRef.current.scale.x === 0 || cursorDispFilterRef.current.scale.y === 0)) {
cursorDispFilterRef.current.scale.x = cursorScale;
cursorDispFilterRef.current.scale.y = cursorScale;
if (isDevelopment) ;
}
const cursorTween = gsap.gsap.to(cursorDispFilterRef.current.scale, {
x: cursorScale,
y: cursorScale,
duration,
ease: "power2.out",
onComplete: () => {
if (resourceManager && cursorDispFilterRef.current) {
resourceManager.trackFilter(cursorDispFilterRef.current);
}
if (isDevelopment) ;
}
});
animations.push(cursorTween);
}
const groupType = targetScale === 0 ? AnimationCoordinator.AnimationGroupType.IDLE_EFFECT : AnimationCoordinator.AnimationGroupType.INTERACTION;
animationCoordinator.queueAnimationGroup({
id: `filter_animation_${Date.now()}`,
type: groupType,
animations,
onComplete
});
return animations;
} catch (error) {
if (onComplete) onComplete();
return [];
}
}, [
bgDispFilterRef,
cursorDispFilterRef,
cursorImgEffect,
defaultCursorFilterScale,
defaultBgFilterScale,
resourceManager,
animationCoordinator
]);
const resetFilters = react.useCallback(() => {
try {
if (isUnmountingRef.current) return;
if (isDevelopment) ;
if (idleTimerRef.current !== null) {
window.clearTimeout(idleTimerRef.current);
idleTimerRef.current = null;
}
if (cursorActive.current) {
if (isDevelopment) ;
return;
}
animationCoordinator.cancelAnimationsByType(AnimationCoordinator.AnimationGroupType.IDLE_EFFECT);
createFilterAnimations(0, 0.5, () => {
if (isDevelopment) ;
});
animationCoordinator.scheduleAnimationUpdate(
AnimationCoordinator.AnimationGroupType.IDLE_EFFECT,
() => {
if (isDevelopment) ;
},
"idle_reset"
);
} catch (error) {
}
}, [
cursorActive,
createFilterAnimations,
animationCoordinator
]);
const restoreFilters = react.useCallback((immediate = false) => {
try {
if (isUnmountingRef.current) return;
if (isDevelopment) ;
if (idleTimerRef.current !== null) {
window.clearTimeout(idleTimerRef.current);
idleTimerRef.current = null;
}
animationCoordinator.cancelAnimationsByType(AnimationCoordinator.AnimationGroupType.INTERACTION);
cursorActive.current = true;
if (bgDispFilterRef.current) {
const originalX = bgDispFilterRef.current.scale.x;
const originalY = bgDispFilterRef.current.scale.y;
bgDispFilterRef.current.scale.x = defaultBgFilterScale;
bgDispFilterRef.current.scale.y = defaultBgFilterScale;
if (isDevelopment) ;
}
if (cursorImgEffect && cursorDispFilterRef.current) {
const originalX = cursorDispFilterRef.current.scale.x;
const originalY = cursorDispFilterRef.current.scale.y;
cursorDispFilterRef.current.scale.x = defaultCursorFilterScale;
cursorDispFilterRef.current.scale.y = defaultCursorFilterScale;
if (isDevelopment) ;
}
RenderScheduler.RenderScheduler.getInstance().scheduleTypedUpdate(
"idleTimer",
UpdateTypes.UpdateType.DISPLACEMENT_EFFECT,
() => {
if (isDevelopment) ;
},
immediate ? "critical" : "high"
// Use critical priority for immediate restoration
);
const animationDuration = immediate ? 0.2 : 0.5;
createFilterAnimations(defaultBgFilterScale, animationDuration, () => {
if (isDevelopment) ;
});
animationCoordinator.scheduleAnimationUpdate(
AnimationCoordinator.AnimationGroupType.INTERACTION,
() => {
if (isDevelopment) ;
},
immediate ? "critical" : "high"
);
} catch (error) {
}
}, [
defaultBgFilterScale,
defaultCursorFilterScale,
bgDispFilterRef,
cursorDispFilterRef,
cursorImgEffect,
cursorActive,
createFilterAnimations,
animationCoordinator
]);
const handleMouseMove = react.useCallback(() => {
try {
if (isUnmountingRef.current) return;
if (idleTimerRef.current !== null) {
window.clearTimeout(idleTimerRef.current);
idleTimerRef.current = null;
}
if (cursorActive.current !== true) {
cursorActive.current = true;
if (isDevelopment) ;
const bgFilter2 = bgDispFilterRef.current;
const cursorFilter2 = cursorDispFilterRef.current;
if (bgFilter2) {
bgFilter2.scale.x = defaultBgFilterScale;
bgFilter2.scale.y = defaultBgFilterScale;
if (isDevelopment) ;
}
if (cursorImgEffect && cursorFilter2) {
cursorFilter2.scale.x = defaultCursorFilterScale;
cursorFilter2.scale.y = defaultCursorFilterScale;
if (isDevelopment) ;
}
RenderScheduler.RenderScheduler.getInstance().scheduleTypedUpdate(
"idleTimer",
UpdateTypes.UpdateType.DISPLACEMENT_EFFECT,
() => {
if (isDevelopment) ;
},
"critical"
// Use critical priority to ensure immediate processing
);
restoreFilters(true);
}
const bgFilter = bgDispFilterRef.current;
const cursorFilter = cursorDispFilterRef.current;
const bgFilterInactive = bgFilter && (bgFilter.scale.x === 0 || bgFilter.scale.y === 0);
const cursorFilterInactive = cursorImgEffect && cursorFilter && (cursorFilter.scale.x === 0 || cursorFilter.scale.y === 0);
if (bgFilterInactive || cursorFilterInactive) {
if (isDevelopment) ;
restoreFilters(true);
}
idleTimerRef.current = window.setTimeout(() => {
cursorActive.current = false;
if (isDevelopment) ;
resetFilters();
idleTimerRef.current = null;
}, idleTimeout);
} catch (error) {
}
}, [
cursorActive,
bgDispFilterRef,
cursorDispFilterRef,
cursorImgEffect,
defaultBgFilterScale,
defaultCursorFilterScale,
idleTimeout,
resetFilters,
restoreFilters
]);
react.useEffect(() => {
if (typeof window === "undefined") return;
if (!sliderRef.current) return;
isUnmountingRef.current = false;
try {
const node = sliderRef.current;
if (resourceManager) {
const listeners = /* @__PURE__ */ new Map();
listeners.set("mousemove", [handleMouseMove]);
resourceManager.addEventListenerBatch(node, listeners);
} else {
node.addEventListener("mousemove", handleMouseMove, { passive: true });
}
idleTimerRef.current = window.setTimeout(() => {
cursorActive.current = false;
resetFilters();
idleTimerRef.current = null;
}, idleTimeout);
return () => {
isUnmountingRef.current = true;
try {
if (idleTimerRef.current !== null) {
window.clearTimeout(idleTimerRef.current);
idleTimerRef.current = null;
}
if (!resourceManager) {
node.removeEventListener("mousemove", handleMouseMove);
}
} catch (cleanupError) {
if (isDevelopment) ;
}
};
} catch (error) {
return () => {
};
}
}, [
sliderRef,
handleMouseMove,
idleTimeout,
resetFilters,
resourceManager
]);
return {
resetFilters,
restoreFilters
};
};
exports.default = useIdleTimer;
//# sourceMappingURL=useIdleTimer.cjs.map