tiny-essentials 1.17.0 → 1.17.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/v1/TinyBasicsEs.js +172 -24
- package/dist/v1/TinyBasicsEs.min.js +1 -1
- package/dist/v1/TinyDragger.js +172 -24
- package/dist/v1/TinyDragger.min.js +1 -1
- package/dist/v1/TinyEssentials.js +172 -24
- package/dist/v1/TinyEssentials.min.js +1 -1
- package/dist/v1/TinyHtml.js +172 -24
- package/dist/v1/TinyHtml.min.js +1 -1
- package/dist/v1/TinySmartScroller.js +172 -24
- package/dist/v1/TinySmartScroller.min.js +1 -1
- package/dist/v1/TinyUploadClicker.js +172 -24
- package/dist/v1/TinyUploadClicker.min.js +1 -1
- package/dist/v1/libs/TinyHtml.cjs +172 -24
- package/dist/v1/libs/TinyHtml.d.mts +88 -0
- package/dist/v1/libs/TinyHtml.mjs +162 -27
- package/docs/v1/libs/TinyHtml.md +99 -0
- package/package.json +1 -1
|
@@ -11,6 +11,19 @@ const {
|
|
|
11
11
|
areElsCollRight,
|
|
12
12
|
} = collision;
|
|
13
13
|
|
|
14
|
+
/**
|
|
15
|
+
* Callback invoked on each animation frame with the current scroll position,
|
|
16
|
+
* normalized animation time (`0` to `1`), and a completion flag.
|
|
17
|
+
*
|
|
18
|
+
* @typedef {(progress: { x: number, y: number, isComplete: boolean, time: number }) => void} OnScrollAnimation
|
|
19
|
+
*/
|
|
20
|
+
|
|
21
|
+
/**
|
|
22
|
+
* A list of supported easing function names for smooth animations.
|
|
23
|
+
*
|
|
24
|
+
* @typedef {'linear' | 'easeInQuad' | 'easeOutQuad' | 'easeInOutQuad' | 'easeInCubic' | 'easeOutCubic' | 'easeInOutCubic'} Easings
|
|
25
|
+
*/
|
|
26
|
+
|
|
14
27
|
/**
|
|
15
28
|
* Represents a raw Node element or an instance of TinyHtml.
|
|
16
29
|
* This type is used to abstract interactions with both plain elements
|
|
@@ -2419,7 +2432,7 @@ class TinyHtml {
|
|
|
2419
2432
|
*/
|
|
2420
2433
|
static setWinScrollTop(value) {
|
|
2421
2434
|
if (typeof value !== 'number') throw new TypeError('The value must be a number.');
|
|
2422
|
-
|
|
2435
|
+
TinyHtml.setScrollTop(window, value);
|
|
2423
2436
|
}
|
|
2424
2437
|
|
|
2425
2438
|
/**
|
|
@@ -2428,7 +2441,7 @@ class TinyHtml {
|
|
|
2428
2441
|
*/
|
|
2429
2442
|
static setWinScrollLeft(value) {
|
|
2430
2443
|
if (typeof value !== 'number') throw new TypeError('The value must be a number.');
|
|
2431
|
-
|
|
2444
|
+
TinyHtml.setScrollLeft(window, value);
|
|
2432
2445
|
}
|
|
2433
2446
|
|
|
2434
2447
|
/**
|
|
@@ -2745,6 +2758,30 @@ class TinyHtml {
|
|
|
2745
2758
|
|
|
2746
2759
|
//////////////////////////////////////////////////
|
|
2747
2760
|
|
|
2761
|
+
/**
|
|
2762
|
+
* Applies an animation to one or multiple TinyElement instances.
|
|
2763
|
+
*
|
|
2764
|
+
* @param {TinyElement|TinyElement[]} el - A single TinyElement or an array of TinyElements to animate.
|
|
2765
|
+
* @param {Keyframe[] | PropertyIndexedKeyframes | null} keyframes - The keyframes used to define the animation.
|
|
2766
|
+
* @param {number | KeyframeAnimationOptions} [ops] - Timing or configuration options for the animation.
|
|
2767
|
+
* @returns {TinyElement|TinyElement[]}
|
|
2768
|
+
*/
|
|
2769
|
+
static animate(el, keyframes, ops) {
|
|
2770
|
+
TinyHtml._preElems(el, 'animate').forEach((elem) => elem.animate(keyframes, ops));
|
|
2771
|
+
return el;
|
|
2772
|
+
}
|
|
2773
|
+
|
|
2774
|
+
/**
|
|
2775
|
+
* Applies an animation to one or multiple TinyElement instances.
|
|
2776
|
+
*
|
|
2777
|
+
* @param {Keyframe[] | PropertyIndexedKeyframes | null} keyframes - The keyframes used to define the animation.
|
|
2778
|
+
* @param {number | KeyframeAnimationOptions} [ops] - Timing or configuration options for the animation.
|
|
2779
|
+
* @returns {TinyElement|TinyElement[]}
|
|
2780
|
+
*/
|
|
2781
|
+
animate(keyframes, ops) {
|
|
2782
|
+
return TinyHtml.animate(this, keyframes, ops);
|
|
2783
|
+
}
|
|
2784
|
+
|
|
2748
2785
|
/**
|
|
2749
2786
|
* Gets the offset of the element relative to the document.
|
|
2750
2787
|
* @param {TinyElement} el - Target element.
|
|
@@ -2900,26 +2937,147 @@ class TinyHtml {
|
|
|
2900
2937
|
}
|
|
2901
2938
|
|
|
2902
2939
|
/**
|
|
2903
|
-
*
|
|
2904
|
-
*
|
|
2905
|
-
*
|
|
2906
|
-
* @
|
|
2940
|
+
* Collection of easing functions used for scroll and animation calculations.
|
|
2941
|
+
* Each function receives a normalized time value (`t` from 0 to 1) and returns the eased progress.
|
|
2942
|
+
*
|
|
2943
|
+
* @type {Record<string, (t: number) => number>}
|
|
2907
2944
|
*/
|
|
2908
|
-
static
|
|
2909
|
-
|
|
2910
|
-
|
|
2911
|
-
|
|
2912
|
-
|
|
2945
|
+
static easings = {
|
|
2946
|
+
linear: (t) => t,
|
|
2947
|
+
easeInQuad: (t) => t * t,
|
|
2948
|
+
easeOutQuad: (t) => t * (2 - t),
|
|
2949
|
+
easeInOutQuad: (t) => (t < 0.5 ? 2 * t * t : -1 + (4 - 2 * t) * t),
|
|
2950
|
+
easeInCubic: (t) => t * t * t,
|
|
2951
|
+
easeOutCubic: (t) => --t * t * t + 1,
|
|
2952
|
+
easeInOutCubic: (t) => (t < 0.5 ? 4 * t * t * t : (t - 1) * (2 * t - 2) * (2 * t - 2) + 1),
|
|
2953
|
+
};
|
|
2954
|
+
|
|
2955
|
+
/**
|
|
2956
|
+
* Smoothly scrolls one or more elements (or the window) to the specified X and Y coordinates
|
|
2957
|
+
* using a custom duration and easing function.
|
|
2958
|
+
*
|
|
2959
|
+
* If `duration` or a valid `easing` is not provided, the scroll will be performed immediately.
|
|
2960
|
+
*
|
|
2961
|
+
* @param {TinyElementAndWindow | TinyElementAndWindow[]} el - A single element, array of elements, or the window to scroll.
|
|
2962
|
+
* @param {Object} [settings={}] - Configuration object for the scroll animation.
|
|
2963
|
+
* @param {number} [settings.targetX] - The horizontal scroll target in pixels.
|
|
2964
|
+
* @param {number} [settings.targetY] - The vertical scroll target in pixels.
|
|
2965
|
+
* @param {number} [settings.duration] - The duration of the animation in milliseconds.
|
|
2966
|
+
* @param {Easings} [settings.easing] - The easing function name to use for the scroll animation.
|
|
2967
|
+
* @param {OnScrollAnimation} [settings.onAnimation] - Optional callback invoked on each animation
|
|
2968
|
+
* frame with the current scroll position, normalized animation time (`0` to `1`), and a completion flag.
|
|
2969
|
+
* @returns {TinyElementAndWindow|TinyElementAndWindow[]}
|
|
2970
|
+
* @throws {TypeError} If `el` is not a valid element, array, or window.
|
|
2971
|
+
* @throws {TypeError} If `targetX` or `targetY` is defined but not a number.
|
|
2972
|
+
* @throws {TypeError} If `duration` is defined but not a number.
|
|
2973
|
+
* @throws {TypeError} If `easing` is defined but not a valid easing function name.
|
|
2974
|
+
* @throws {TypeError} If `onAnimation` is defined but not a function.
|
|
2975
|
+
*/
|
|
2976
|
+
static scrollToXY(el, { targetX, targetY, duration, easing, onAnimation } = {}) {
|
|
2977
|
+
if (targetX !== undefined && typeof targetX !== 'number')
|
|
2978
|
+
throw new TypeError('`targetX` must be a number if provided.');
|
|
2979
|
+
if (targetY !== undefined && typeof targetY !== 'number')
|
|
2980
|
+
throw new TypeError('`targetY` must be a number if provided.');
|
|
2981
|
+
if (duration !== undefined && typeof duration !== 'number')
|
|
2982
|
+
throw new TypeError('`duration` must be a number if provided.');
|
|
2983
|
+
if (easing !== undefined && typeof easing !== 'string')
|
|
2984
|
+
throw new TypeError('`easing` must be a string if provided.');
|
|
2985
|
+
if (easing !== undefined && typeof TinyHtml.easings[easing] !== 'function')
|
|
2986
|
+
throw new TypeError(`Unknown easing function: "${easing}".`);
|
|
2987
|
+
if (onAnimation !== undefined && typeof onAnimation !== 'function')
|
|
2988
|
+
throw new TypeError('`onAnimation` must be a function if provided.');
|
|
2989
|
+
|
|
2990
|
+
/**
|
|
2991
|
+
* Performs an instant scroll to the given coordinates.
|
|
2992
|
+
*
|
|
2993
|
+
* @param {ElementAndWindow} elem - The element or window to scroll.
|
|
2994
|
+
* @param {number} newX - The final horizontal scroll position.
|
|
2995
|
+
* @param {number} newY - The final vertical scroll position.
|
|
2996
|
+
* @param {number} time - Normalized progress value.
|
|
2997
|
+
*/
|
|
2998
|
+
const executeScroll = (elem, newX, newY, time) => {
|
|
2999
|
+
if (elem instanceof Window) {
|
|
3000
|
+
window.scrollTo(newX, newY);
|
|
2913
3001
|
} else if (elem.nodeType === 9) {
|
|
2914
3002
|
// @ts-ignore
|
|
2915
|
-
elem.defaultView.scrollTo(
|
|
3003
|
+
elem.defaultView.scrollTo(newX, newY);
|
|
2916
3004
|
} else {
|
|
2917
|
-
elem.
|
|
3005
|
+
const startX = elem instanceof Window ? window.scrollX : elem.scrollLeft;
|
|
3006
|
+
const startY = elem instanceof Window ? window.scrollY : elem.scrollTop;
|
|
3007
|
+
if (startX !== newX) elem.scrollLeft = newX;
|
|
3008
|
+
if (startY !== newY) elem.scrollTop = newY;
|
|
3009
|
+
}
|
|
3010
|
+
if (typeof onAnimation === 'function')
|
|
3011
|
+
onAnimation({ x: newX, y: newY, isComplete: time >= 1, time });
|
|
3012
|
+
};
|
|
3013
|
+
|
|
3014
|
+
TinyHtml._preElemsAndWindow(el, 'scrollToXY').forEach((elem) => {
|
|
3015
|
+
const startX = elem instanceof Window ? window.scrollX : elem.scrollLeft;
|
|
3016
|
+
const startY = elem instanceof Window ? window.scrollY : elem.scrollTop;
|
|
3017
|
+
const targX = targetX ?? startX;
|
|
3018
|
+
const targY = targetY ?? startY;
|
|
3019
|
+
|
|
3020
|
+
const changeX = targX - startX;
|
|
3021
|
+
const changeY = targY - startY;
|
|
3022
|
+
|
|
3023
|
+
const ease = (typeof easing === 'string' && TinyHtml.easings[easing]) || null;
|
|
3024
|
+
if (typeof duration !== 'number' || typeof ease !== 'function')
|
|
3025
|
+
return executeScroll(elem, targX, targY, 1);
|
|
3026
|
+
const startTime = performance.now();
|
|
3027
|
+
const dur = duration ?? 0;
|
|
3028
|
+
|
|
3029
|
+
/**
|
|
3030
|
+
* Animates the scroll position based on easing and time.
|
|
3031
|
+
*
|
|
3032
|
+
* @param {number} currentTime - Timestamp provided by requestAnimationFrame.
|
|
3033
|
+
*/
|
|
3034
|
+
function animateScroll(currentTime) {
|
|
3035
|
+
if (typeof ease !== 'function') return;
|
|
3036
|
+
const time = Math.min(1, (currentTime - startTime) / dur);
|
|
3037
|
+
const easedTime = ease(time);
|
|
3038
|
+
|
|
3039
|
+
const newX = startX + changeX * easedTime;
|
|
3040
|
+
const newY = startY + changeY * easedTime;
|
|
3041
|
+
executeScroll(elem, newX, newY, time);
|
|
3042
|
+
|
|
3043
|
+
if (time < 1) requestAnimationFrame(animateScroll);
|
|
2918
3044
|
}
|
|
3045
|
+
|
|
3046
|
+
requestAnimationFrame(animateScroll);
|
|
2919
3047
|
});
|
|
2920
3048
|
return el;
|
|
2921
3049
|
}
|
|
2922
3050
|
|
|
3051
|
+
/**
|
|
3052
|
+
* Smoothly scrolls one or more elements (or the window) to the specified X and Y coordinates
|
|
3053
|
+
* using a custom duration and easing function.
|
|
3054
|
+
*
|
|
3055
|
+
* If `duration` or a valid `easing` is not provided, the scroll will be performed immediately.
|
|
3056
|
+
*
|
|
3057
|
+
* @param {Object} [settings={}] - Configuration object for the scroll animation.
|
|
3058
|
+
* @param {number} [settings.targetX] - The horizontal scroll target in pixels.
|
|
3059
|
+
* @param {number} [settings.targetY] - The vertical scroll target in pixels.
|
|
3060
|
+
* @param {number} [settings.duration] - The duration of the animation in milliseconds.
|
|
3061
|
+
* @param {Easings} [settings.easing] - The easing function name to use for the scroll animation.
|
|
3062
|
+
* @param {OnScrollAnimation} [settings.onAnimation] - Optional callback invoked on each animation
|
|
3063
|
+
* frame with the current scroll position, normalized animation time (`0` to `1`), and a completion flag.
|
|
3064
|
+
* @returns {TinyElementAndWindow|TinyElementAndWindow[]}
|
|
3065
|
+
*/
|
|
3066
|
+
scrollToXY({ targetX, targetY, duration, easing, onAnimation } = {}) {
|
|
3067
|
+
return TinyHtml.scrollToXY(this, { targetX, targetY, duration, easing, onAnimation });
|
|
3068
|
+
}
|
|
3069
|
+
|
|
3070
|
+
/**
|
|
3071
|
+
* Sets the vertical scroll position.
|
|
3072
|
+
* @param {TinyElementAndWindow|TinyElementAndWindow[]} el - Element or window.
|
|
3073
|
+
* @param {number} value - Scroll top value.
|
|
3074
|
+
* @returns {TinyElementAndWindow|TinyElementAndWindow[]}
|
|
3075
|
+
*/
|
|
3076
|
+
static setScrollTop(el, value) {
|
|
3077
|
+
if (typeof value !== 'number') throw new TypeError('ScrollTop value must be a number.');
|
|
3078
|
+
return TinyHtml.scrollToXY(el, { targetY: value });
|
|
3079
|
+
}
|
|
3080
|
+
|
|
2923
3081
|
/**
|
|
2924
3082
|
* Sets the vertical scroll position.
|
|
2925
3083
|
* @param {number} value - Scroll top value.
|
|
@@ -2937,17 +3095,7 @@ class TinyHtml {
|
|
|
2937
3095
|
*/
|
|
2938
3096
|
static setScrollLeft(el, value) {
|
|
2939
3097
|
if (typeof value !== 'number') throw new TypeError('ScrollLeft value must be a number.');
|
|
2940
|
-
TinyHtml.
|
|
2941
|
-
if (TinyHtml.isWindow(elem)) {
|
|
2942
|
-
elem.scrollTo(value, elem.pageYOffset);
|
|
2943
|
-
} else if (elem.nodeType === 9) {
|
|
2944
|
-
// @ts-ignore
|
|
2945
|
-
elem.defaultView.scrollTo(value, elem.defaultView.pageYOffset);
|
|
2946
|
-
} else {
|
|
2947
|
-
elem.scrollLeft = value;
|
|
2948
|
-
}
|
|
2949
|
-
});
|
|
2950
|
-
return el;
|
|
3098
|
+
return TinyHtml.scrollToXY(el, { targetX: value });
|
|
2951
3099
|
}
|
|
2952
3100
|
|
|
2953
3101
|
/**
|
|
@@ -1,4 +1,18 @@
|
|
|
1
1
|
export default TinyHtml;
|
|
2
|
+
/**
|
|
3
|
+
* Callback invoked on each animation frame with the current scroll position,
|
|
4
|
+
* normalized animation time (`0` to `1`), and a completion flag.
|
|
5
|
+
*/
|
|
6
|
+
export type OnScrollAnimation = (progress: {
|
|
7
|
+
x: number;
|
|
8
|
+
y: number;
|
|
9
|
+
isComplete: boolean;
|
|
10
|
+
time: number;
|
|
11
|
+
}) => void;
|
|
12
|
+
/**
|
|
13
|
+
* A list of supported easing function names for smooth animations.
|
|
14
|
+
*/
|
|
15
|
+
export type Easings = "linear" | "easeInQuad" | "easeOutQuad" | "easeInOutQuad" | "easeInCubic" | "easeOutCubic" | "easeInOutCubic";
|
|
2
16
|
/**
|
|
3
17
|
* Represents a raw Node element or an instance of TinyHtml.
|
|
4
18
|
* This type is used to abstract interactions with both plain elements
|
|
@@ -1084,6 +1098,15 @@ declare class TinyHtml {
|
|
|
1084
1098
|
* @returns {number}
|
|
1085
1099
|
*/
|
|
1086
1100
|
static outerWidth(el: TinyElementAndWinAndDoc, includeMargin?: boolean): number;
|
|
1101
|
+
/**
|
|
1102
|
+
* Applies an animation to one or multiple TinyElement instances.
|
|
1103
|
+
*
|
|
1104
|
+
* @param {TinyElement|TinyElement[]} el - A single TinyElement or an array of TinyElements to animate.
|
|
1105
|
+
* @param {Keyframe[] | PropertyIndexedKeyframes | null} keyframes - The keyframes used to define the animation.
|
|
1106
|
+
* @param {number | KeyframeAnimationOptions} [ops] - Timing or configuration options for the animation.
|
|
1107
|
+
* @returns {TinyElement|TinyElement[]}
|
|
1108
|
+
*/
|
|
1109
|
+
static animate(el: TinyElement | TinyElement[], keyframes: Keyframe[] | PropertyIndexedKeyframes | null, ops?: number | KeyframeAnimationOptions): TinyElement | TinyElement[];
|
|
1087
1110
|
/**
|
|
1088
1111
|
* Gets the offset of the element relative to the document.
|
|
1089
1112
|
* @param {TinyElement} el - Target element.
|
|
@@ -1120,6 +1143,41 @@ declare class TinyHtml {
|
|
|
1120
1143
|
* @returns {number}
|
|
1121
1144
|
*/
|
|
1122
1145
|
static scrollLeft(el: TinyElementAndWindow): number;
|
|
1146
|
+
/**
|
|
1147
|
+
* Collection of easing functions used for scroll and animation calculations.
|
|
1148
|
+
* Each function receives a normalized time value (`t` from 0 to 1) and returns the eased progress.
|
|
1149
|
+
*
|
|
1150
|
+
* @type {Record<string, (t: number) => number>}
|
|
1151
|
+
*/
|
|
1152
|
+
static easings: Record<string, (t: number) => number>;
|
|
1153
|
+
/**
|
|
1154
|
+
* Smoothly scrolls one or more elements (or the window) to the specified X and Y coordinates
|
|
1155
|
+
* using a custom duration and easing function.
|
|
1156
|
+
*
|
|
1157
|
+
* If `duration` or a valid `easing` is not provided, the scroll will be performed immediately.
|
|
1158
|
+
*
|
|
1159
|
+
* @param {TinyElementAndWindow | TinyElementAndWindow[]} el - A single element, array of elements, or the window to scroll.
|
|
1160
|
+
* @param {Object} [settings={}] - Configuration object for the scroll animation.
|
|
1161
|
+
* @param {number} [settings.targetX] - The horizontal scroll target in pixels.
|
|
1162
|
+
* @param {number} [settings.targetY] - The vertical scroll target in pixels.
|
|
1163
|
+
* @param {number} [settings.duration] - The duration of the animation in milliseconds.
|
|
1164
|
+
* @param {Easings} [settings.easing] - The easing function name to use for the scroll animation.
|
|
1165
|
+
* @param {OnScrollAnimation} [settings.onAnimation] - Optional callback invoked on each animation
|
|
1166
|
+
* frame with the current scroll position, normalized animation time (`0` to `1`), and a completion flag.
|
|
1167
|
+
* @returns {TinyElementAndWindow|TinyElementAndWindow[]}
|
|
1168
|
+
* @throws {TypeError} If `el` is not a valid element, array, or window.
|
|
1169
|
+
* @throws {TypeError} If `targetX` or `targetY` is defined but not a number.
|
|
1170
|
+
* @throws {TypeError} If `duration` is defined but not a number.
|
|
1171
|
+
* @throws {TypeError} If `easing` is defined but not a valid easing function name.
|
|
1172
|
+
* @throws {TypeError} If `onAnimation` is defined but not a function.
|
|
1173
|
+
*/
|
|
1174
|
+
static scrollToXY(el: TinyElementAndWindow | TinyElementAndWindow[], { targetX, targetY, duration, easing, onAnimation }?: {
|
|
1175
|
+
targetX?: number | undefined;
|
|
1176
|
+
targetY?: number | undefined;
|
|
1177
|
+
duration?: number | undefined;
|
|
1178
|
+
easing?: Easings | undefined;
|
|
1179
|
+
onAnimation?: OnScrollAnimation | undefined;
|
|
1180
|
+
}): TinyElementAndWindow | TinyElementAndWindow[];
|
|
1123
1181
|
/**
|
|
1124
1182
|
* Sets the vertical scroll position.
|
|
1125
1183
|
* @param {TinyElementAndWindow|TinyElementAndWindow[]} el - Element or window.
|
|
@@ -2093,6 +2151,14 @@ declare class TinyHtml {
|
|
|
2093
2151
|
* @returns {number}
|
|
2094
2152
|
*/
|
|
2095
2153
|
outerWidth(includeMargin?: boolean): number;
|
|
2154
|
+
/**
|
|
2155
|
+
* Applies an animation to one or multiple TinyElement instances.
|
|
2156
|
+
*
|
|
2157
|
+
* @param {Keyframe[] | PropertyIndexedKeyframes | null} keyframes - The keyframes used to define the animation.
|
|
2158
|
+
* @param {number | KeyframeAnimationOptions} [ops] - Timing or configuration options for the animation.
|
|
2159
|
+
* @returns {TinyElement|TinyElement[]}
|
|
2160
|
+
*/
|
|
2161
|
+
animate(keyframes: Keyframe[] | PropertyIndexedKeyframes | null, ops?: number | KeyframeAnimationOptions): TinyElement | TinyElement[];
|
|
2096
2162
|
/**
|
|
2097
2163
|
* Gets the offset of the element relative to the document.
|
|
2098
2164
|
* @returns {{top: number, left: number}}
|
|
@@ -2124,6 +2190,28 @@ declare class TinyHtml {
|
|
|
2124
2190
|
* @returns {number}
|
|
2125
2191
|
*/
|
|
2126
2192
|
scrollLeft(): number;
|
|
2193
|
+
/**
|
|
2194
|
+
* Smoothly scrolls one or more elements (or the window) to the specified X and Y coordinates
|
|
2195
|
+
* using a custom duration and easing function.
|
|
2196
|
+
*
|
|
2197
|
+
* If `duration` or a valid `easing` is not provided, the scroll will be performed immediately.
|
|
2198
|
+
*
|
|
2199
|
+
* @param {Object} [settings={}] - Configuration object for the scroll animation.
|
|
2200
|
+
* @param {number} [settings.targetX] - The horizontal scroll target in pixels.
|
|
2201
|
+
* @param {number} [settings.targetY] - The vertical scroll target in pixels.
|
|
2202
|
+
* @param {number} [settings.duration] - The duration of the animation in milliseconds.
|
|
2203
|
+
* @param {Easings} [settings.easing] - The easing function name to use for the scroll animation.
|
|
2204
|
+
* @param {OnScrollAnimation} [settings.onAnimation] - Optional callback invoked on each animation
|
|
2205
|
+
* frame with the current scroll position, normalized animation time (`0` to `1`), and a completion flag.
|
|
2206
|
+
* @returns {TinyElementAndWindow|TinyElementAndWindow[]}
|
|
2207
|
+
*/
|
|
2208
|
+
scrollToXY({ targetX, targetY, duration, easing, onAnimation }?: {
|
|
2209
|
+
targetX?: number | undefined;
|
|
2210
|
+
targetY?: number | undefined;
|
|
2211
|
+
duration?: number | undefined;
|
|
2212
|
+
easing?: Easings | undefined;
|
|
2213
|
+
onAnimation?: OnScrollAnimation | undefined;
|
|
2214
|
+
}): TinyElementAndWindow | TinyElementAndWindow[];
|
|
2127
2215
|
/**
|
|
2128
2216
|
* Sets the vertical scroll position.
|
|
2129
2217
|
* @param {number} value - Scroll top value.
|
|
@@ -1,5 +1,16 @@
|
|
|
1
1
|
import * as TinyCollision from '../basics/collision.mjs';
|
|
2
2
|
const { areElsColliding, areElsPerfColliding, areElsCollTop, areElsCollBottom, areElsCollLeft, areElsCollRight, } = TinyCollision;
|
|
3
|
+
/**
|
|
4
|
+
* Callback invoked on each animation frame with the current scroll position,
|
|
5
|
+
* normalized animation time (`0` to `1`), and a completion flag.
|
|
6
|
+
*
|
|
7
|
+
* @typedef {(progress: { x: number, y: number, isComplete: boolean, time: number }) => void} OnScrollAnimation
|
|
8
|
+
*/
|
|
9
|
+
/**
|
|
10
|
+
* A list of supported easing function names for smooth animations.
|
|
11
|
+
*
|
|
12
|
+
* @typedef {'linear' | 'easeInQuad' | 'easeOutQuad' | 'easeInOutQuad' | 'easeInCubic' | 'easeOutCubic' | 'easeInOutCubic'} Easings
|
|
13
|
+
*/
|
|
3
14
|
/**
|
|
4
15
|
* Represents a raw Node element or an instance of TinyHtml.
|
|
5
16
|
* This type is used to abstract interactions with both plain elements
|
|
@@ -2179,7 +2190,7 @@ class TinyHtml {
|
|
|
2179
2190
|
static setWinScrollTop(value) {
|
|
2180
2191
|
if (typeof value !== 'number')
|
|
2181
2192
|
throw new TypeError('The value must be a number.');
|
|
2182
|
-
|
|
2193
|
+
TinyHtml.setScrollTop(window, value);
|
|
2183
2194
|
}
|
|
2184
2195
|
/**
|
|
2185
2196
|
* Sets the horizontal scroll position of the window.
|
|
@@ -2188,7 +2199,7 @@ class TinyHtml {
|
|
|
2188
2199
|
static setWinScrollLeft(value) {
|
|
2189
2200
|
if (typeof value !== 'number')
|
|
2190
2201
|
throw new TypeError('The value must be a number.');
|
|
2191
|
-
|
|
2202
|
+
TinyHtml.setScrollLeft(window, value);
|
|
2192
2203
|
}
|
|
2193
2204
|
/**
|
|
2194
2205
|
* Gets the vertical scroll position of the window.
|
|
@@ -2464,6 +2475,28 @@ class TinyHtml {
|
|
|
2464
2475
|
return TinyHtml.outerWidth(this, includeMargin);
|
|
2465
2476
|
}
|
|
2466
2477
|
//////////////////////////////////////////////////
|
|
2478
|
+
/**
|
|
2479
|
+
* Applies an animation to one or multiple TinyElement instances.
|
|
2480
|
+
*
|
|
2481
|
+
* @param {TinyElement|TinyElement[]} el - A single TinyElement or an array of TinyElements to animate.
|
|
2482
|
+
* @param {Keyframe[] | PropertyIndexedKeyframes | null} keyframes - The keyframes used to define the animation.
|
|
2483
|
+
* @param {number | KeyframeAnimationOptions} [ops] - Timing or configuration options for the animation.
|
|
2484
|
+
* @returns {TinyElement|TinyElement[]}
|
|
2485
|
+
*/
|
|
2486
|
+
static animate(el, keyframes, ops) {
|
|
2487
|
+
TinyHtml._preElems(el, 'animate').forEach((elem) => elem.animate(keyframes, ops));
|
|
2488
|
+
return el;
|
|
2489
|
+
}
|
|
2490
|
+
/**
|
|
2491
|
+
* Applies an animation to one or multiple TinyElement instances.
|
|
2492
|
+
*
|
|
2493
|
+
* @param {Keyframe[] | PropertyIndexedKeyframes | null} keyframes - The keyframes used to define the animation.
|
|
2494
|
+
* @param {number | KeyframeAnimationOptions} [ops] - Timing or configuration options for the animation.
|
|
2495
|
+
* @returns {TinyElement|TinyElement[]}
|
|
2496
|
+
*/
|
|
2497
|
+
animate(keyframes, ops) {
|
|
2498
|
+
return TinyHtml.animate(this, keyframes, ops);
|
|
2499
|
+
}
|
|
2467
2500
|
/**
|
|
2468
2501
|
* Gets the offset of the element relative to the document.
|
|
2469
2502
|
* @param {TinyElement} el - Target element.
|
|
@@ -2598,28 +2631,142 @@ class TinyHtml {
|
|
|
2598
2631
|
return TinyHtml.scrollLeft(this);
|
|
2599
2632
|
}
|
|
2600
2633
|
/**
|
|
2601
|
-
*
|
|
2602
|
-
*
|
|
2603
|
-
*
|
|
2604
|
-
* @
|
|
2634
|
+
* Collection of easing functions used for scroll and animation calculations.
|
|
2635
|
+
* Each function receives a normalized time value (`t` from 0 to 1) and returns the eased progress.
|
|
2636
|
+
*
|
|
2637
|
+
* @type {Record<string, (t: number) => number>}
|
|
2605
2638
|
*/
|
|
2606
|
-
static
|
|
2607
|
-
|
|
2608
|
-
|
|
2609
|
-
|
|
2610
|
-
|
|
2611
|
-
|
|
2639
|
+
static easings = {
|
|
2640
|
+
linear: (t) => t,
|
|
2641
|
+
easeInQuad: (t) => t * t,
|
|
2642
|
+
easeOutQuad: (t) => t * (2 - t),
|
|
2643
|
+
easeInOutQuad: (t) => (t < 0.5 ? 2 * t * t : -1 + (4 - 2 * t) * t),
|
|
2644
|
+
easeInCubic: (t) => t * t * t,
|
|
2645
|
+
easeOutCubic: (t) => --t * t * t + 1,
|
|
2646
|
+
easeInOutCubic: (t) => (t < 0.5 ? 4 * t * t * t : (t - 1) * (2 * t - 2) * (2 * t - 2) + 1),
|
|
2647
|
+
};
|
|
2648
|
+
/**
|
|
2649
|
+
* Smoothly scrolls one or more elements (or the window) to the specified X and Y coordinates
|
|
2650
|
+
* using a custom duration and easing function.
|
|
2651
|
+
*
|
|
2652
|
+
* If `duration` or a valid `easing` is not provided, the scroll will be performed immediately.
|
|
2653
|
+
*
|
|
2654
|
+
* @param {TinyElementAndWindow | TinyElementAndWindow[]} el - A single element, array of elements, or the window to scroll.
|
|
2655
|
+
* @param {Object} [settings={}] - Configuration object for the scroll animation.
|
|
2656
|
+
* @param {number} [settings.targetX] - The horizontal scroll target in pixels.
|
|
2657
|
+
* @param {number} [settings.targetY] - The vertical scroll target in pixels.
|
|
2658
|
+
* @param {number} [settings.duration] - The duration of the animation in milliseconds.
|
|
2659
|
+
* @param {Easings} [settings.easing] - The easing function name to use for the scroll animation.
|
|
2660
|
+
* @param {OnScrollAnimation} [settings.onAnimation] - Optional callback invoked on each animation
|
|
2661
|
+
* frame with the current scroll position, normalized animation time (`0` to `1`), and a completion flag.
|
|
2662
|
+
* @returns {TinyElementAndWindow|TinyElementAndWindow[]}
|
|
2663
|
+
* @throws {TypeError} If `el` is not a valid element, array, or window.
|
|
2664
|
+
* @throws {TypeError} If `targetX` or `targetY` is defined but not a number.
|
|
2665
|
+
* @throws {TypeError} If `duration` is defined but not a number.
|
|
2666
|
+
* @throws {TypeError} If `easing` is defined but not a valid easing function name.
|
|
2667
|
+
* @throws {TypeError} If `onAnimation` is defined but not a function.
|
|
2668
|
+
*/
|
|
2669
|
+
static scrollToXY(el, { targetX, targetY, duration, easing, onAnimation } = {}) {
|
|
2670
|
+
if (targetX !== undefined && typeof targetX !== 'number')
|
|
2671
|
+
throw new TypeError('`targetX` must be a number if provided.');
|
|
2672
|
+
if (targetY !== undefined && typeof targetY !== 'number')
|
|
2673
|
+
throw new TypeError('`targetY` must be a number if provided.');
|
|
2674
|
+
if (duration !== undefined && typeof duration !== 'number')
|
|
2675
|
+
throw new TypeError('`duration` must be a number if provided.');
|
|
2676
|
+
if (easing !== undefined && typeof easing !== 'string')
|
|
2677
|
+
throw new TypeError('`easing` must be a string if provided.');
|
|
2678
|
+
if (easing !== undefined && typeof TinyHtml.easings[easing] !== 'function')
|
|
2679
|
+
throw new TypeError(`Unknown easing function: "${easing}".`);
|
|
2680
|
+
if (onAnimation !== undefined && typeof onAnimation !== 'function')
|
|
2681
|
+
throw new TypeError('`onAnimation` must be a function if provided.');
|
|
2682
|
+
/**
|
|
2683
|
+
* Performs an instant scroll to the given coordinates.
|
|
2684
|
+
*
|
|
2685
|
+
* @param {ElementAndWindow} elem - The element or window to scroll.
|
|
2686
|
+
* @param {number} newX - The final horizontal scroll position.
|
|
2687
|
+
* @param {number} newY - The final vertical scroll position.
|
|
2688
|
+
* @param {number} time - Normalized progress value.
|
|
2689
|
+
*/
|
|
2690
|
+
const executeScroll = (elem, newX, newY, time) => {
|
|
2691
|
+
if (elem instanceof Window) {
|
|
2692
|
+
window.scrollTo(newX, newY);
|
|
2612
2693
|
}
|
|
2613
2694
|
else if (elem.nodeType === 9) {
|
|
2614
2695
|
// @ts-ignore
|
|
2615
|
-
elem.defaultView.scrollTo(
|
|
2696
|
+
elem.defaultView.scrollTo(newX, newY);
|
|
2616
2697
|
}
|
|
2617
2698
|
else {
|
|
2618
|
-
elem.
|
|
2699
|
+
const startX = elem instanceof Window ? window.scrollX : elem.scrollLeft;
|
|
2700
|
+
const startY = elem instanceof Window ? window.scrollY : elem.scrollTop;
|
|
2701
|
+
if (startX !== newX)
|
|
2702
|
+
elem.scrollLeft = newX;
|
|
2703
|
+
if (startY !== newY)
|
|
2704
|
+
elem.scrollTop = newY;
|
|
2705
|
+
}
|
|
2706
|
+
if (typeof onAnimation === 'function')
|
|
2707
|
+
onAnimation({ x: newX, y: newY, isComplete: time >= 1, time });
|
|
2708
|
+
};
|
|
2709
|
+
TinyHtml._preElemsAndWindow(el, 'scrollToXY').forEach((elem) => {
|
|
2710
|
+
const startX = elem instanceof Window ? window.scrollX : elem.scrollLeft;
|
|
2711
|
+
const startY = elem instanceof Window ? window.scrollY : elem.scrollTop;
|
|
2712
|
+
const targX = targetX ?? startX;
|
|
2713
|
+
const targY = targetY ?? startY;
|
|
2714
|
+
const changeX = targX - startX;
|
|
2715
|
+
const changeY = targY - startY;
|
|
2716
|
+
const ease = (typeof easing === 'string' && TinyHtml.easings[easing]) || null;
|
|
2717
|
+
if (typeof duration !== 'number' || typeof ease !== 'function')
|
|
2718
|
+
return executeScroll(elem, targX, targY, 1);
|
|
2719
|
+
const startTime = performance.now();
|
|
2720
|
+
const dur = duration ?? 0;
|
|
2721
|
+
/**
|
|
2722
|
+
* Animates the scroll position based on easing and time.
|
|
2723
|
+
*
|
|
2724
|
+
* @param {number} currentTime - Timestamp provided by requestAnimationFrame.
|
|
2725
|
+
*/
|
|
2726
|
+
function animateScroll(currentTime) {
|
|
2727
|
+
if (typeof ease !== 'function')
|
|
2728
|
+
return;
|
|
2729
|
+
const time = Math.min(1, (currentTime - startTime) / dur);
|
|
2730
|
+
const easedTime = ease(time);
|
|
2731
|
+
const newX = startX + changeX * easedTime;
|
|
2732
|
+
const newY = startY + changeY * easedTime;
|
|
2733
|
+
executeScroll(elem, newX, newY, time);
|
|
2734
|
+
if (time < 1)
|
|
2735
|
+
requestAnimationFrame(animateScroll);
|
|
2619
2736
|
}
|
|
2737
|
+
requestAnimationFrame(animateScroll);
|
|
2620
2738
|
});
|
|
2621
2739
|
return el;
|
|
2622
2740
|
}
|
|
2741
|
+
/**
|
|
2742
|
+
* Smoothly scrolls one or more elements (or the window) to the specified X and Y coordinates
|
|
2743
|
+
* using a custom duration and easing function.
|
|
2744
|
+
*
|
|
2745
|
+
* If `duration` or a valid `easing` is not provided, the scroll will be performed immediately.
|
|
2746
|
+
*
|
|
2747
|
+
* @param {Object} [settings={}] - Configuration object for the scroll animation.
|
|
2748
|
+
* @param {number} [settings.targetX] - The horizontal scroll target in pixels.
|
|
2749
|
+
* @param {number} [settings.targetY] - The vertical scroll target in pixels.
|
|
2750
|
+
* @param {number} [settings.duration] - The duration of the animation in milliseconds.
|
|
2751
|
+
* @param {Easings} [settings.easing] - The easing function name to use for the scroll animation.
|
|
2752
|
+
* @param {OnScrollAnimation} [settings.onAnimation] - Optional callback invoked on each animation
|
|
2753
|
+
* frame with the current scroll position, normalized animation time (`0` to `1`), and a completion flag.
|
|
2754
|
+
* @returns {TinyElementAndWindow|TinyElementAndWindow[]}
|
|
2755
|
+
*/
|
|
2756
|
+
scrollToXY({ targetX, targetY, duration, easing, onAnimation } = {}) {
|
|
2757
|
+
return TinyHtml.scrollToXY(this, { targetX, targetY, duration, easing, onAnimation });
|
|
2758
|
+
}
|
|
2759
|
+
/**
|
|
2760
|
+
* Sets the vertical scroll position.
|
|
2761
|
+
* @param {TinyElementAndWindow|TinyElementAndWindow[]} el - Element or window.
|
|
2762
|
+
* @param {number} value - Scroll top value.
|
|
2763
|
+
* @returns {TinyElementAndWindow|TinyElementAndWindow[]}
|
|
2764
|
+
*/
|
|
2765
|
+
static setScrollTop(el, value) {
|
|
2766
|
+
if (typeof value !== 'number')
|
|
2767
|
+
throw new TypeError('ScrollTop value must be a number.');
|
|
2768
|
+
return TinyHtml.scrollToXY(el, { targetY: value });
|
|
2769
|
+
}
|
|
2623
2770
|
/**
|
|
2624
2771
|
* Sets the vertical scroll position.
|
|
2625
2772
|
* @param {number} value - Scroll top value.
|
|
@@ -2637,19 +2784,7 @@ class TinyHtml {
|
|
|
2637
2784
|
static setScrollLeft(el, value) {
|
|
2638
2785
|
if (typeof value !== 'number')
|
|
2639
2786
|
throw new TypeError('ScrollLeft value must be a number.');
|
|
2640
|
-
TinyHtml.
|
|
2641
|
-
if (TinyHtml.isWindow(elem)) {
|
|
2642
|
-
elem.scrollTo(value, elem.pageYOffset);
|
|
2643
|
-
}
|
|
2644
|
-
else if (elem.nodeType === 9) {
|
|
2645
|
-
// @ts-ignore
|
|
2646
|
-
elem.defaultView.scrollTo(value, elem.defaultView.pageYOffset);
|
|
2647
|
-
}
|
|
2648
|
-
else {
|
|
2649
|
-
elem.scrollLeft = value;
|
|
2650
|
-
}
|
|
2651
|
-
});
|
|
2652
|
-
return el;
|
|
2787
|
+
return TinyHtml.scrollToXY(el, { targetX: value });
|
|
2653
2788
|
}
|
|
2654
2789
|
/**
|
|
2655
2790
|
* Sets the horizontal scroll position.
|