scroll.ts 1.1 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950
  1. const easingOutQuint = (
  2. x: number,
  3. t: number,
  4. b: number,
  5. c: number,
  6. d: number,
  7. ) => c * ((t = t / d - 1) * t * t * t * t + 1) + b;
  8. const scroll = (
  9. node: Element,
  10. key: 'scrollTop' | 'scrollLeft',
  11. target: number,
  12. ) => {
  13. const startTime = Date.now();
  14. const offset = node[key];
  15. const gap = target - offset;
  16. const duration = 1000;
  17. let interrupt = false;
  18. const step = () => {
  19. const elapsed = Date.now() - startTime;
  20. const percentage = elapsed / duration;
  21. if (percentage > 1 || interrupt) {
  22. return;
  23. }
  24. node[key] = easingOutQuint(0, elapsed, offset, gap, duration);
  25. requestAnimationFrame(step);
  26. };
  27. step();
  28. return () => {
  29. interrupt = true;
  30. };
  31. };
  32. const isScrollBehaviorSupported =
  33. 'scrollBehavior' in document.documentElement.style;
  34. export const scrollRight = (node: Element, position: number) => {
  35. if (isScrollBehaviorSupported)
  36. node.scrollTo({ left: position, behavior: 'smooth' });
  37. else scroll(node, 'scrollLeft', position);
  38. };
  39. export const scrollTop = (node: Element) => {
  40. if (isScrollBehaviorSupported) node.scrollTo({ top: 0, behavior: 'smooth' });
  41. else scroll(node, 'scrollTop', 0);
  42. };