masonry-simple 4.5.0 → 5.0.0
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/README.md +1 -1
- package/dist/index.cjs +198 -0
- package/dist/index.cjs.map +1 -0
- package/dist/index.d.cts +42 -0
- package/dist/index.d.ts +43 -43
- package/dist/index.js +197 -0
- package/dist/index.js.map +1 -0
- package/package.json +35 -27
- package/dist/index.cjs.js +0 -3
- package/dist/index.cjs.js.map +0 -1
- package/dist/index.es.js +0 -135
- package/dist/index.es.js.map +0 -1
- package/dist/index.umd.js +0 -3
- package/dist/index.umd.js.map +0 -1
package/README.md
CHANGED
package/dist/index.cjs
ADDED
|
@@ -0,0 +1,198 @@
|
|
|
1
|
+
|
|
2
|
+
//#region src/index.ts
|
|
3
|
+
var MasonrySimple = class {
|
|
4
|
+
containerOption;
|
|
5
|
+
container = null;
|
|
6
|
+
gridItems = [];
|
|
7
|
+
rowHeight = 1;
|
|
8
|
+
rowGap = 0;
|
|
9
|
+
resizeScheduled = false;
|
|
10
|
+
rafId = null;
|
|
11
|
+
resizeObserver = null;
|
|
12
|
+
mutationObserver = null;
|
|
13
|
+
observerAbortController = null;
|
|
14
|
+
imageAbortController = null;
|
|
15
|
+
observedImages = /* @__PURE__ */ new WeakSet();
|
|
16
|
+
isInitialized = false;
|
|
17
|
+
isDestroyed = false;
|
|
18
|
+
originalContainerStyles = {
|
|
19
|
+
gridAutoRows: "",
|
|
20
|
+
contain: "",
|
|
21
|
+
alignItems: ""
|
|
22
|
+
};
|
|
23
|
+
constructor(options = {}) {
|
|
24
|
+
this.containerOption = options.container;
|
|
25
|
+
}
|
|
26
|
+
init() {
|
|
27
|
+
if (this.isInitialized) return;
|
|
28
|
+
this.container = this.resolveContainer();
|
|
29
|
+
if (!this.container) return;
|
|
30
|
+
this.isInitialized = true;
|
|
31
|
+
this.isDestroyed = false;
|
|
32
|
+
this.setupAbortControllers();
|
|
33
|
+
this.storeContainerStyles();
|
|
34
|
+
this.initializeContainerStyles();
|
|
35
|
+
this.initializeGridItems();
|
|
36
|
+
this.setupResizeObserver();
|
|
37
|
+
this.setupMutationObserver();
|
|
38
|
+
this.scheduleLayout();
|
|
39
|
+
}
|
|
40
|
+
refresh() {
|
|
41
|
+
if (!this.isInitialized || this.isDestroyed || !this.container) return;
|
|
42
|
+
this.initializeGridItems();
|
|
43
|
+
this.scheduleLayout();
|
|
44
|
+
}
|
|
45
|
+
destroy() {
|
|
46
|
+
if (!this.isInitialized && !this.container) return;
|
|
47
|
+
this.isDestroyed = true;
|
|
48
|
+
this.isInitialized = false;
|
|
49
|
+
this.cancelScheduledLayout();
|
|
50
|
+
this.observerAbortController?.abort();
|
|
51
|
+
this.imageAbortController?.abort();
|
|
52
|
+
this.resizeObserver?.disconnect();
|
|
53
|
+
this.mutationObserver?.disconnect();
|
|
54
|
+
this.gridItems.forEach((item) => {
|
|
55
|
+
item.style.gridRowEnd = "";
|
|
56
|
+
});
|
|
57
|
+
if (this.container) {
|
|
58
|
+
this.container.style.gridAutoRows = this.originalContainerStyles.gridAutoRows;
|
|
59
|
+
this.container.style.contain = this.originalContainerStyles.contain;
|
|
60
|
+
this.container.style.alignItems = this.originalContainerStyles.alignItems;
|
|
61
|
+
}
|
|
62
|
+
this.gridItems = [];
|
|
63
|
+
this.rowHeight = 1;
|
|
64
|
+
this.rowGap = 0;
|
|
65
|
+
this.resizeObserver = null;
|
|
66
|
+
this.mutationObserver = null;
|
|
67
|
+
this.observerAbortController = null;
|
|
68
|
+
this.imageAbortController = null;
|
|
69
|
+
this.observedImages = /* @__PURE__ */ new WeakSet();
|
|
70
|
+
this.resizeScheduled = false;
|
|
71
|
+
this.container = null;
|
|
72
|
+
this.originalContainerStyles = {
|
|
73
|
+
gridAutoRows: "",
|
|
74
|
+
contain: "",
|
|
75
|
+
alignItems: ""
|
|
76
|
+
};
|
|
77
|
+
}
|
|
78
|
+
resolveContainer() {
|
|
79
|
+
if (this.containerOption instanceof HTMLElement) return this.containerOption;
|
|
80
|
+
if (typeof document === "undefined") return null;
|
|
81
|
+
if (typeof this.containerOption === "string") return document.querySelector(this.containerOption);
|
|
82
|
+
return document.querySelector(".masonry");
|
|
83
|
+
}
|
|
84
|
+
scheduleLayout() {
|
|
85
|
+
if (!this.isInitialized || this.isDestroyed || !this.container || this.resizeScheduled) return;
|
|
86
|
+
this.resizeScheduled = true;
|
|
87
|
+
if (typeof requestAnimationFrame === "function") {
|
|
88
|
+
this.rafId = requestAnimationFrame(() => {
|
|
89
|
+
this.rafId = null;
|
|
90
|
+
this.resizeScheduled = false;
|
|
91
|
+
this.performLayout();
|
|
92
|
+
});
|
|
93
|
+
return;
|
|
94
|
+
}
|
|
95
|
+
this.rafId = null;
|
|
96
|
+
this.resizeScheduled = false;
|
|
97
|
+
this.performLayout();
|
|
98
|
+
}
|
|
99
|
+
cancelScheduledLayout() {
|
|
100
|
+
if (this.rafId !== null && typeof cancelAnimationFrame === "function") cancelAnimationFrame(this.rafId);
|
|
101
|
+
this.rafId = null;
|
|
102
|
+
this.resizeScheduled = false;
|
|
103
|
+
}
|
|
104
|
+
performLayout() {
|
|
105
|
+
if (!this.isInitialized || this.isDestroyed || !this.container) return;
|
|
106
|
+
this.measureContainerMetrics();
|
|
107
|
+
this.resizeAllItems();
|
|
108
|
+
}
|
|
109
|
+
resizeAllItems() {
|
|
110
|
+
const denominator = this.rowHeight + this.rowGap;
|
|
111
|
+
this.gridItems.forEach((item) => {
|
|
112
|
+
if (denominator <= 0 || !Number.isFinite(denominator)) {
|
|
113
|
+
item.style.gridRowEnd = "span 1";
|
|
114
|
+
return;
|
|
115
|
+
}
|
|
116
|
+
const rowSpan = Math.max(1, Math.ceil((item.getBoundingClientRect().height + this.rowGap) / denominator));
|
|
117
|
+
item.style.gridRowEnd = `span ${rowSpan}`;
|
|
118
|
+
});
|
|
119
|
+
}
|
|
120
|
+
setupAbortControllers() {
|
|
121
|
+
this.observerAbortController = new AbortController();
|
|
122
|
+
this.imageAbortController = new AbortController();
|
|
123
|
+
this.observerAbortController.signal.addEventListener("abort", () => {
|
|
124
|
+
this.resizeObserver?.disconnect();
|
|
125
|
+
this.mutationObserver?.disconnect();
|
|
126
|
+
});
|
|
127
|
+
}
|
|
128
|
+
setupResizeObserver() {
|
|
129
|
+
if (!this.container || typeof ResizeObserver === "undefined") return;
|
|
130
|
+
this.resizeObserver = new ResizeObserver(() => this.handleResize());
|
|
131
|
+
this.resizeObserver.observe(this.container);
|
|
132
|
+
}
|
|
133
|
+
setupMutationObserver() {
|
|
134
|
+
if (!this.container || typeof MutationObserver === "undefined") return;
|
|
135
|
+
this.mutationObserver = new MutationObserver(() => {
|
|
136
|
+
this.initializeGridItems();
|
|
137
|
+
this.scheduleLayout();
|
|
138
|
+
});
|
|
139
|
+
this.mutationObserver.observe(this.container, {
|
|
140
|
+
childList: true,
|
|
141
|
+
subtree: false
|
|
142
|
+
});
|
|
143
|
+
}
|
|
144
|
+
handleResize() {
|
|
145
|
+
this.scheduleLayout();
|
|
146
|
+
}
|
|
147
|
+
initializeContainerStyles() {
|
|
148
|
+
if (!this.container) return;
|
|
149
|
+
this.container.style.gridAutoRows = "1px";
|
|
150
|
+
this.container.style.contain = "layout";
|
|
151
|
+
this.container.style.alignItems = "start";
|
|
152
|
+
}
|
|
153
|
+
measureContainerMetrics() {
|
|
154
|
+
if (!this.container) return;
|
|
155
|
+
const cs = getComputedStyle(this.container);
|
|
156
|
+
this.rowGap = this.parseCssPixelValue(cs.rowGap);
|
|
157
|
+
const parsedRowHeight = this.parseCssPixelValue(cs.gridAutoRows);
|
|
158
|
+
this.rowHeight = parsedRowHeight > 0 ? parsedRowHeight : 1;
|
|
159
|
+
}
|
|
160
|
+
initializeGridItems() {
|
|
161
|
+
if (!this.container) return;
|
|
162
|
+
this.gridItems = Array.from(this.container.children).filter((item) => item instanceof HTMLElement);
|
|
163
|
+
this.gridItems.forEach((item) => {
|
|
164
|
+
item.querySelectorAll("img").forEach((image) => {
|
|
165
|
+
this.observeImage(image);
|
|
166
|
+
});
|
|
167
|
+
});
|
|
168
|
+
}
|
|
169
|
+
observeImage(image) {
|
|
170
|
+
if (image.complete || this.observedImages.has(image)) return;
|
|
171
|
+
this.observedImages.add(image);
|
|
172
|
+
const onLoad = () => this.scheduleLayout();
|
|
173
|
+
if (this.imageAbortController) {
|
|
174
|
+
image.addEventListener("load", onLoad, {
|
|
175
|
+
once: true,
|
|
176
|
+
signal: this.imageAbortController.signal
|
|
177
|
+
});
|
|
178
|
+
return;
|
|
179
|
+
}
|
|
180
|
+
image.addEventListener("load", onLoad, { once: true });
|
|
181
|
+
}
|
|
182
|
+
parseCssPixelValue(value) {
|
|
183
|
+
const parsedValue = Number.parseFloat(value);
|
|
184
|
+
return Number.isFinite(parsedValue) ? parsedValue : 0;
|
|
185
|
+
}
|
|
186
|
+
storeContainerStyles() {
|
|
187
|
+
if (!this.container) return;
|
|
188
|
+
this.originalContainerStyles = {
|
|
189
|
+
gridAutoRows: this.container.style.gridAutoRows || "",
|
|
190
|
+
contain: this.container.style.contain || "",
|
|
191
|
+
alignItems: this.container.style.alignItems || ""
|
|
192
|
+
};
|
|
193
|
+
}
|
|
194
|
+
};
|
|
195
|
+
|
|
196
|
+
//#endregion
|
|
197
|
+
module.exports = MasonrySimple;
|
|
198
|
+
//# sourceMappingURL=index.cjs.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.cjs","names":[],"sources":["../src/index.ts"],"sourcesContent":["interface MasonrySimpleOptions {\n container?: HTMLElement | string;\n}\n\nexport default class MasonrySimple {\n private readonly containerOption: HTMLElement | string | undefined;\n private container: HTMLElement | null = null;\n private gridItems: HTMLElement[] = [];\n private rowHeight = 1;\n private rowGap = 0;\n private resizeScheduled = false;\n private rafId: number | null = null;\n private resizeObserver: ResizeObserver | null = null;\n private mutationObserver: MutationObserver | null = null;\n private observerAbortController: AbortController | null = null;\n private imageAbortController: AbortController | null = null;\n private observedImages = new WeakSet<HTMLImageElement>();\n private isInitialized = false;\n private isDestroyed = false;\n private originalContainerStyles = {\n gridAutoRows: '',\n contain: '',\n alignItems: '',\n };\n\n constructor(options: MasonrySimpleOptions = {}) {\n this.containerOption = options.container;\n }\n\n public init(): void {\n if (this.isInitialized) return;\n\n this.container = this.resolveContainer();\n\n if (!this.container) return;\n\n this.isInitialized = true;\n this.isDestroyed = false;\n\n this.setupAbortControllers();\n this.storeContainerStyles();\n this.initializeContainerStyles();\n this.initializeGridItems();\n this.setupResizeObserver();\n this.setupMutationObserver();\n this.scheduleLayout();\n }\n\n public refresh(): void {\n if (!this.isInitialized || this.isDestroyed || !this.container) return;\n\n this.initializeGridItems();\n this.scheduleLayout();\n }\n\n public destroy(): void {\n if (!this.isInitialized && !this.container) return;\n\n this.isDestroyed = true;\n this.isInitialized = false;\n this.cancelScheduledLayout();\n this.observerAbortController?.abort();\n this.imageAbortController?.abort();\n this.resizeObserver?.disconnect();\n this.mutationObserver?.disconnect();\n this.gridItems.forEach((item) => {\n item.style.gridRowEnd = '';\n });\n\n if (this.container) {\n this.container.style.gridAutoRows = this.originalContainerStyles.gridAutoRows;\n this.container.style.contain = this.originalContainerStyles.contain;\n this.container.style.alignItems = this.originalContainerStyles.alignItems;\n }\n\n this.gridItems = [];\n this.rowHeight = 1;\n this.rowGap = 0;\n this.resizeObserver = null;\n this.mutationObserver = null;\n this.observerAbortController = null;\n this.imageAbortController = null;\n this.observedImages = new WeakSet<HTMLImageElement>();\n this.resizeScheduled = false;\n this.container = null;\n this.originalContainerStyles = {\n gridAutoRows: '',\n contain: '',\n alignItems: '',\n };\n }\n\n private resolveContainer(): HTMLElement | null {\n if (this.containerOption instanceof HTMLElement) {\n return this.containerOption;\n }\n\n if (typeof document === 'undefined') return null;\n\n if (typeof this.containerOption === 'string') {\n return document.querySelector<HTMLElement>(this.containerOption);\n }\n\n return document.querySelector<HTMLElement>('.masonry');\n }\n\n private scheduleLayout(): void {\n if (!this.isInitialized || this.isDestroyed || !this.container || this.resizeScheduled) return;\n\n this.resizeScheduled = true;\n\n if (typeof requestAnimationFrame === 'function') {\n this.rafId = requestAnimationFrame(() => {\n this.rafId = null;\n this.resizeScheduled = false;\n this.performLayout();\n });\n\n return;\n }\n\n this.rafId = null;\n this.resizeScheduled = false;\n this.performLayout();\n }\n\n private cancelScheduledLayout(): void {\n if (this.rafId !== null && typeof cancelAnimationFrame === 'function') {\n cancelAnimationFrame(this.rafId);\n }\n\n this.rafId = null;\n this.resizeScheduled = false;\n }\n\n private performLayout(): void {\n if (!this.isInitialized || this.isDestroyed || !this.container) return;\n\n this.measureContainerMetrics();\n this.resizeAllItems();\n }\n\n private resizeAllItems(): void {\n const denominator = this.rowHeight + this.rowGap;\n\n this.gridItems.forEach((item) => {\n if (denominator <= 0 || !Number.isFinite(denominator)) {\n item.style.gridRowEnd = 'span 1';\n\n return;\n }\n\n const rowSpan = Math.max(\n 1,\n Math.ceil((item.getBoundingClientRect().height + this.rowGap) / denominator),\n );\n item.style.gridRowEnd = `span ${rowSpan}`;\n });\n }\n\n private setupAbortControllers(): void {\n this.observerAbortController = new AbortController();\n this.imageAbortController = new AbortController();\n\n this.observerAbortController.signal.addEventListener('abort', () => {\n this.resizeObserver?.disconnect();\n this.mutationObserver?.disconnect();\n });\n }\n\n private setupResizeObserver(): void {\n if (!this.container || typeof ResizeObserver === 'undefined') return;\n\n this.resizeObserver = new ResizeObserver(() => this.handleResize());\n\n this.resizeObserver.observe(this.container);\n }\n\n private setupMutationObserver(): void {\n if (!this.container || typeof MutationObserver === 'undefined') return;\n\n this.mutationObserver = new MutationObserver(() => {\n this.initializeGridItems();\n this.scheduleLayout();\n });\n\n this.mutationObserver.observe(this.container, {\n childList: true,\n subtree: false,\n });\n }\n\n private handleResize(): void {\n this.scheduleLayout();\n }\n\n private initializeContainerStyles(): void {\n if (!this.container) return;\n\n this.container.style.gridAutoRows = '1px';\n this.container.style.contain = 'layout';\n this.container.style.alignItems = 'start';\n }\n\n private measureContainerMetrics(): void {\n if (!this.container) return;\n\n const cs = getComputedStyle(this.container);\n\n this.rowGap = this.parseCssPixelValue(cs.rowGap);\n\n const parsedRowHeight = this.parseCssPixelValue(cs.gridAutoRows);\n\n this.rowHeight = parsedRowHeight > 0 ? parsedRowHeight : 1;\n }\n\n private initializeGridItems(): void {\n if (!this.container) return;\n\n this.gridItems = Array.from(this.container.children).filter(\n (item): item is HTMLElement => item instanceof HTMLElement,\n );\n\n this.gridItems.forEach((item) => {\n const images = item.querySelectorAll('img');\n\n images.forEach((image) => {\n this.observeImage(image);\n });\n });\n }\n\n private observeImage(image: HTMLImageElement): void {\n if (image.complete || this.observedImages.has(image)) return;\n\n this.observedImages.add(image);\n\n const onLoad = (): void => this.scheduleLayout();\n\n if (this.imageAbortController) {\n image.addEventListener('load', onLoad, {\n once: true,\n signal: this.imageAbortController.signal,\n });\n\n return;\n }\n\n image.addEventListener('load', onLoad, { once: true });\n }\n\n private parseCssPixelValue(value: string): number {\n const parsedValue = Number.parseFloat(value);\n\n return Number.isFinite(parsedValue) ? parsedValue : 0;\n }\n\n private storeContainerStyles(): void {\n if (!this.container) return;\n\n this.originalContainerStyles = {\n gridAutoRows: this.container.style.gridAutoRows || '',\n contain: this.container.style.contain || '',\n alignItems: this.container.style.alignItems || '',\n };\n }\n}\n"],"mappings":"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"}
|
package/dist/index.d.cts
ADDED
|
@@ -0,0 +1,42 @@
|
|
|
1
|
+
//#region src/index.d.ts
|
|
2
|
+
interface MasonrySimpleOptions {
|
|
3
|
+
container?: HTMLElement | string;
|
|
4
|
+
}
|
|
5
|
+
declare class MasonrySimple {
|
|
6
|
+
private readonly containerOption;
|
|
7
|
+
private container;
|
|
8
|
+
private gridItems;
|
|
9
|
+
private rowHeight;
|
|
10
|
+
private rowGap;
|
|
11
|
+
private resizeScheduled;
|
|
12
|
+
private rafId;
|
|
13
|
+
private resizeObserver;
|
|
14
|
+
private mutationObserver;
|
|
15
|
+
private observerAbortController;
|
|
16
|
+
private imageAbortController;
|
|
17
|
+
private observedImages;
|
|
18
|
+
private isInitialized;
|
|
19
|
+
private isDestroyed;
|
|
20
|
+
private originalContainerStyles;
|
|
21
|
+
constructor(options?: MasonrySimpleOptions);
|
|
22
|
+
init(): void;
|
|
23
|
+
refresh(): void;
|
|
24
|
+
destroy(): void;
|
|
25
|
+
private resolveContainer;
|
|
26
|
+
private scheduleLayout;
|
|
27
|
+
private cancelScheduledLayout;
|
|
28
|
+
private performLayout;
|
|
29
|
+
private resizeAllItems;
|
|
30
|
+
private setupAbortControllers;
|
|
31
|
+
private setupResizeObserver;
|
|
32
|
+
private setupMutationObserver;
|
|
33
|
+
private handleResize;
|
|
34
|
+
private initializeContainerStyles;
|
|
35
|
+
private measureContainerMetrics;
|
|
36
|
+
private initializeGridItems;
|
|
37
|
+
private observeImage;
|
|
38
|
+
private parseCssPixelValue;
|
|
39
|
+
private storeContainerStyles;
|
|
40
|
+
}
|
|
41
|
+
export = MasonrySimple;
|
|
42
|
+
//# sourceMappingURL=index.d.cts.map
|
package/dist/index.d.ts
CHANGED
|
@@ -1,43 +1,43 @@
|
|
|
1
|
-
|
|
2
|
-
|
|
3
|
-
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
|
|
43
|
-
|
|
1
|
+
//#region src/index.d.ts
|
|
2
|
+
interface MasonrySimpleOptions {
|
|
3
|
+
container?: HTMLElement | string;
|
|
4
|
+
}
|
|
5
|
+
declare class MasonrySimple {
|
|
6
|
+
private readonly containerOption;
|
|
7
|
+
private container;
|
|
8
|
+
private gridItems;
|
|
9
|
+
private rowHeight;
|
|
10
|
+
private rowGap;
|
|
11
|
+
private resizeScheduled;
|
|
12
|
+
private rafId;
|
|
13
|
+
private resizeObserver;
|
|
14
|
+
private mutationObserver;
|
|
15
|
+
private observerAbortController;
|
|
16
|
+
private imageAbortController;
|
|
17
|
+
private observedImages;
|
|
18
|
+
private isInitialized;
|
|
19
|
+
private isDestroyed;
|
|
20
|
+
private originalContainerStyles;
|
|
21
|
+
constructor(options?: MasonrySimpleOptions);
|
|
22
|
+
init(): void;
|
|
23
|
+
refresh(): void;
|
|
24
|
+
destroy(): void;
|
|
25
|
+
private resolveContainer;
|
|
26
|
+
private scheduleLayout;
|
|
27
|
+
private cancelScheduledLayout;
|
|
28
|
+
private performLayout;
|
|
29
|
+
private resizeAllItems;
|
|
30
|
+
private setupAbortControllers;
|
|
31
|
+
private setupResizeObserver;
|
|
32
|
+
private setupMutationObserver;
|
|
33
|
+
private handleResize;
|
|
34
|
+
private initializeContainerStyles;
|
|
35
|
+
private measureContainerMetrics;
|
|
36
|
+
private initializeGridItems;
|
|
37
|
+
private observeImage;
|
|
38
|
+
private parseCssPixelValue;
|
|
39
|
+
private storeContainerStyles;
|
|
40
|
+
}
|
|
41
|
+
//#endregion
|
|
42
|
+
export { MasonrySimple as default };
|
|
43
|
+
//# sourceMappingURL=index.d.ts.map
|
package/dist/index.js
ADDED
|
@@ -0,0 +1,197 @@
|
|
|
1
|
+
//#region src/index.ts
|
|
2
|
+
var MasonrySimple = class {
|
|
3
|
+
containerOption;
|
|
4
|
+
container = null;
|
|
5
|
+
gridItems = [];
|
|
6
|
+
rowHeight = 1;
|
|
7
|
+
rowGap = 0;
|
|
8
|
+
resizeScheduled = false;
|
|
9
|
+
rafId = null;
|
|
10
|
+
resizeObserver = null;
|
|
11
|
+
mutationObserver = null;
|
|
12
|
+
observerAbortController = null;
|
|
13
|
+
imageAbortController = null;
|
|
14
|
+
observedImages = /* @__PURE__ */ new WeakSet();
|
|
15
|
+
isInitialized = false;
|
|
16
|
+
isDestroyed = false;
|
|
17
|
+
originalContainerStyles = {
|
|
18
|
+
gridAutoRows: "",
|
|
19
|
+
contain: "",
|
|
20
|
+
alignItems: ""
|
|
21
|
+
};
|
|
22
|
+
constructor(options = {}) {
|
|
23
|
+
this.containerOption = options.container;
|
|
24
|
+
}
|
|
25
|
+
init() {
|
|
26
|
+
if (this.isInitialized) return;
|
|
27
|
+
this.container = this.resolveContainer();
|
|
28
|
+
if (!this.container) return;
|
|
29
|
+
this.isInitialized = true;
|
|
30
|
+
this.isDestroyed = false;
|
|
31
|
+
this.setupAbortControllers();
|
|
32
|
+
this.storeContainerStyles();
|
|
33
|
+
this.initializeContainerStyles();
|
|
34
|
+
this.initializeGridItems();
|
|
35
|
+
this.setupResizeObserver();
|
|
36
|
+
this.setupMutationObserver();
|
|
37
|
+
this.scheduleLayout();
|
|
38
|
+
}
|
|
39
|
+
refresh() {
|
|
40
|
+
if (!this.isInitialized || this.isDestroyed || !this.container) return;
|
|
41
|
+
this.initializeGridItems();
|
|
42
|
+
this.scheduleLayout();
|
|
43
|
+
}
|
|
44
|
+
destroy() {
|
|
45
|
+
if (!this.isInitialized && !this.container) return;
|
|
46
|
+
this.isDestroyed = true;
|
|
47
|
+
this.isInitialized = false;
|
|
48
|
+
this.cancelScheduledLayout();
|
|
49
|
+
this.observerAbortController?.abort();
|
|
50
|
+
this.imageAbortController?.abort();
|
|
51
|
+
this.resizeObserver?.disconnect();
|
|
52
|
+
this.mutationObserver?.disconnect();
|
|
53
|
+
this.gridItems.forEach((item) => {
|
|
54
|
+
item.style.gridRowEnd = "";
|
|
55
|
+
});
|
|
56
|
+
if (this.container) {
|
|
57
|
+
this.container.style.gridAutoRows = this.originalContainerStyles.gridAutoRows;
|
|
58
|
+
this.container.style.contain = this.originalContainerStyles.contain;
|
|
59
|
+
this.container.style.alignItems = this.originalContainerStyles.alignItems;
|
|
60
|
+
}
|
|
61
|
+
this.gridItems = [];
|
|
62
|
+
this.rowHeight = 1;
|
|
63
|
+
this.rowGap = 0;
|
|
64
|
+
this.resizeObserver = null;
|
|
65
|
+
this.mutationObserver = null;
|
|
66
|
+
this.observerAbortController = null;
|
|
67
|
+
this.imageAbortController = null;
|
|
68
|
+
this.observedImages = /* @__PURE__ */ new WeakSet();
|
|
69
|
+
this.resizeScheduled = false;
|
|
70
|
+
this.container = null;
|
|
71
|
+
this.originalContainerStyles = {
|
|
72
|
+
gridAutoRows: "",
|
|
73
|
+
contain: "",
|
|
74
|
+
alignItems: ""
|
|
75
|
+
};
|
|
76
|
+
}
|
|
77
|
+
resolveContainer() {
|
|
78
|
+
if (this.containerOption instanceof HTMLElement) return this.containerOption;
|
|
79
|
+
if (typeof document === "undefined") return null;
|
|
80
|
+
if (typeof this.containerOption === "string") return document.querySelector(this.containerOption);
|
|
81
|
+
return document.querySelector(".masonry");
|
|
82
|
+
}
|
|
83
|
+
scheduleLayout() {
|
|
84
|
+
if (!this.isInitialized || this.isDestroyed || !this.container || this.resizeScheduled) return;
|
|
85
|
+
this.resizeScheduled = true;
|
|
86
|
+
if (typeof requestAnimationFrame === "function") {
|
|
87
|
+
this.rafId = requestAnimationFrame(() => {
|
|
88
|
+
this.rafId = null;
|
|
89
|
+
this.resizeScheduled = false;
|
|
90
|
+
this.performLayout();
|
|
91
|
+
});
|
|
92
|
+
return;
|
|
93
|
+
}
|
|
94
|
+
this.rafId = null;
|
|
95
|
+
this.resizeScheduled = false;
|
|
96
|
+
this.performLayout();
|
|
97
|
+
}
|
|
98
|
+
cancelScheduledLayout() {
|
|
99
|
+
if (this.rafId !== null && typeof cancelAnimationFrame === "function") cancelAnimationFrame(this.rafId);
|
|
100
|
+
this.rafId = null;
|
|
101
|
+
this.resizeScheduled = false;
|
|
102
|
+
}
|
|
103
|
+
performLayout() {
|
|
104
|
+
if (!this.isInitialized || this.isDestroyed || !this.container) return;
|
|
105
|
+
this.measureContainerMetrics();
|
|
106
|
+
this.resizeAllItems();
|
|
107
|
+
}
|
|
108
|
+
resizeAllItems() {
|
|
109
|
+
const denominator = this.rowHeight + this.rowGap;
|
|
110
|
+
this.gridItems.forEach((item) => {
|
|
111
|
+
if (denominator <= 0 || !Number.isFinite(denominator)) {
|
|
112
|
+
item.style.gridRowEnd = "span 1";
|
|
113
|
+
return;
|
|
114
|
+
}
|
|
115
|
+
const rowSpan = Math.max(1, Math.ceil((item.getBoundingClientRect().height + this.rowGap) / denominator));
|
|
116
|
+
item.style.gridRowEnd = `span ${rowSpan}`;
|
|
117
|
+
});
|
|
118
|
+
}
|
|
119
|
+
setupAbortControllers() {
|
|
120
|
+
this.observerAbortController = new AbortController();
|
|
121
|
+
this.imageAbortController = new AbortController();
|
|
122
|
+
this.observerAbortController.signal.addEventListener("abort", () => {
|
|
123
|
+
this.resizeObserver?.disconnect();
|
|
124
|
+
this.mutationObserver?.disconnect();
|
|
125
|
+
});
|
|
126
|
+
}
|
|
127
|
+
setupResizeObserver() {
|
|
128
|
+
if (!this.container || typeof ResizeObserver === "undefined") return;
|
|
129
|
+
this.resizeObserver = new ResizeObserver(() => this.handleResize());
|
|
130
|
+
this.resizeObserver.observe(this.container);
|
|
131
|
+
}
|
|
132
|
+
setupMutationObserver() {
|
|
133
|
+
if (!this.container || typeof MutationObserver === "undefined") return;
|
|
134
|
+
this.mutationObserver = new MutationObserver(() => {
|
|
135
|
+
this.initializeGridItems();
|
|
136
|
+
this.scheduleLayout();
|
|
137
|
+
});
|
|
138
|
+
this.mutationObserver.observe(this.container, {
|
|
139
|
+
childList: true,
|
|
140
|
+
subtree: false
|
|
141
|
+
});
|
|
142
|
+
}
|
|
143
|
+
handleResize() {
|
|
144
|
+
this.scheduleLayout();
|
|
145
|
+
}
|
|
146
|
+
initializeContainerStyles() {
|
|
147
|
+
if (!this.container) return;
|
|
148
|
+
this.container.style.gridAutoRows = "1px";
|
|
149
|
+
this.container.style.contain = "layout";
|
|
150
|
+
this.container.style.alignItems = "start";
|
|
151
|
+
}
|
|
152
|
+
measureContainerMetrics() {
|
|
153
|
+
if (!this.container) return;
|
|
154
|
+
const cs = getComputedStyle(this.container);
|
|
155
|
+
this.rowGap = this.parseCssPixelValue(cs.rowGap);
|
|
156
|
+
const parsedRowHeight = this.parseCssPixelValue(cs.gridAutoRows);
|
|
157
|
+
this.rowHeight = parsedRowHeight > 0 ? parsedRowHeight : 1;
|
|
158
|
+
}
|
|
159
|
+
initializeGridItems() {
|
|
160
|
+
if (!this.container) return;
|
|
161
|
+
this.gridItems = Array.from(this.container.children).filter((item) => item instanceof HTMLElement);
|
|
162
|
+
this.gridItems.forEach((item) => {
|
|
163
|
+
item.querySelectorAll("img").forEach((image) => {
|
|
164
|
+
this.observeImage(image);
|
|
165
|
+
});
|
|
166
|
+
});
|
|
167
|
+
}
|
|
168
|
+
observeImage(image) {
|
|
169
|
+
if (image.complete || this.observedImages.has(image)) return;
|
|
170
|
+
this.observedImages.add(image);
|
|
171
|
+
const onLoad = () => this.scheduleLayout();
|
|
172
|
+
if (this.imageAbortController) {
|
|
173
|
+
image.addEventListener("load", onLoad, {
|
|
174
|
+
once: true,
|
|
175
|
+
signal: this.imageAbortController.signal
|
|
176
|
+
});
|
|
177
|
+
return;
|
|
178
|
+
}
|
|
179
|
+
image.addEventListener("load", onLoad, { once: true });
|
|
180
|
+
}
|
|
181
|
+
parseCssPixelValue(value) {
|
|
182
|
+
const parsedValue = Number.parseFloat(value);
|
|
183
|
+
return Number.isFinite(parsedValue) ? parsedValue : 0;
|
|
184
|
+
}
|
|
185
|
+
storeContainerStyles() {
|
|
186
|
+
if (!this.container) return;
|
|
187
|
+
this.originalContainerStyles = {
|
|
188
|
+
gridAutoRows: this.container.style.gridAutoRows || "",
|
|
189
|
+
contain: this.container.style.contain || "",
|
|
190
|
+
alignItems: this.container.style.alignItems || ""
|
|
191
|
+
};
|
|
192
|
+
}
|
|
193
|
+
};
|
|
194
|
+
|
|
195
|
+
//#endregion
|
|
196
|
+
export { MasonrySimple as default };
|
|
197
|
+
//# sourceMappingURL=index.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.js","names":[],"sources":["../src/index.ts"],"sourcesContent":["interface MasonrySimpleOptions {\n container?: HTMLElement | string;\n}\n\nexport default class MasonrySimple {\n private readonly containerOption: HTMLElement | string | undefined;\n private container: HTMLElement | null = null;\n private gridItems: HTMLElement[] = [];\n private rowHeight = 1;\n private rowGap = 0;\n private resizeScheduled = false;\n private rafId: number | null = null;\n private resizeObserver: ResizeObserver | null = null;\n private mutationObserver: MutationObserver | null = null;\n private observerAbortController: AbortController | null = null;\n private imageAbortController: AbortController | null = null;\n private observedImages = new WeakSet<HTMLImageElement>();\n private isInitialized = false;\n private isDestroyed = false;\n private originalContainerStyles = {\n gridAutoRows: '',\n contain: '',\n alignItems: '',\n };\n\n constructor(options: MasonrySimpleOptions = {}) {\n this.containerOption = options.container;\n }\n\n public init(): void {\n if (this.isInitialized) return;\n\n this.container = this.resolveContainer();\n\n if (!this.container) return;\n\n this.isInitialized = true;\n this.isDestroyed = false;\n\n this.setupAbortControllers();\n this.storeContainerStyles();\n this.initializeContainerStyles();\n this.initializeGridItems();\n this.setupResizeObserver();\n this.setupMutationObserver();\n this.scheduleLayout();\n }\n\n public refresh(): void {\n if (!this.isInitialized || this.isDestroyed || !this.container) return;\n\n this.initializeGridItems();\n this.scheduleLayout();\n }\n\n public destroy(): void {\n if (!this.isInitialized && !this.container) return;\n\n this.isDestroyed = true;\n this.isInitialized = false;\n this.cancelScheduledLayout();\n this.observerAbortController?.abort();\n this.imageAbortController?.abort();\n this.resizeObserver?.disconnect();\n this.mutationObserver?.disconnect();\n this.gridItems.forEach((item) => {\n item.style.gridRowEnd = '';\n });\n\n if (this.container) {\n this.container.style.gridAutoRows = this.originalContainerStyles.gridAutoRows;\n this.container.style.contain = this.originalContainerStyles.contain;\n this.container.style.alignItems = this.originalContainerStyles.alignItems;\n }\n\n this.gridItems = [];\n this.rowHeight = 1;\n this.rowGap = 0;\n this.resizeObserver = null;\n this.mutationObserver = null;\n this.observerAbortController = null;\n this.imageAbortController = null;\n this.observedImages = new WeakSet<HTMLImageElement>();\n this.resizeScheduled = false;\n this.container = null;\n this.originalContainerStyles = {\n gridAutoRows: '',\n contain: '',\n alignItems: '',\n };\n }\n\n private resolveContainer(): HTMLElement | null {\n if (this.containerOption instanceof HTMLElement) {\n return this.containerOption;\n }\n\n if (typeof document === 'undefined') return null;\n\n if (typeof this.containerOption === 'string') {\n return document.querySelector<HTMLElement>(this.containerOption);\n }\n\n return document.querySelector<HTMLElement>('.masonry');\n }\n\n private scheduleLayout(): void {\n if (!this.isInitialized || this.isDestroyed || !this.container || this.resizeScheduled) return;\n\n this.resizeScheduled = true;\n\n if (typeof requestAnimationFrame === 'function') {\n this.rafId = requestAnimationFrame(() => {\n this.rafId = null;\n this.resizeScheduled = false;\n this.performLayout();\n });\n\n return;\n }\n\n this.rafId = null;\n this.resizeScheduled = false;\n this.performLayout();\n }\n\n private cancelScheduledLayout(): void {\n if (this.rafId !== null && typeof cancelAnimationFrame === 'function') {\n cancelAnimationFrame(this.rafId);\n }\n\n this.rafId = null;\n this.resizeScheduled = false;\n }\n\n private performLayout(): void {\n if (!this.isInitialized || this.isDestroyed || !this.container) return;\n\n this.measureContainerMetrics();\n this.resizeAllItems();\n }\n\n private resizeAllItems(): void {\n const denominator = this.rowHeight + this.rowGap;\n\n this.gridItems.forEach((item) => {\n if (denominator <= 0 || !Number.isFinite(denominator)) {\n item.style.gridRowEnd = 'span 1';\n\n return;\n }\n\n const rowSpan = Math.max(\n 1,\n Math.ceil((item.getBoundingClientRect().height + this.rowGap) / denominator),\n );\n item.style.gridRowEnd = `span ${rowSpan}`;\n });\n }\n\n private setupAbortControllers(): void {\n this.observerAbortController = new AbortController();\n this.imageAbortController = new AbortController();\n\n this.observerAbortController.signal.addEventListener('abort', () => {\n this.resizeObserver?.disconnect();\n this.mutationObserver?.disconnect();\n });\n }\n\n private setupResizeObserver(): void {\n if (!this.container || typeof ResizeObserver === 'undefined') return;\n\n this.resizeObserver = new ResizeObserver(() => this.handleResize());\n\n this.resizeObserver.observe(this.container);\n }\n\n private setupMutationObserver(): void {\n if (!this.container || typeof MutationObserver === 'undefined') return;\n\n this.mutationObserver = new MutationObserver(() => {\n this.initializeGridItems();\n this.scheduleLayout();\n });\n\n this.mutationObserver.observe(this.container, {\n childList: true,\n subtree: false,\n });\n }\n\n private handleResize(): void {\n this.scheduleLayout();\n }\n\n private initializeContainerStyles(): void {\n if (!this.container) return;\n\n this.container.style.gridAutoRows = '1px';\n this.container.style.contain = 'layout';\n this.container.style.alignItems = 'start';\n }\n\n private measureContainerMetrics(): void {\n if (!this.container) return;\n\n const cs = getComputedStyle(this.container);\n\n this.rowGap = this.parseCssPixelValue(cs.rowGap);\n\n const parsedRowHeight = this.parseCssPixelValue(cs.gridAutoRows);\n\n this.rowHeight = parsedRowHeight > 0 ? parsedRowHeight : 1;\n }\n\n private initializeGridItems(): void {\n if (!this.container) return;\n\n this.gridItems = Array.from(this.container.children).filter(\n (item): item is HTMLElement => item instanceof HTMLElement,\n );\n\n this.gridItems.forEach((item) => {\n const images = item.querySelectorAll('img');\n\n images.forEach((image) => {\n this.observeImage(image);\n });\n });\n }\n\n private observeImage(image: HTMLImageElement): void {\n if (image.complete || this.observedImages.has(image)) return;\n\n this.observedImages.add(image);\n\n const onLoad = (): void => this.scheduleLayout();\n\n if (this.imageAbortController) {\n image.addEventListener('load', onLoad, {\n once: true,\n signal: this.imageAbortController.signal,\n });\n\n return;\n }\n\n image.addEventListener('load', onLoad, { once: true });\n }\n\n private parseCssPixelValue(value: string): number {\n const parsedValue = Number.parseFloat(value);\n\n return Number.isFinite(parsedValue) ? parsedValue : 0;\n }\n\n private storeContainerStyles(): void {\n if (!this.container) return;\n\n this.originalContainerStyles = {\n gridAutoRows: this.container.style.gridAutoRows || '',\n contain: this.container.style.contain || '',\n alignItems: this.container.style.alignItems || '',\n };\n }\n}\n"],"mappings":"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"}
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "masonry-simple",
|
|
3
|
-
"version": "
|
|
3
|
+
"version": "5.0.0",
|
|
4
4
|
"description": "MasonrySimple implements a simple system for placing masonry style elements using CSS Grid. Masonry placement is used for dynamic grids where elements may have different heights and need to be placed neatly without gaps.",
|
|
5
5
|
"author": "ux-ui.pro",
|
|
6
6
|
"license": "MIT",
|
|
@@ -14,49 +14,57 @@
|
|
|
14
14
|
"homepage": "https://github.com/ux-ui-pro/masonry-simple",
|
|
15
15
|
"sideEffects": false,
|
|
16
16
|
"type": "module",
|
|
17
|
-
"packageManager": "
|
|
17
|
+
"packageManager": "npm@10.9.3",
|
|
18
18
|
"engines": {
|
|
19
|
-
"node": ">=
|
|
19
|
+
"node": ">=20.19.0"
|
|
20
20
|
},
|
|
21
21
|
"scripts": {
|
|
22
22
|
"clean": "rimraf dist",
|
|
23
|
-
"build": "
|
|
24
|
-
"
|
|
25
|
-
"
|
|
26
|
-
"lint": "biome check src tests",
|
|
27
|
-
"
|
|
28
|
-
"format": "biome format --write src tests",
|
|
23
|
+
"build": "tsdown",
|
|
24
|
+
"verify": "npm run lint && npm run typecheck && npm run build && npm run test:smoke && npm run pack:check",
|
|
25
|
+
"lint": "biome check src tests tsdown.config.ts",
|
|
26
|
+
"lint:fix": "biome check --write src tests tsdown.config.ts",
|
|
27
|
+
"format": "biome format --write src tests tsdown.config.ts",
|
|
29
28
|
"typecheck": "tsc -p tsconfig.json --noEmit",
|
|
30
|
-
"test:smoke": "node --test tests
|
|
31
|
-
"
|
|
29
|
+
"test:smoke": "node --test \"tests/**/*.js\"",
|
|
30
|
+
"pack:check": "npm pack --dry-run && publint && attw --pack . --profile node16 --ignore-rules false-export-default",
|
|
31
|
+
"prepublishOnly": "npm run clean && npm run verify"
|
|
32
32
|
},
|
|
33
33
|
"source": "src/index.ts",
|
|
34
|
-
"main": "dist/index.cjs
|
|
35
|
-
"module": "dist/index.
|
|
36
|
-
"
|
|
37
|
-
"types": "dist/index.d.ts",
|
|
34
|
+
"main": "./dist/index.cjs",
|
|
35
|
+
"module": "./dist/index.js",
|
|
36
|
+
"types": "./dist/index.d.ts",
|
|
38
37
|
"exports": {
|
|
39
38
|
".": {
|
|
40
|
-
"
|
|
41
|
-
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
|
|
45
|
-
|
|
39
|
+
"import": {
|
|
40
|
+
"types": "./dist/index.d.ts",
|
|
41
|
+
"default": "./dist/index.js"
|
|
42
|
+
},
|
|
43
|
+
"require": {
|
|
44
|
+
"types": "./dist/index.d.cts",
|
|
45
|
+
"default": "./dist/index.cjs"
|
|
46
|
+
}
|
|
47
|
+
}
|
|
46
48
|
},
|
|
47
49
|
"files": [
|
|
48
50
|
"dist",
|
|
49
51
|
"README.md",
|
|
50
52
|
"LICENSE"
|
|
51
53
|
],
|
|
54
|
+
"publishConfig": {
|
|
55
|
+
"access": "public"
|
|
56
|
+
},
|
|
52
57
|
"devDependencies": {
|
|
53
|
-
"@
|
|
54
|
-
"@
|
|
55
|
-
"
|
|
58
|
+
"@arethetypeswrong/cli": "^0.18.3",
|
|
59
|
+
"@biomejs/biome": "2.4.16",
|
|
60
|
+
"@types/node": "25.9.2",
|
|
61
|
+
"@ux-ui/biome-config": "^0.1.0",
|
|
62
|
+
"@ux-ui/tsconfig-base": "^0.1.0",
|
|
63
|
+
"@ux-ui/tsdown-config": "^0.1.0",
|
|
64
|
+
"publint": "^0.3.21",
|
|
56
65
|
"rimraf": "6.1.3",
|
|
57
|
-
"
|
|
58
|
-
"
|
|
59
|
-
"vite-plugin-dts": "4.5.4"
|
|
66
|
+
"tsdown": "0.22.3",
|
|
67
|
+
"typescript": "6.0.3"
|
|
60
68
|
},
|
|
61
69
|
"keywords": [
|
|
62
70
|
"masonry",
|
package/dist/index.cjs.js
DELETED
|
@@ -1,3 +0,0 @@
|
|
|
1
|
-
var r=class{containerOption;container=null;gridItems=[];rowHeight=1;rowGap=0;resizeScheduled=!1;rafId=null;resizeObserver=null;mutationObserver=null;observerAbortController=null;imageAbortController=null;observedImages=new WeakSet;isInitialized=!1;isDestroyed=!1;originalContainerStyles={gridAutoRows:"",contain:"",alignItems:""};constructor(e={}){this.containerOption=e.container}init(){this.isInitialized||(this.container=this.resolveContainer(),this.container&&(this.isInitialized=!0,this.isDestroyed=!1,this.setupAbortControllers(),this.storeContainerStyles(),this.initializeContainerStyles(),this.initializeGridItems(),this.setupResizeObserver(),this.setupMutationObserver(),this.scheduleLayout()))}refresh(){!this.isInitialized||this.isDestroyed||!this.container||(this.initializeGridItems(),this.scheduleLayout())}destroy(){!this.isInitialized&&!this.container||(this.isDestroyed=!0,this.isInitialized=!1,this.cancelScheduledLayout(),this.observerAbortController?.abort(),this.imageAbortController?.abort(),this.resizeObserver?.disconnect(),this.mutationObserver?.disconnect(),this.gridItems.forEach(e=>{e.style.gridRowEnd=""}),this.container&&(this.container.style.gridAutoRows=this.originalContainerStyles.gridAutoRows,this.container.style.contain=this.originalContainerStyles.contain,this.container.style.alignItems=this.originalContainerStyles.alignItems),this.gridItems=[],this.rowHeight=1,this.rowGap=0,this.resizeObserver=null,this.mutationObserver=null,this.observerAbortController=null,this.imageAbortController=null,this.observedImages=new WeakSet,this.resizeScheduled=!1,this.container=null,this.originalContainerStyles={gridAutoRows:"",contain:"",alignItems:""})}resolveContainer(){return this.containerOption instanceof HTMLElement?this.containerOption:typeof document>"u"?null:typeof this.containerOption=="string"?document.querySelector(this.containerOption):document.querySelector(".masonry")}scheduleLayout(){if(!(!this.isInitialized||this.isDestroyed||!this.container||this.resizeScheduled)){if(this.resizeScheduled=!0,typeof requestAnimationFrame=="function"){this.rafId=requestAnimationFrame(()=>{this.rafId=null,this.resizeScheduled=!1,this.performLayout()});return}this.rafId=null,this.resizeScheduled=!1,this.performLayout()}}cancelScheduledLayout(){this.rafId!==null&&typeof cancelAnimationFrame=="function"&&cancelAnimationFrame(this.rafId),this.rafId=null,this.resizeScheduled=!1}performLayout(){!this.isInitialized||this.isDestroyed||!this.container||(this.measureContainerMetrics(),this.resizeAllItems())}resizeAllItems(){const e=this.rowHeight+this.rowGap;this.gridItems.forEach(t=>{if(e<=0||!Number.isFinite(e)){t.style.gridRowEnd="span 1";return}const i=Math.max(1,Math.ceil((t.getBoundingClientRect().height+this.rowGap)/e));t.style.gridRowEnd=`span ${i}`})}setupAbortControllers(){this.observerAbortController=new AbortController,this.imageAbortController=new AbortController,this.observerAbortController.signal.addEventListener("abort",()=>{this.resizeObserver?.disconnect(),this.mutationObserver?.disconnect()})}setupResizeObserver(){!this.container||typeof ResizeObserver>"u"||(this.resizeObserver=new ResizeObserver(()=>this.handleResize()),this.resizeObserver.observe(this.container))}setupMutationObserver(){!this.container||typeof MutationObserver>"u"||(this.mutationObserver=new MutationObserver(()=>{this.initializeGridItems(),this.scheduleLayout()}),this.mutationObserver.observe(this.container,{childList:!0,subtree:!1}))}handleResize(){this.scheduleLayout()}initializeContainerStyles(){this.container&&(this.container.style.gridAutoRows="1px",this.container.style.contain="layout",this.container.style.alignItems="start")}measureContainerMetrics(){if(!this.container)return;const e=getComputedStyle(this.container);this.rowGap=this.parseCssPixelValue(e.rowGap);const t=this.parseCssPixelValue(e.gridAutoRows);this.rowHeight=t>0?t:1}initializeGridItems(){this.container&&(this.gridItems=Array.from(this.container.children).filter(e=>e instanceof HTMLElement),this.gridItems.forEach(e=>{e.querySelectorAll("img").forEach(t=>{this.observeImage(t)})}))}observeImage(e){if(e.complete||this.observedImages.has(e))return;this.observedImages.add(e);const t=()=>this.scheduleLayout();if(this.imageAbortController){e.addEventListener("load",t,{once:!0,signal:this.imageAbortController.signal});return}e.addEventListener("load",t,{once:!0})}parseCssPixelValue(e){const t=Number.parseFloat(e);return Number.isFinite(t)?t:0}storeContainerStyles(){this.container&&(this.originalContainerStyles={gridAutoRows:this.container.style.gridAutoRows||"",contain:this.container.style.contain||"",alignItems:this.container.style.alignItems||""})}};module.exports=r;
|
|
2
|
-
|
|
3
|
-
//# sourceMappingURL=index.cjs.js.map
|
package/dist/index.cjs.js.map
DELETED
|
@@ -1 +0,0 @@
|
|
|
1
|
-
{"version":3,"file":"index.cjs.js","names":[],"sources":["../src/index.ts"],"sourcesContent":["interface MasonrySimpleOptions {\n container?: HTMLElement | string;\n}\n\nexport default class MasonrySimple {\n private readonly containerOption: HTMLElement | string | undefined;\n private container: HTMLElement | null = null;\n private gridItems: HTMLElement[] = [];\n private rowHeight = 1;\n private rowGap = 0;\n private resizeScheduled = false;\n private rafId: number | null = null;\n private resizeObserver: ResizeObserver | null = null;\n private mutationObserver: MutationObserver | null = null;\n private observerAbortController: AbortController | null = null;\n private imageAbortController: AbortController | null = null;\n private observedImages = new WeakSet<HTMLImageElement>();\n private isInitialized = false;\n private isDestroyed = false;\n private originalContainerStyles = {\n gridAutoRows: '',\n contain: '',\n alignItems: '',\n };\n\n constructor(options: MasonrySimpleOptions = {}) {\n this.containerOption = options.container;\n }\n\n public init(): void {\n if (this.isInitialized) return;\n\n this.container = this.resolveContainer();\n\n if (!this.container) return;\n\n this.isInitialized = true;\n this.isDestroyed = false;\n\n this.setupAbortControllers();\n this.storeContainerStyles();\n this.initializeContainerStyles();\n this.initializeGridItems();\n this.setupResizeObserver();\n this.setupMutationObserver();\n this.scheduleLayout();\n }\n\n public refresh(): void {\n if (!this.isInitialized || this.isDestroyed || !this.container) return;\n\n this.initializeGridItems();\n this.scheduleLayout();\n }\n\n public destroy(): void {\n if (!this.isInitialized && !this.container) return;\n\n this.isDestroyed = true;\n this.isInitialized = false;\n this.cancelScheduledLayout();\n this.observerAbortController?.abort();\n this.imageAbortController?.abort();\n this.resizeObserver?.disconnect();\n this.mutationObserver?.disconnect();\n this.gridItems.forEach((item) => {\n item.style.gridRowEnd = '';\n });\n\n if (this.container) {\n this.container.style.gridAutoRows = this.originalContainerStyles.gridAutoRows;\n this.container.style.contain = this.originalContainerStyles.contain;\n this.container.style.alignItems = this.originalContainerStyles.alignItems;\n }\n\n this.gridItems = [];\n this.rowHeight = 1;\n this.rowGap = 0;\n this.resizeObserver = null;\n this.mutationObserver = null;\n this.observerAbortController = null;\n this.imageAbortController = null;\n this.observedImages = new WeakSet<HTMLImageElement>();\n this.resizeScheduled = false;\n this.container = null;\n this.originalContainerStyles = {\n gridAutoRows: '',\n contain: '',\n alignItems: '',\n };\n }\n\n private resolveContainer(): HTMLElement | null {\n if (this.containerOption instanceof HTMLElement) {\n return this.containerOption;\n }\n\n if (typeof document === 'undefined') return null;\n\n if (typeof this.containerOption === 'string') {\n return document.querySelector<HTMLElement>(this.containerOption);\n }\n\n return document.querySelector<HTMLElement>('.masonry');\n }\n\n private scheduleLayout(): void {\n if (!this.isInitialized || this.isDestroyed || !this.container || this.resizeScheduled) return;\n\n this.resizeScheduled = true;\n\n if (typeof requestAnimationFrame === 'function') {\n this.rafId = requestAnimationFrame(() => {\n this.rafId = null;\n this.resizeScheduled = false;\n this.performLayout();\n });\n\n return;\n }\n\n this.rafId = null;\n this.resizeScheduled = false;\n this.performLayout();\n }\n\n private cancelScheduledLayout(): void {\n if (this.rafId !== null && typeof cancelAnimationFrame === 'function') {\n cancelAnimationFrame(this.rafId);\n }\n\n this.rafId = null;\n this.resizeScheduled = false;\n }\n\n private performLayout(): void {\n if (!this.isInitialized || this.isDestroyed || !this.container) return;\n\n this.measureContainerMetrics();\n this.resizeAllItems();\n }\n\n private resizeAllItems(): void {\n const denominator = this.rowHeight + this.rowGap;\n\n this.gridItems.forEach((item) => {\n if (denominator <= 0 || !Number.isFinite(denominator)) {\n item.style.gridRowEnd = 'span 1';\n\n return;\n }\n\n const rowSpan = Math.max(\n 1,\n Math.ceil((item.getBoundingClientRect().height + this.rowGap) / denominator),\n );\n item.style.gridRowEnd = `span ${rowSpan}`;\n });\n }\n\n private setupAbortControllers(): void {\n this.observerAbortController = new AbortController();\n this.imageAbortController = new AbortController();\n\n this.observerAbortController.signal.addEventListener('abort', () => {\n this.resizeObserver?.disconnect();\n this.mutationObserver?.disconnect();\n });\n }\n\n private setupResizeObserver(): void {\n if (!this.container || typeof ResizeObserver === 'undefined') return;\n\n this.resizeObserver = new ResizeObserver(() => this.handleResize());\n\n this.resizeObserver.observe(this.container);\n }\n\n private setupMutationObserver(): void {\n if (!this.container || typeof MutationObserver === 'undefined') return;\n\n this.mutationObserver = new MutationObserver(() => {\n this.initializeGridItems();\n this.scheduleLayout();\n });\n\n this.mutationObserver.observe(this.container, {\n childList: true,\n subtree: false,\n });\n }\n\n private handleResize(): void {\n this.scheduleLayout();\n }\n\n private initializeContainerStyles(): void {\n if (!this.container) return;\n\n this.container.style.gridAutoRows = '1px';\n this.container.style.contain = 'layout';\n this.container.style.alignItems = 'start';\n }\n\n private measureContainerMetrics(): void {\n if (!this.container) return;\n\n const cs = getComputedStyle(this.container);\n\n this.rowGap = this.parseCssPixelValue(cs.rowGap);\n\n const parsedRowHeight = this.parseCssPixelValue(cs.gridAutoRows);\n\n this.rowHeight = parsedRowHeight > 0 ? parsedRowHeight : 1;\n }\n\n private initializeGridItems(): void {\n if (!this.container) return;\n\n this.gridItems = Array.from(this.container.children).filter(\n (item): item is HTMLElement => item instanceof HTMLElement,\n );\n\n this.gridItems.forEach((item) => {\n const images = item.querySelectorAll('img');\n\n images.forEach((image) => {\n this.observeImage(image);\n });\n });\n }\n\n private observeImage(image: HTMLImageElement): void {\n if (image.complete || this.observedImages.has(image)) return;\n\n this.observedImages.add(image);\n\n const onLoad = (): void => this.scheduleLayout();\n\n if (this.imageAbortController) {\n image.addEventListener('load', onLoad, {\n once: true,\n signal: this.imageAbortController.signal,\n });\n\n return;\n }\n\n image.addEventListener('load', onLoad, { once: true });\n }\n\n private parseCssPixelValue(value: string): number {\n const parsedValue = Number.parseFloat(value);\n\n return Number.isFinite(parsedValue) ? parsedValue : 0;\n }\n\n private storeContainerStyles(): void {\n if (!this.container) return;\n\n this.originalContainerStyles = {\n gridAutoRows: this.container.style.gridAutoRows || '',\n contain: this.container.style.contain || '',\n alignItems: this.container.style.alignItems || '',\n };\n }\n}\n"],"mappings":"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"}
|
package/dist/index.es.js
DELETED
|
@@ -1,135 +0,0 @@
|
|
|
1
|
-
var r = class {
|
|
2
|
-
containerOption;
|
|
3
|
-
container = null;
|
|
4
|
-
gridItems = [];
|
|
5
|
-
rowHeight = 1;
|
|
6
|
-
rowGap = 0;
|
|
7
|
-
resizeScheduled = !1;
|
|
8
|
-
rafId = null;
|
|
9
|
-
resizeObserver = null;
|
|
10
|
-
mutationObserver = null;
|
|
11
|
-
observerAbortController = null;
|
|
12
|
-
imageAbortController = null;
|
|
13
|
-
observedImages = /* @__PURE__ */ new WeakSet();
|
|
14
|
-
isInitialized = !1;
|
|
15
|
-
isDestroyed = !1;
|
|
16
|
-
originalContainerStyles = {
|
|
17
|
-
gridAutoRows: "",
|
|
18
|
-
contain: "",
|
|
19
|
-
alignItems: ""
|
|
20
|
-
};
|
|
21
|
-
constructor(e = {}) {
|
|
22
|
-
this.containerOption = e.container;
|
|
23
|
-
}
|
|
24
|
-
init() {
|
|
25
|
-
this.isInitialized || (this.container = this.resolveContainer(), this.container && (this.isInitialized = !0, this.isDestroyed = !1, this.setupAbortControllers(), this.storeContainerStyles(), this.initializeContainerStyles(), this.initializeGridItems(), this.setupResizeObserver(), this.setupMutationObserver(), this.scheduleLayout()));
|
|
26
|
-
}
|
|
27
|
-
refresh() {
|
|
28
|
-
!this.isInitialized || this.isDestroyed || !this.container || (this.initializeGridItems(), this.scheduleLayout());
|
|
29
|
-
}
|
|
30
|
-
destroy() {
|
|
31
|
-
!this.isInitialized && !this.container || (this.isDestroyed = !0, this.isInitialized = !1, this.cancelScheduledLayout(), this.observerAbortController?.abort(), this.imageAbortController?.abort(), this.resizeObserver?.disconnect(), this.mutationObserver?.disconnect(), this.gridItems.forEach((e) => {
|
|
32
|
-
e.style.gridRowEnd = "";
|
|
33
|
-
}), this.container && (this.container.style.gridAutoRows = this.originalContainerStyles.gridAutoRows, this.container.style.contain = this.originalContainerStyles.contain, this.container.style.alignItems = this.originalContainerStyles.alignItems), this.gridItems = [], this.rowHeight = 1, this.rowGap = 0, this.resizeObserver = null, this.mutationObserver = null, this.observerAbortController = null, this.imageAbortController = null, this.observedImages = /* @__PURE__ */ new WeakSet(), this.resizeScheduled = !1, this.container = null, this.originalContainerStyles = {
|
|
34
|
-
gridAutoRows: "",
|
|
35
|
-
contain: "",
|
|
36
|
-
alignItems: ""
|
|
37
|
-
});
|
|
38
|
-
}
|
|
39
|
-
resolveContainer() {
|
|
40
|
-
return this.containerOption instanceof HTMLElement ? this.containerOption : typeof document > "u" ? null : typeof this.containerOption == "string" ? document.querySelector(this.containerOption) : document.querySelector(".masonry");
|
|
41
|
-
}
|
|
42
|
-
scheduleLayout() {
|
|
43
|
-
if (!(!this.isInitialized || this.isDestroyed || !this.container || this.resizeScheduled)) {
|
|
44
|
-
if (this.resizeScheduled = !0, typeof requestAnimationFrame == "function") {
|
|
45
|
-
this.rafId = requestAnimationFrame(() => {
|
|
46
|
-
this.rafId = null, this.resizeScheduled = !1, this.performLayout();
|
|
47
|
-
});
|
|
48
|
-
return;
|
|
49
|
-
}
|
|
50
|
-
this.rafId = null, this.resizeScheduled = !1, this.performLayout();
|
|
51
|
-
}
|
|
52
|
-
}
|
|
53
|
-
cancelScheduledLayout() {
|
|
54
|
-
this.rafId !== null && typeof cancelAnimationFrame == "function" && cancelAnimationFrame(this.rafId), this.rafId = null, this.resizeScheduled = !1;
|
|
55
|
-
}
|
|
56
|
-
performLayout() {
|
|
57
|
-
!this.isInitialized || this.isDestroyed || !this.container || (this.measureContainerMetrics(), this.resizeAllItems());
|
|
58
|
-
}
|
|
59
|
-
resizeAllItems() {
|
|
60
|
-
const e = this.rowHeight + this.rowGap;
|
|
61
|
-
this.gridItems.forEach((t) => {
|
|
62
|
-
if (e <= 0 || !Number.isFinite(e)) {
|
|
63
|
-
t.style.gridRowEnd = "span 1";
|
|
64
|
-
return;
|
|
65
|
-
}
|
|
66
|
-
const i = Math.max(1, Math.ceil((t.getBoundingClientRect().height + this.rowGap) / e));
|
|
67
|
-
t.style.gridRowEnd = `span ${i}`;
|
|
68
|
-
});
|
|
69
|
-
}
|
|
70
|
-
setupAbortControllers() {
|
|
71
|
-
this.observerAbortController = new AbortController(), this.imageAbortController = new AbortController(), this.observerAbortController.signal.addEventListener("abort", () => {
|
|
72
|
-
this.resizeObserver?.disconnect(), this.mutationObserver?.disconnect();
|
|
73
|
-
});
|
|
74
|
-
}
|
|
75
|
-
setupResizeObserver() {
|
|
76
|
-
!this.container || typeof ResizeObserver > "u" || (this.resizeObserver = new ResizeObserver(() => this.handleResize()), this.resizeObserver.observe(this.container));
|
|
77
|
-
}
|
|
78
|
-
setupMutationObserver() {
|
|
79
|
-
!this.container || typeof MutationObserver > "u" || (this.mutationObserver = new MutationObserver(() => {
|
|
80
|
-
this.initializeGridItems(), this.scheduleLayout();
|
|
81
|
-
}), this.mutationObserver.observe(this.container, {
|
|
82
|
-
childList: !0,
|
|
83
|
-
subtree: !1
|
|
84
|
-
}));
|
|
85
|
-
}
|
|
86
|
-
handleResize() {
|
|
87
|
-
this.scheduleLayout();
|
|
88
|
-
}
|
|
89
|
-
initializeContainerStyles() {
|
|
90
|
-
this.container && (this.container.style.gridAutoRows = "1px", this.container.style.contain = "layout", this.container.style.alignItems = "start");
|
|
91
|
-
}
|
|
92
|
-
measureContainerMetrics() {
|
|
93
|
-
if (!this.container) return;
|
|
94
|
-
const e = getComputedStyle(this.container);
|
|
95
|
-
this.rowGap = this.parseCssPixelValue(e.rowGap);
|
|
96
|
-
const t = this.parseCssPixelValue(e.gridAutoRows);
|
|
97
|
-
this.rowHeight = t > 0 ? t : 1;
|
|
98
|
-
}
|
|
99
|
-
initializeGridItems() {
|
|
100
|
-
this.container && (this.gridItems = Array.from(this.container.children).filter((e) => e instanceof HTMLElement), this.gridItems.forEach((e) => {
|
|
101
|
-
e.querySelectorAll("img").forEach((t) => {
|
|
102
|
-
this.observeImage(t);
|
|
103
|
-
});
|
|
104
|
-
}));
|
|
105
|
-
}
|
|
106
|
-
observeImage(e) {
|
|
107
|
-
if (e.complete || this.observedImages.has(e)) return;
|
|
108
|
-
this.observedImages.add(e);
|
|
109
|
-
const t = () => this.scheduleLayout();
|
|
110
|
-
if (this.imageAbortController) {
|
|
111
|
-
e.addEventListener("load", t, {
|
|
112
|
-
once: !0,
|
|
113
|
-
signal: this.imageAbortController.signal
|
|
114
|
-
});
|
|
115
|
-
return;
|
|
116
|
-
}
|
|
117
|
-
e.addEventListener("load", t, { once: !0 });
|
|
118
|
-
}
|
|
119
|
-
parseCssPixelValue(e) {
|
|
120
|
-
const t = Number.parseFloat(e);
|
|
121
|
-
return Number.isFinite(t) ? t : 0;
|
|
122
|
-
}
|
|
123
|
-
storeContainerStyles() {
|
|
124
|
-
this.container && (this.originalContainerStyles = {
|
|
125
|
-
gridAutoRows: this.container.style.gridAutoRows || "",
|
|
126
|
-
contain: this.container.style.contain || "",
|
|
127
|
-
alignItems: this.container.style.alignItems || ""
|
|
128
|
-
});
|
|
129
|
-
}
|
|
130
|
-
};
|
|
131
|
-
export {
|
|
132
|
-
r as default
|
|
133
|
-
};
|
|
134
|
-
|
|
135
|
-
//# sourceMappingURL=index.es.js.map
|
package/dist/index.es.js.map
DELETED
|
@@ -1 +0,0 @@
|
|
|
1
|
-
{"version":3,"file":"index.es.js","names":[],"sources":["../src/index.ts"],"sourcesContent":["interface MasonrySimpleOptions {\n container?: HTMLElement | string;\n}\n\nexport default class MasonrySimple {\n private readonly containerOption: HTMLElement | string | undefined;\n private container: HTMLElement | null = null;\n private gridItems: HTMLElement[] = [];\n private rowHeight = 1;\n private rowGap = 0;\n private resizeScheduled = false;\n private rafId: number | null = null;\n private resizeObserver: ResizeObserver | null = null;\n private mutationObserver: MutationObserver | null = null;\n private observerAbortController: AbortController | null = null;\n private imageAbortController: AbortController | null = null;\n private observedImages = new WeakSet<HTMLImageElement>();\n private isInitialized = false;\n private isDestroyed = false;\n private originalContainerStyles = {\n gridAutoRows: '',\n contain: '',\n alignItems: '',\n };\n\n constructor(options: MasonrySimpleOptions = {}) {\n this.containerOption = options.container;\n }\n\n public init(): void {\n if (this.isInitialized) return;\n\n this.container = this.resolveContainer();\n\n if (!this.container) return;\n\n this.isInitialized = true;\n this.isDestroyed = false;\n\n this.setupAbortControllers();\n this.storeContainerStyles();\n this.initializeContainerStyles();\n this.initializeGridItems();\n this.setupResizeObserver();\n this.setupMutationObserver();\n this.scheduleLayout();\n }\n\n public refresh(): void {\n if (!this.isInitialized || this.isDestroyed || !this.container) return;\n\n this.initializeGridItems();\n this.scheduleLayout();\n }\n\n public destroy(): void {\n if (!this.isInitialized && !this.container) return;\n\n this.isDestroyed = true;\n this.isInitialized = false;\n this.cancelScheduledLayout();\n this.observerAbortController?.abort();\n this.imageAbortController?.abort();\n this.resizeObserver?.disconnect();\n this.mutationObserver?.disconnect();\n this.gridItems.forEach((item) => {\n item.style.gridRowEnd = '';\n });\n\n if (this.container) {\n this.container.style.gridAutoRows = this.originalContainerStyles.gridAutoRows;\n this.container.style.contain = this.originalContainerStyles.contain;\n this.container.style.alignItems = this.originalContainerStyles.alignItems;\n }\n\n this.gridItems = [];\n this.rowHeight = 1;\n this.rowGap = 0;\n this.resizeObserver = null;\n this.mutationObserver = null;\n this.observerAbortController = null;\n this.imageAbortController = null;\n this.observedImages = new WeakSet<HTMLImageElement>();\n this.resizeScheduled = false;\n this.container = null;\n this.originalContainerStyles = {\n gridAutoRows: '',\n contain: '',\n alignItems: '',\n };\n }\n\n private resolveContainer(): HTMLElement | null {\n if (this.containerOption instanceof HTMLElement) {\n return this.containerOption;\n }\n\n if (typeof document === 'undefined') return null;\n\n if (typeof this.containerOption === 'string') {\n return document.querySelector<HTMLElement>(this.containerOption);\n }\n\n return document.querySelector<HTMLElement>('.masonry');\n }\n\n private scheduleLayout(): void {\n if (!this.isInitialized || this.isDestroyed || !this.container || this.resizeScheduled) return;\n\n this.resizeScheduled = true;\n\n if (typeof requestAnimationFrame === 'function') {\n this.rafId = requestAnimationFrame(() => {\n this.rafId = null;\n this.resizeScheduled = false;\n this.performLayout();\n });\n\n return;\n }\n\n this.rafId = null;\n this.resizeScheduled = false;\n this.performLayout();\n }\n\n private cancelScheduledLayout(): void {\n if (this.rafId !== null && typeof cancelAnimationFrame === 'function') {\n cancelAnimationFrame(this.rafId);\n }\n\n this.rafId = null;\n this.resizeScheduled = false;\n }\n\n private performLayout(): void {\n if (!this.isInitialized || this.isDestroyed || !this.container) return;\n\n this.measureContainerMetrics();\n this.resizeAllItems();\n }\n\n private resizeAllItems(): void {\n const denominator = this.rowHeight + this.rowGap;\n\n this.gridItems.forEach((item) => {\n if (denominator <= 0 || !Number.isFinite(denominator)) {\n item.style.gridRowEnd = 'span 1';\n\n return;\n }\n\n const rowSpan = Math.max(\n 1,\n Math.ceil((item.getBoundingClientRect().height + this.rowGap) / denominator),\n );\n item.style.gridRowEnd = `span ${rowSpan}`;\n });\n }\n\n private setupAbortControllers(): void {\n this.observerAbortController = new AbortController();\n this.imageAbortController = new AbortController();\n\n this.observerAbortController.signal.addEventListener('abort', () => {\n this.resizeObserver?.disconnect();\n this.mutationObserver?.disconnect();\n });\n }\n\n private setupResizeObserver(): void {\n if (!this.container || typeof ResizeObserver === 'undefined') return;\n\n this.resizeObserver = new ResizeObserver(() => this.handleResize());\n\n this.resizeObserver.observe(this.container);\n }\n\n private setupMutationObserver(): void {\n if (!this.container || typeof MutationObserver === 'undefined') return;\n\n this.mutationObserver = new MutationObserver(() => {\n this.initializeGridItems();\n this.scheduleLayout();\n });\n\n this.mutationObserver.observe(this.container, {\n childList: true,\n subtree: false,\n });\n }\n\n private handleResize(): void {\n this.scheduleLayout();\n }\n\n private initializeContainerStyles(): void {\n if (!this.container) return;\n\n this.container.style.gridAutoRows = '1px';\n this.container.style.contain = 'layout';\n this.container.style.alignItems = 'start';\n }\n\n private measureContainerMetrics(): void {\n if (!this.container) return;\n\n const cs = getComputedStyle(this.container);\n\n this.rowGap = this.parseCssPixelValue(cs.rowGap);\n\n const parsedRowHeight = this.parseCssPixelValue(cs.gridAutoRows);\n\n this.rowHeight = parsedRowHeight > 0 ? parsedRowHeight : 1;\n }\n\n private initializeGridItems(): void {\n if (!this.container) return;\n\n this.gridItems = Array.from(this.container.children).filter(\n (item): item is HTMLElement => item instanceof HTMLElement,\n );\n\n this.gridItems.forEach((item) => {\n const images = item.querySelectorAll('img');\n\n images.forEach((image) => {\n this.observeImage(image);\n });\n });\n }\n\n private observeImage(image: HTMLImageElement): void {\n if (image.complete || this.observedImages.has(image)) return;\n\n this.observedImages.add(image);\n\n const onLoad = (): void => this.scheduleLayout();\n\n if (this.imageAbortController) {\n image.addEventListener('load', onLoad, {\n once: true,\n signal: this.imageAbortController.signal,\n });\n\n return;\n }\n\n image.addEventListener('load', onLoad, { once: true });\n }\n\n private parseCssPixelValue(value: string): number {\n const parsedValue = Number.parseFloat(value);\n\n return Number.isFinite(parsedValue) ? parsedValue : 0;\n }\n\n private storeContainerStyles(): void {\n if (!this.container) return;\n\n this.originalContainerStyles = {\n gridAutoRows: this.container.style.gridAutoRows || '',\n contain: this.container.style.contain || '',\n alignItems: this.container.style.alignItems || '',\n };\n }\n}\n"],"mappings":"AAIA,IAAqB,IAArB,MAAmC;AAAA,EACjC;AAAA,EACA,YAAwC;AAAA,EACxC,YAAmC,CAAA;AAAA,EACnC,YAAoB;AAAA,EACpB,SAAiB;AAAA,EACjB,kBAA0B;AAAA,EAC1B,QAA+B;AAAA,EAC/B,iBAAgD;AAAA,EAChD,mBAAoD;AAAA,EACpD,0BAA0D;AAAA,EAC1D,uBAAuD;AAAA,EACvD,iBAAyB,oBAAI,QAAA;AAAA,EAC7B,gBAAwB;AAAA,EACxB,cAAsB;AAAA,EACtB,0BAAkC;AAAA,IAChC,cAAc;AAAA,IACd,SAAS;AAAA,IACT,YAAY;AAAA;EAGd,YAAY,IAAgC,CAAA,GAAI;AAC9C,SAAK,kBAAkB,EAAQ;AAAA;EAGjC,OAAoB;AAClB,IAAI,KAAK,kBAET,KAAK,YAAY,KAAK,iBAAA,GAEjB,KAAK,cAEV,KAAK,gBAAgB,IACrB,KAAK,cAAc,IAEnB,KAAK,sBAAA,GACL,KAAK,qBAAA,GACL,KAAK,0BAAA,GACL,KAAK,oBAAA,GACL,KAAK,oBAAA,GACL,KAAK,sBAAA,GACL,KAAK,eAAA;AAAA;EAGP,UAAuB;AACrB,IAAI,CAAC,KAAK,iBAAiB,KAAK,eAAe,CAAC,KAAK,cAErD,KAAK,oBAAA,GACL,KAAK,eAAA;AAAA;EAGP,UAAuB;AACrB,IAAI,CAAC,KAAK,iBAAiB,CAAC,KAAK,cAEjC,KAAK,cAAc,IACnB,KAAK,gBAAgB,IACrB,KAAK,sBAAA,GACL,KAAK,yBAAyB,MAAA,GAC9B,KAAK,sBAAsB,MAAA,GAC3B,KAAK,gBAAgB,WAAA,GACrB,KAAK,kBAAkB,WAAA,GACvB,KAAK,UAAU,QAAA,CAAS,MAAS;AAC/B,MAAA,EAAK,MAAM,aAAa;AAAA,QAGtB,KAAK,cACP,KAAK,UAAU,MAAM,eAAe,KAAK,wBAAwB,cACjE,KAAK,UAAU,MAAM,UAAU,KAAK,wBAAwB,SAC5D,KAAK,UAAU,MAAM,aAAa,KAAK,wBAAwB,aAGjE,KAAK,YAAY,CAAA,GACjB,KAAK,YAAY,GACjB,KAAK,SAAS,GACd,KAAK,iBAAiB,MACtB,KAAK,mBAAmB,MACxB,KAAK,0BAA0B,MAC/B,KAAK,uBAAuB,MAC5B,KAAK,iBAAiB,oBAAI,QAAA,GAC1B,KAAK,kBAAkB,IACvB,KAAK,YAAY,MACjB,KAAK,0BAA0B;AAAA,MAC7B,cAAc;AAAA,MACd,SAAS;AAAA,MACT,YAAY;AAAA;;EAIhB,mBAA+C;AAC7C,WAAI,KAAK,2BAA2B,cAC3B,KAAK,kBAGV,OAAO,WAAa,MAAoB,OAExC,OAAO,KAAK,mBAAoB,WAC3B,SAAS,cAA2B,KAAK,eAAA,IAG3C,SAAS,cAA2B,UAAA;AAAA;EAG7C,iBAA+B;AAC7B,QAAI,GAAC,KAAK,iBAAiB,KAAK,eAAe,CAAC,KAAK,aAAa,KAAK,kBAIvE;AAAA,UAFA,KAAK,kBAAkB,IAEnB,OAAO,yBAA0B,YAAY;AAC/C,aAAK,QAAQ,sBAAA,MAA4B;AACvC,eAAK,QAAQ,MACb,KAAK,kBAAkB,IACvB,KAAK,cAAA;AAAA;AAGP;AAAA;AAGF,WAAK,QAAQ,MACb,KAAK,kBAAkB,IACvB,KAAK,cAAA;AAAA;AAAA;EAGP,wBAAsC;AACpC,IAAI,KAAK,UAAU,QAAQ,OAAO,wBAAyB,cACzD,qBAAqB,KAAK,KAAA,GAG5B,KAAK,QAAQ,MACb,KAAK,kBAAkB;AAAA;EAGzB,gBAA8B;AAC5B,IAAI,CAAC,KAAK,iBAAiB,KAAK,eAAe,CAAC,KAAK,cAErD,KAAK,wBAAA,GACL,KAAK,eAAA;AAAA;EAGP,iBAA+B;AAC7B,UAAM,IAAc,KAAK,YAAY,KAAK;AAE1C,SAAK,UAAU,QAAA,CAAS,MAAS;AAC/B,UAAI,KAAe,KAAK,CAAC,OAAO,SAAS,CAAA,GAAc;AACrD,QAAA,EAAK,MAAM,aAAa;AAExB;AAAA;AAGF,YAAM,IAAU,KAAK,IACnB,GACA,KAAK,MAAM,EAAK,sBAAA,EAAwB,SAAS,KAAK,UAAU,CAAA,CAAY;AAE9E,MAAA,EAAK,MAAM,aAAa,QAAQ,CAAA;AAAA;;EAIpC,wBAAsC;AACpC,SAAK,0BAA0B,IAAI,gBAAA,GACnC,KAAK,uBAAuB,IAAI,gBAAA,GAEhC,KAAK,wBAAwB,OAAO,iBAAiB,SAAA,MAAe;AAClE,WAAK,gBAAgB,WAAA,GACrB,KAAK,kBAAkB,WAAA;AAAA;;EAI3B,sBAAoC;AAClC,IAAI,CAAC,KAAK,aAAa,OAAO,iBAAmB,QAEjD,KAAK,iBAAiB,IAAI,eAAA,MAAqB,KAAK,aAAA,CAAc,GAElE,KAAK,eAAe,QAAQ,KAAK,SAAA;AAAA;EAGnC,wBAAsC;AACpC,IAAI,CAAC,KAAK,aAAa,OAAO,mBAAqB,QAEnD,KAAK,mBAAmB,IAAI,iBAAA,MAAuB;AACjD,WAAK,oBAAA,GACL,KAAK,eAAA;AAAA,QAGP,KAAK,iBAAiB,QAAQ,KAAK,WAAW;AAAA,MAC5C,WAAW;AAAA,MACX,SAAS;AAAA,KACV;AAAA;EAGH,eAA6B;AAC3B,SAAK,eAAA;AAAA;EAGP,4BAA0C;AACxC,IAAK,KAAK,cAEV,KAAK,UAAU,MAAM,eAAe,OACpC,KAAK,UAAU,MAAM,UAAU,UAC/B,KAAK,UAAU,MAAM,aAAa;AAAA;EAGpC,0BAAwC;AACtC,QAAI,CAAC,KAAK,UAAW;AAErB,UAAM,IAAK,iBAAiB,KAAK,SAAA;AAEjC,SAAK,SAAS,KAAK,mBAAmB,EAAG,MAAA;AAEzC,UAAM,IAAkB,KAAK,mBAAmB,EAAG,YAAA;AAEnD,SAAK,YAAY,IAAkB,IAAI,IAAkB;AAAA;EAG3D,sBAAoC;AAClC,IAAK,KAAK,cAEV,KAAK,YAAY,MAAM,KAAK,KAAK,UAAU,QAAA,EAAU,OAAA,CAClD,MAA8B,aAAgB,WAAA,GAGjD,KAAK,UAAU,QAAA,CAAS,MAAS;AAChB,MAAA,EAAK,iBAAiB,KAAA,EAE9B,QAAA,CAAS,MAAU;AACxB,aAAK,aAAa,CAAA;AAAA;;;EAKxB,aAAqB,GAA+B;AAClD,QAAI,EAAM,YAAY,KAAK,eAAe,IAAI,CAAA,EAAQ;AAEtD,SAAK,eAAe,IAAI,CAAA;AAExB,UAAM,IAAA,MAAqB,KAAK,eAAA;AAEhC,QAAI,KAAK,sBAAsB;AAC7B,MAAA,EAAM,iBAAiB,QAAQ,GAAQ;AAAA,QACrC,MAAM;AAAA,QACN,QAAQ,KAAK,qBAAqB;AAAA,OACnC;AAED;AAAA;AAGF,IAAA,EAAM,iBAAiB,QAAQ,GAAQ,EAAE,MAAM,GAAA,CAAM;AAAA;EAGvD,mBAA2B,GAAuB;AAChD,UAAM,IAAc,OAAO,WAAW,CAAA;AAEtC,WAAO,OAAO,SAAS,CAAA,IAAe,IAAc;AAAA;EAGtD,uBAAqC;AACnC,IAAK,KAAK,cAEV,KAAK,0BAA0B;AAAA,MAC7B,cAAc,KAAK,UAAU,MAAM,gBAAgB;AAAA,MACnD,SAAS,KAAK,UAAU,MAAM,WAAW;AAAA,MACzC,YAAY,KAAK,UAAU,MAAM,cAAc;AAAA"}
|
package/dist/index.umd.js
DELETED
|
@@ -1,3 +0,0 @@
|
|
|
1
|
-
(function(i,e){typeof exports=="object"&&typeof module<"u"?module.exports=e():typeof define=="function"&&define.amd?define([],e):(i=typeof globalThis<"u"?globalThis:i||self,i.MasonrySimple=e())})(this,function(){var i=class{containerOption;container=null;gridItems=[];rowHeight=1;rowGap=0;resizeScheduled=!1;rafId=null;resizeObserver=null;mutationObserver=null;observerAbortController=null;imageAbortController=null;observedImages=new WeakSet;isInitialized=!1;isDestroyed=!1;originalContainerStyles={gridAutoRows:"",contain:"",alignItems:""};constructor(e={}){this.containerOption=e.container}init(){this.isInitialized||(this.container=this.resolveContainer(),this.container&&(this.isInitialized=!0,this.isDestroyed=!1,this.setupAbortControllers(),this.storeContainerStyles(),this.initializeContainerStyles(),this.initializeGridItems(),this.setupResizeObserver(),this.setupMutationObserver(),this.scheduleLayout()))}refresh(){!this.isInitialized||this.isDestroyed||!this.container||(this.initializeGridItems(),this.scheduleLayout())}destroy(){!this.isInitialized&&!this.container||(this.isDestroyed=!0,this.isInitialized=!1,this.cancelScheduledLayout(),this.observerAbortController?.abort(),this.imageAbortController?.abort(),this.resizeObserver?.disconnect(),this.mutationObserver?.disconnect(),this.gridItems.forEach(e=>{e.style.gridRowEnd=""}),this.container&&(this.container.style.gridAutoRows=this.originalContainerStyles.gridAutoRows,this.container.style.contain=this.originalContainerStyles.contain,this.container.style.alignItems=this.originalContainerStyles.alignItems),this.gridItems=[],this.rowHeight=1,this.rowGap=0,this.resizeObserver=null,this.mutationObserver=null,this.observerAbortController=null,this.imageAbortController=null,this.observedImages=new WeakSet,this.resizeScheduled=!1,this.container=null,this.originalContainerStyles={gridAutoRows:"",contain:"",alignItems:""})}resolveContainer(){return this.containerOption instanceof HTMLElement?this.containerOption:typeof document>"u"?null:typeof this.containerOption=="string"?document.querySelector(this.containerOption):document.querySelector(".masonry")}scheduleLayout(){if(!(!this.isInitialized||this.isDestroyed||!this.container||this.resizeScheduled)){if(this.resizeScheduled=!0,typeof requestAnimationFrame=="function"){this.rafId=requestAnimationFrame(()=>{this.rafId=null,this.resizeScheduled=!1,this.performLayout()});return}this.rafId=null,this.resizeScheduled=!1,this.performLayout()}}cancelScheduledLayout(){this.rafId!==null&&typeof cancelAnimationFrame=="function"&&cancelAnimationFrame(this.rafId),this.rafId=null,this.resizeScheduled=!1}performLayout(){!this.isInitialized||this.isDestroyed||!this.container||(this.measureContainerMetrics(),this.resizeAllItems())}resizeAllItems(){const e=this.rowHeight+this.rowGap;this.gridItems.forEach(t=>{if(e<=0||!Number.isFinite(e)){t.style.gridRowEnd="span 1";return}const s=Math.max(1,Math.ceil((t.getBoundingClientRect().height+this.rowGap)/e));t.style.gridRowEnd=`span ${s}`})}setupAbortControllers(){this.observerAbortController=new AbortController,this.imageAbortController=new AbortController,this.observerAbortController.signal.addEventListener("abort",()=>{this.resizeObserver?.disconnect(),this.mutationObserver?.disconnect()})}setupResizeObserver(){!this.container||typeof ResizeObserver>"u"||(this.resizeObserver=new ResizeObserver(()=>this.handleResize()),this.resizeObserver.observe(this.container))}setupMutationObserver(){!this.container||typeof MutationObserver>"u"||(this.mutationObserver=new MutationObserver(()=>{this.initializeGridItems(),this.scheduleLayout()}),this.mutationObserver.observe(this.container,{childList:!0,subtree:!1}))}handleResize(){this.scheduleLayout()}initializeContainerStyles(){this.container&&(this.container.style.gridAutoRows="1px",this.container.style.contain="layout",this.container.style.alignItems="start")}measureContainerMetrics(){if(!this.container)return;const e=getComputedStyle(this.container);this.rowGap=this.parseCssPixelValue(e.rowGap);const t=this.parseCssPixelValue(e.gridAutoRows);this.rowHeight=t>0?t:1}initializeGridItems(){this.container&&(this.gridItems=Array.from(this.container.children).filter(e=>e instanceof HTMLElement),this.gridItems.forEach(e=>{e.querySelectorAll("img").forEach(t=>{this.observeImage(t)})}))}observeImage(e){if(e.complete||this.observedImages.has(e))return;this.observedImages.add(e);const t=()=>this.scheduleLayout();if(this.imageAbortController){e.addEventListener("load",t,{once:!0,signal:this.imageAbortController.signal});return}e.addEventListener("load",t,{once:!0})}parseCssPixelValue(e){const t=Number.parseFloat(e);return Number.isFinite(t)?t:0}storeContainerStyles(){this.container&&(this.originalContainerStyles={gridAutoRows:this.container.style.gridAutoRows||"",contain:this.container.style.contain||"",alignItems:this.container.style.alignItems||""})}};return i});
|
|
2
|
-
|
|
3
|
-
//# sourceMappingURL=index.umd.js.map
|
package/dist/index.umd.js.map
DELETED
|
@@ -1 +0,0 @@
|
|
|
1
|
-
{"version":3,"file":"index.umd.js","names":[],"sources":["../src/index.ts"],"sourcesContent":["interface MasonrySimpleOptions {\n container?: HTMLElement | string;\n}\n\nexport default class MasonrySimple {\n private readonly containerOption: HTMLElement | string | undefined;\n private container: HTMLElement | null = null;\n private gridItems: HTMLElement[] = [];\n private rowHeight = 1;\n private rowGap = 0;\n private resizeScheduled = false;\n private rafId: number | null = null;\n private resizeObserver: ResizeObserver | null = null;\n private mutationObserver: MutationObserver | null = null;\n private observerAbortController: AbortController | null = null;\n private imageAbortController: AbortController | null = null;\n private observedImages = new WeakSet<HTMLImageElement>();\n private isInitialized = false;\n private isDestroyed = false;\n private originalContainerStyles = {\n gridAutoRows: '',\n contain: '',\n alignItems: '',\n };\n\n constructor(options: MasonrySimpleOptions = {}) {\n this.containerOption = options.container;\n }\n\n public init(): void {\n if (this.isInitialized) return;\n\n this.container = this.resolveContainer();\n\n if (!this.container) return;\n\n this.isInitialized = true;\n this.isDestroyed = false;\n\n this.setupAbortControllers();\n this.storeContainerStyles();\n this.initializeContainerStyles();\n this.initializeGridItems();\n this.setupResizeObserver();\n this.setupMutationObserver();\n this.scheduleLayout();\n }\n\n public refresh(): void {\n if (!this.isInitialized || this.isDestroyed || !this.container) return;\n\n this.initializeGridItems();\n this.scheduleLayout();\n }\n\n public destroy(): void {\n if (!this.isInitialized && !this.container) return;\n\n this.isDestroyed = true;\n this.isInitialized = false;\n this.cancelScheduledLayout();\n this.observerAbortController?.abort();\n this.imageAbortController?.abort();\n this.resizeObserver?.disconnect();\n this.mutationObserver?.disconnect();\n this.gridItems.forEach((item) => {\n item.style.gridRowEnd = '';\n });\n\n if (this.container) {\n this.container.style.gridAutoRows = this.originalContainerStyles.gridAutoRows;\n this.container.style.contain = this.originalContainerStyles.contain;\n this.container.style.alignItems = this.originalContainerStyles.alignItems;\n }\n\n this.gridItems = [];\n this.rowHeight = 1;\n this.rowGap = 0;\n this.resizeObserver = null;\n this.mutationObserver = null;\n this.observerAbortController = null;\n this.imageAbortController = null;\n this.observedImages = new WeakSet<HTMLImageElement>();\n this.resizeScheduled = false;\n this.container = null;\n this.originalContainerStyles = {\n gridAutoRows: '',\n contain: '',\n alignItems: '',\n };\n }\n\n private resolveContainer(): HTMLElement | null {\n if (this.containerOption instanceof HTMLElement) {\n return this.containerOption;\n }\n\n if (typeof document === 'undefined') return null;\n\n if (typeof this.containerOption === 'string') {\n return document.querySelector<HTMLElement>(this.containerOption);\n }\n\n return document.querySelector<HTMLElement>('.masonry');\n }\n\n private scheduleLayout(): void {\n if (!this.isInitialized || this.isDestroyed || !this.container || this.resizeScheduled) return;\n\n this.resizeScheduled = true;\n\n if (typeof requestAnimationFrame === 'function') {\n this.rafId = requestAnimationFrame(() => {\n this.rafId = null;\n this.resizeScheduled = false;\n this.performLayout();\n });\n\n return;\n }\n\n this.rafId = null;\n this.resizeScheduled = false;\n this.performLayout();\n }\n\n private cancelScheduledLayout(): void {\n if (this.rafId !== null && typeof cancelAnimationFrame === 'function') {\n cancelAnimationFrame(this.rafId);\n }\n\n this.rafId = null;\n this.resizeScheduled = false;\n }\n\n private performLayout(): void {\n if (!this.isInitialized || this.isDestroyed || !this.container) return;\n\n this.measureContainerMetrics();\n this.resizeAllItems();\n }\n\n private resizeAllItems(): void {\n const denominator = this.rowHeight + this.rowGap;\n\n this.gridItems.forEach((item) => {\n if (denominator <= 0 || !Number.isFinite(denominator)) {\n item.style.gridRowEnd = 'span 1';\n\n return;\n }\n\n const rowSpan = Math.max(\n 1,\n Math.ceil((item.getBoundingClientRect().height + this.rowGap) / denominator),\n );\n item.style.gridRowEnd = `span ${rowSpan}`;\n });\n }\n\n private setupAbortControllers(): void {\n this.observerAbortController = new AbortController();\n this.imageAbortController = new AbortController();\n\n this.observerAbortController.signal.addEventListener('abort', () => {\n this.resizeObserver?.disconnect();\n this.mutationObserver?.disconnect();\n });\n }\n\n private setupResizeObserver(): void {\n if (!this.container || typeof ResizeObserver === 'undefined') return;\n\n this.resizeObserver = new ResizeObserver(() => this.handleResize());\n\n this.resizeObserver.observe(this.container);\n }\n\n private setupMutationObserver(): void {\n if (!this.container || typeof MutationObserver === 'undefined') return;\n\n this.mutationObserver = new MutationObserver(() => {\n this.initializeGridItems();\n this.scheduleLayout();\n });\n\n this.mutationObserver.observe(this.container, {\n childList: true,\n subtree: false,\n });\n }\n\n private handleResize(): void {\n this.scheduleLayout();\n }\n\n private initializeContainerStyles(): void {\n if (!this.container) return;\n\n this.container.style.gridAutoRows = '1px';\n this.container.style.contain = 'layout';\n this.container.style.alignItems = 'start';\n }\n\n private measureContainerMetrics(): void {\n if (!this.container) return;\n\n const cs = getComputedStyle(this.container);\n\n this.rowGap = this.parseCssPixelValue(cs.rowGap);\n\n const parsedRowHeight = this.parseCssPixelValue(cs.gridAutoRows);\n\n this.rowHeight = parsedRowHeight > 0 ? parsedRowHeight : 1;\n }\n\n private initializeGridItems(): void {\n if (!this.container) return;\n\n this.gridItems = Array.from(this.container.children).filter(\n (item): item is HTMLElement => item instanceof HTMLElement,\n );\n\n this.gridItems.forEach((item) => {\n const images = item.querySelectorAll('img');\n\n images.forEach((image) => {\n this.observeImage(image);\n });\n });\n }\n\n private observeImage(image: HTMLImageElement): void {\n if (image.complete || this.observedImages.has(image)) return;\n\n this.observedImages.add(image);\n\n const onLoad = (): void => this.scheduleLayout();\n\n if (this.imageAbortController) {\n image.addEventListener('load', onLoad, {\n once: true,\n signal: this.imageAbortController.signal,\n });\n\n return;\n }\n\n image.addEventListener('load', onLoad, { once: true });\n }\n\n private parseCssPixelValue(value: string): number {\n const parsedValue = Number.parseFloat(value);\n\n return Number.isFinite(parsedValue) ? parsedValue : 0;\n }\n\n private storeContainerStyles(): void {\n if (!this.container) return;\n\n this.originalContainerStyles = {\n gridAutoRows: this.container.style.gridAutoRows || '',\n contain: this.container.style.contain || '',\n alignItems: this.container.style.alignItems || '',\n };\n }\n}\n"],"mappings":"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"}
|