react-skeletonify 1.0.2 → 1.1.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 +102 -32
- package/dist/index.css +22 -10
- package/dist/index.css.map +1 -1
- package/dist/index.d.mts +27 -2
- package/dist/index.d.ts +27 -2
- package/dist/index.js +259 -30
- package/dist/index.js.map +1 -1
- package/dist/index.mjs +261 -30
- package/dist/index.mjs.map +1 -1
- package/package.json +1 -1
package/README.md
CHANGED
|
@@ -2,9 +2,10 @@
|
|
|
2
2
|
[](https://www.npmjs.com/package/react-skeletonify)
|
|
3
3
|
[](https://github.com/prettier/prettier)
|
|
4
4
|
|
|
5
|
-
# React Skeletonify
|
|
5
|
+
# ⚡ React Skeletonify
|
|
6
6
|
|
|
7
|
-
|
|
7
|
+
A **lightweight and flexible skeleton loader** for React, built to make loading states feel smooth and natural.
|
|
8
|
+
Unlike traditional static skeletons, **React Skeletonify** adapts to your components dynamically — letting you configure animations, styles, and exclusions globally or per-component.
|
|
8
9
|
|
|
9
10
|
## 🎮 Live Demo
|
|
10
11
|
|
|
@@ -12,10 +13,12 @@ React Skeletonify is a lightweight React skeleton loader component. Create beaut
|
|
|
12
13
|
|
|
13
14
|
## ✨ Features
|
|
14
15
|
|
|
15
|
-
-
|
|
16
|
-
-
|
|
17
|
-
-
|
|
18
|
-
-
|
|
16
|
+
- 🎨 **Global & local configuration** with `SkeletonProvider` and `SkeletonWrapper`
|
|
17
|
+
- ⚡ **Smooth animations** with multiple presets
|
|
18
|
+
- 🛠️ **Highly customizable** styles, backgrounds, borders, and speed
|
|
19
|
+
- 🧩 Works with **any React component**
|
|
20
|
+
- 🧃 Exclude tags or groups (text, form, media, etc.) from skeleton rendering
|
|
21
|
+
- 🪶 Lightweight, no external dependencies
|
|
19
22
|
|
|
20
23
|
## 🚀 Installation
|
|
21
24
|
|
|
@@ -25,32 +28,41 @@ npm install react-skeletonify
|
|
|
25
28
|
yarn add react-skeletonify
|
|
26
29
|
```
|
|
27
30
|
|
|
28
|
-
|
|
29
|
-
import "react-skeletonify/dist/index.css";
|
|
31
|
+
Import styles once:
|
|
30
32
|
|
|
33
|
+
```tsx
|
|
34
|
+
import "react-skeletonify/dist/index.css";
|
|
31
35
|
```
|
|
32
36
|
|
|
33
|
-
## Example
|
|
37
|
+
## 🔥 Quick Example
|
|
34
38
|
|
|
35
|
-
```
|
|
39
|
+
```tsx
|
|
36
40
|
import React from "react";
|
|
37
|
-
import { SkeletonWrapper } from "react-skeletonify";
|
|
41
|
+
import { SkeletonProvider, SkeletonWrapper } from "react-skeletonify";
|
|
38
42
|
import "react-skeletonify/dist/index.css";
|
|
39
43
|
|
|
40
44
|
function App() {
|
|
41
45
|
return (
|
|
42
|
-
<
|
|
43
|
-
|
|
44
|
-
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
46
|
+
<SkeletonProvider
|
|
47
|
+
config={{
|
|
48
|
+
animation: "animation-1",
|
|
49
|
+
borderRadius: "8px",
|
|
50
|
+
animationSpeed: 3,
|
|
51
|
+
}}>
|
|
52
|
+
<SkeletonWrapper loading={true}>
|
|
53
|
+
<div style={{ height: "120px", width: "400px", padding: "10px" }}>
|
|
54
|
+
<div
|
|
55
|
+
style={{
|
|
56
|
+
height: "50px",
|
|
57
|
+
width: "50px",
|
|
58
|
+
borderRadius: "100%",
|
|
59
|
+
marginBottom: "10px",
|
|
60
|
+
}}></div>
|
|
61
|
+
<h6>React Skeletonify</h6>
|
|
62
|
+
<p>This is an example with global provider config 🚀</p>
|
|
63
|
+
</div>
|
|
64
|
+
</SkeletonWrapper>
|
|
65
|
+
</SkeletonProvider>
|
|
54
66
|
);
|
|
55
67
|
}
|
|
56
68
|
|
|
@@ -59,23 +71,81 @@ export default App;
|
|
|
59
71
|
|
|
60
72
|
## ⚙️ API
|
|
61
73
|
|
|
62
|
-
###
|
|
74
|
+
### 🔹 `SkeletonProvider`
|
|
75
|
+
|
|
76
|
+
Provides **global configuration** for skeletons. Wrap your app (or part of it) in this provider.
|
|
77
|
+
|
|
78
|
+
| Prop | Type | Default | Description |
|
|
79
|
+
| -------- | ------------------------- | ------- | ---------------------- |
|
|
80
|
+
| children | `ReactNode` | `null` | Child components |
|
|
81
|
+
| config | `Partial<SkeletonConfig>` | `{}` | Global skeleton config |
|
|
82
|
+
| style | `CSSProperties` | `{}` | Inline style overrides |
|
|
83
|
+
|
|
84
|
+
---
|
|
85
|
+
|
|
86
|
+
### 🔹 `SkeletonWrapper`
|
|
87
|
+
|
|
88
|
+
Wraps **specific content** and applies skeletons when `loading` is true.
|
|
89
|
+
It can **inherit** from `SkeletonProvider` or override per instance.
|
|
90
|
+
|
|
91
|
+
| Prop | Type | Default | Description |
|
|
92
|
+
| -------------- | ------------------------- | ------- | ---------------------- |
|
|
93
|
+
| loading | `boolean` | `false` | Show skeleton if true |
|
|
94
|
+
| children | `ReactNode` | `null` | Content to render |
|
|
95
|
+
| overrideConfig | `Partial<SkeletonConfig>` | `{}` | Override global config |
|
|
96
|
+
| style | `CSSProperties` | `{}` | Inline style overrides |
|
|
97
|
+
|
|
98
|
+
---
|
|
99
|
+
|
|
100
|
+
## 🎨 Configuration Options (`SkeletonConfig`)
|
|
101
|
+
|
|
102
|
+
| Key | Type | Default | Description |
|
|
103
|
+
| --------------- | -------------------------------- | --------------- | -------------------- |
|
|
104
|
+
| animationSpeed | `number` | `3` | Speed of animation |
|
|
105
|
+
| background | `string` | `#aeaeae` | Background color |
|
|
106
|
+
| border | `string` | `"none"` | Border style |
|
|
107
|
+
| borderRadius | `string \| number` | `"0"` | Border radius |
|
|
108
|
+
| textTagsMargin | `string` | `"0"` | Margin for text tags |
|
|
109
|
+
| className | `string` | `""` | Custom class |
|
|
110
|
+
| style | `CSSProperties` | `{}` | Inline styles |
|
|
111
|
+
| animation | `"animation-1" \| "animation-2"` | `"animation-1"` | Animation type |
|
|
112
|
+
| exceptTags | `string[]` | `[]` | Excluded HTML tags |
|
|
113
|
+
| exceptTagGroups | `HtmlTagGroup[]` | `[]` | Excluded tag groups |
|
|
114
|
+
|
|
115
|
+
**Available Tag Groups:**
|
|
116
|
+
`TEXT_TAGS`, `STRUCTURE_TAGS`, `METADATA_TAGS`, `LIST_TAGS`, `TABLE_TAGS`, `FORM_TAGS`, `MEDIA_TAGS`, `INTERACTIVE_TAGS`, `MISC_TAGS`
|
|
117
|
+
|
|
118
|
+
---
|
|
119
|
+
|
|
120
|
+
## 📦 Example with `exceptTags`
|
|
121
|
+
|
|
122
|
+
```tsx
|
|
123
|
+
<SkeletonWrapper
|
|
124
|
+
loading={true}
|
|
125
|
+
overrideConfig={{
|
|
126
|
+
exceptTags: ["img", "button"],
|
|
127
|
+
borderRadius: "6px",
|
|
128
|
+
}}>
|
|
129
|
+
<div>
|
|
130
|
+
<img src="/profile.jpg" alt="Profile" />
|
|
131
|
+
<h2>Hello World</h2>
|
|
132
|
+
<button>Click me</button>
|
|
133
|
+
</div>
|
|
134
|
+
</SkeletonWrapper>
|
|
135
|
+
```
|
|
63
136
|
|
|
64
|
-
|
|
65
|
-
| :------: | :-------: | :-----: | :---------------------------------------: |
|
|
66
|
-
| loading | boolean | false | Whether to show skeletons or real content |
|
|
67
|
-
| children | ReactNode | null | Content you want wrapped with skeletons |
|
|
137
|
+
👉 In this case, the `img` and `button` will not be skeletonized.
|
|
68
138
|
|
|
69
|
-
## Versioning
|
|
139
|
+
## 📌 Versioning
|
|
70
140
|
|
|
71
141
|
We use [SemVer](http://semver.org/) for versioning. For the versions available, see the [versions](https://www.npmjs.com/package/react-skeletonify?activeTab=versions).
|
|
72
142
|
|
|
73
143
|
## 🤝 Contributing
|
|
74
144
|
|
|
75
|
-
Contributions, issues, and feature requests are welcome!
|
|
76
|
-
Feel free to open a PR or issue.
|
|
145
|
+
Contributions, issues, and feature requests are welcome! 🎉
|
|
146
|
+
Feel free to open a PR or an issue.
|
|
77
147
|
|
|
78
|
-
##
|
|
148
|
+
## 👨💻 Author
|
|
79
149
|
|
|
80
150
|
- **Sinan** - [GitHub](https://github.com/Sinan0333) · [Portfolio](http://sinan-dev.in)
|
|
81
151
|
|
package/dist/index.css
CHANGED
|
@@ -1,27 +1,39 @@
|
|
|
1
1
|
/* src/styles/skeleton.css */
|
|
2
|
-
.
|
|
3
|
-
animation: Rss-skeleton-loading 1s linear infinite alternate;
|
|
4
|
-
background-color: hsl(200, 20%, 90%);
|
|
2
|
+
.react-skeletonify {
|
|
5
3
|
color: transparent !important;
|
|
6
|
-
border: none !important;
|
|
7
4
|
outline: none !important;
|
|
8
5
|
pointer-events: none !important;
|
|
9
|
-
border-radius: 8px !important;
|
|
10
6
|
}
|
|
11
|
-
.
|
|
7
|
+
.react-skeletonify img {
|
|
12
8
|
opacity: 0;
|
|
13
9
|
}
|
|
14
|
-
.
|
|
10
|
+
.react-skeletonify a {
|
|
15
11
|
text-decoration: none !important;
|
|
16
12
|
color: transparent !important;
|
|
17
13
|
}
|
|
18
|
-
.
|
|
14
|
+
.react-skeletonify-text {
|
|
19
15
|
margin-top: 5px !important;
|
|
20
16
|
}
|
|
21
|
-
.
|
|
17
|
+
.react-skeletonify::placeholder {
|
|
22
18
|
color: transparent !important;
|
|
23
19
|
}
|
|
24
|
-
@keyframes
|
|
20
|
+
@keyframes react-skeletonify-animation-1 {
|
|
21
|
+
0% {
|
|
22
|
+
opacity: 1;
|
|
23
|
+
}
|
|
24
|
+
50% {
|
|
25
|
+
opacity: 0.4;
|
|
26
|
+
}
|
|
27
|
+
100% {
|
|
28
|
+
opacity: 1;
|
|
29
|
+
}
|
|
30
|
+
}
|
|
31
|
+
@keyframes react-skeletonify-animation-2 {
|
|
32
|
+
100% {
|
|
33
|
+
background-position: -100% 0;
|
|
34
|
+
}
|
|
35
|
+
}
|
|
36
|
+
@keyframes react-skeletonify-animation-3 {
|
|
25
37
|
0% {
|
|
26
38
|
background-color: hsl(200, 20%, 80%);
|
|
27
39
|
}
|
package/dist/index.css.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["../src/styles/skeleton.css"],"sourcesContent":[".
|
|
1
|
+
{"version":3,"sources":["../src/styles/skeleton.css"],"sourcesContent":[".react-skeletonify {\n color: transparent !important;\n outline: none !important;\n pointer-events: none !important;\n}\n.react-skeletonify img {\n opacity: 0;\n}\n.react-skeletonify a {\n text-decoration: none !important;\n color: transparent !important;\n}\n.react-skeletonify-text {\n margin-top: 5px !important;\n}\n.react-skeletonify::placeholder {\n color: transparent !important;\n}\n\n/* Animation 1 */\n/* animation: react-skeletonify-animation-1 3s ease-in-out infinite;\nanimation-delay: 0.5s; */\n@keyframes react-skeletonify-animation-1 {\n 0% {\n opacity: 1;\n }\n 50% {\n opacity: 0.4;\n }\n 100% {\n opacity: 1;\n }\n}\n\n/* Animation 2 */\n/* animation: react-skeletonify-animation-2 2s infinite;*/\n@keyframes react-skeletonify-animation-2 {\n 100% {\n background-position: -100% 0;\n }\n}\n\n/* Animation 3 */\n/* animation: react-skeletonify-animation-3 1s linear infinite alternate; */\n@keyframes react-skeletonify-animation-3 {\n 0% {\n background-color: hsl(200, 20%, 80%);\n }\n 100% {\n background-color: hsl(200, 20%, 95%);\n }\n}\n"],"mappings":";AAAA,CAAC;AACC,SAAO;AACP,WAAS;AACT,kBAAgB;AAClB;AACA,CALC,kBAKkB;AACjB,WAAS;AACX;AACA,CARC,kBAQkB;AACjB,mBAAiB;AACjB,SAAO;AACT;AACA,CAAC;AACC,cAAY;AACd;AACA,CAfC,iBAeiB;AAChB,SAAO;AACT;AAKA,WAAW;AACT;AACE,aAAS;AACX;AACA;AACE,aAAS;AACX;AACA;AACE,aAAS;AACX;AACF;AAIA,WAAW;AACT;AACE,yBAAqB,MAAM;AAC7B;AACF;AAIA,WAAW;AACT;AACE,sBAAkB,IAAI,GAAG,EAAE,GAAG,EAAE;AAClC;AACA;AACE,sBAAkB,IAAI,GAAG,EAAE,GAAG,EAAE;AAClC;AACF;","names":[]}
|
package/dist/index.d.mts
CHANGED
|
@@ -1,9 +1,34 @@
|
|
|
1
|
-
import React from 'react';
|
|
1
|
+
import React, { CSSProperties } from 'react';
|
|
2
|
+
|
|
3
|
+
declare const HTML_TAG_GROUPS: readonly ["TEXT_TAGS", "STRUCTURE_TAGS", "METADATA_TAGS", "LIST_TAGS", "TABLE_TAGS", "FORM_TAGS", "MEDIA_TAGS", "INTERACTIVE_TAGS", "MISC_TAGS"];
|
|
4
|
+
type HtmlTagGroup = (typeof HTML_TAG_GROUPS)[number];
|
|
5
|
+
type SkeletonConfig = {
|
|
6
|
+
animationSpeed: number;
|
|
7
|
+
background: string;
|
|
8
|
+
border: string;
|
|
9
|
+
borderRadius: string | number;
|
|
10
|
+
textTagsMargin: string;
|
|
11
|
+
className?: string;
|
|
12
|
+
style?: CSSProperties;
|
|
13
|
+
animation: "animation-1" | "animation-2";
|
|
14
|
+
exceptTags: string[];
|
|
15
|
+
exceptTagGroups: HtmlTagGroup[];
|
|
16
|
+
};
|
|
2
17
|
|
|
3
18
|
interface SkeletonWrapperProps {
|
|
4
19
|
loading: boolean;
|
|
5
20
|
children: React.ReactNode;
|
|
21
|
+
overrideConfig?: Partial<SkeletonConfig>;
|
|
22
|
+
style?: CSSProperties;
|
|
6
23
|
}
|
|
7
24
|
declare const SkeletonWrapper: React.FC<SkeletonWrapperProps>;
|
|
8
25
|
|
|
9
|
-
|
|
26
|
+
interface SkeletonProviderProps {
|
|
27
|
+
children: React.ReactNode;
|
|
28
|
+
config?: Partial<SkeletonConfig>;
|
|
29
|
+
style?: CSSProperties;
|
|
30
|
+
}
|
|
31
|
+
declare const SkeletonProvider: React.FC<SkeletonProviderProps>;
|
|
32
|
+
declare const useSkeleton: () => SkeletonConfig;
|
|
33
|
+
|
|
34
|
+
export { type SkeletonConfig, SkeletonProvider, SkeletonWrapper, useSkeleton };
|
package/dist/index.d.ts
CHANGED
|
@@ -1,9 +1,34 @@
|
|
|
1
|
-
import React from 'react';
|
|
1
|
+
import React, { CSSProperties } from 'react';
|
|
2
|
+
|
|
3
|
+
declare const HTML_TAG_GROUPS: readonly ["TEXT_TAGS", "STRUCTURE_TAGS", "METADATA_TAGS", "LIST_TAGS", "TABLE_TAGS", "FORM_TAGS", "MEDIA_TAGS", "INTERACTIVE_TAGS", "MISC_TAGS"];
|
|
4
|
+
type HtmlTagGroup = (typeof HTML_TAG_GROUPS)[number];
|
|
5
|
+
type SkeletonConfig = {
|
|
6
|
+
animationSpeed: number;
|
|
7
|
+
background: string;
|
|
8
|
+
border: string;
|
|
9
|
+
borderRadius: string | number;
|
|
10
|
+
textTagsMargin: string;
|
|
11
|
+
className?: string;
|
|
12
|
+
style?: CSSProperties;
|
|
13
|
+
animation: "animation-1" | "animation-2";
|
|
14
|
+
exceptTags: string[];
|
|
15
|
+
exceptTagGroups: HtmlTagGroup[];
|
|
16
|
+
};
|
|
2
17
|
|
|
3
18
|
interface SkeletonWrapperProps {
|
|
4
19
|
loading: boolean;
|
|
5
20
|
children: React.ReactNode;
|
|
21
|
+
overrideConfig?: Partial<SkeletonConfig>;
|
|
22
|
+
style?: CSSProperties;
|
|
6
23
|
}
|
|
7
24
|
declare const SkeletonWrapper: React.FC<SkeletonWrapperProps>;
|
|
8
25
|
|
|
9
|
-
|
|
26
|
+
interface SkeletonProviderProps {
|
|
27
|
+
children: React.ReactNode;
|
|
28
|
+
config?: Partial<SkeletonConfig>;
|
|
29
|
+
style?: CSSProperties;
|
|
30
|
+
}
|
|
31
|
+
declare const SkeletonProvider: React.FC<SkeletonProviderProps>;
|
|
32
|
+
declare const useSkeleton: () => SkeletonConfig;
|
|
33
|
+
|
|
34
|
+
export { type SkeletonConfig, SkeletonProvider, SkeletonWrapper, useSkeleton };
|
package/dist/index.js
CHANGED
|
@@ -30,10 +30,15 @@ var __toCommonJS = (mod) => __copyProps(__defProp({}, "__esModule", { value: tru
|
|
|
30
30
|
// src/index.tsx
|
|
31
31
|
var index_exports = {};
|
|
32
32
|
__export(index_exports, {
|
|
33
|
-
|
|
33
|
+
SkeletonProvider: () => SkeletonProvider,
|
|
34
|
+
SkeletonWrapper: () => SkeletonWrapper_default,
|
|
35
|
+
useSkeleton: () => useSkeleton
|
|
34
36
|
});
|
|
35
37
|
module.exports = __toCommonJS(index_exports);
|
|
36
38
|
|
|
39
|
+
// src/components/SkeletonWrapper.tsx
|
|
40
|
+
var import_react6 = require("react");
|
|
41
|
+
|
|
37
42
|
// src/components/SkeletonElement.tsx
|
|
38
43
|
var import_react4 = __toESM(require("react"));
|
|
39
44
|
|
|
@@ -42,18 +47,69 @@ var import_react3 = __toESM(require("react"));
|
|
|
42
47
|
|
|
43
48
|
// src/utils/create-node-wrapper.ts
|
|
44
49
|
var import_react = require("react");
|
|
45
|
-
function createNodeWrapper(node) {
|
|
46
|
-
var _a;
|
|
50
|
+
function createNodeWrapper(node, className, style) {
|
|
51
|
+
var _a, _b;
|
|
47
52
|
if (!node) return null;
|
|
48
53
|
return (0, import_react.createElement)(
|
|
49
54
|
"div",
|
|
50
55
|
{
|
|
51
|
-
className: (((_a = node == null ? void 0 : node.props) == null ? void 0 : _a.className) || "")
|
|
56
|
+
className: className + (((_a = node == null ? void 0 : node.props) == null ? void 0 : _a.className) || ""),
|
|
57
|
+
style: {
|
|
58
|
+
...style,
|
|
59
|
+
...(_b = node == null ? void 0 : node.props) == null ? void 0 : _b.style
|
|
60
|
+
}
|
|
52
61
|
},
|
|
53
62
|
node
|
|
54
63
|
);
|
|
55
64
|
}
|
|
56
65
|
|
|
66
|
+
// src/utils/create-leaf-node.ts
|
|
67
|
+
var import_react2 = __toESM(require("react"));
|
|
68
|
+
function createLeafNode(node, className, style) {
|
|
69
|
+
return import_react2.default.cloneElement(node, {
|
|
70
|
+
...node.props,
|
|
71
|
+
className: className + (node.props.className || ""),
|
|
72
|
+
style: {
|
|
73
|
+
...style,
|
|
74
|
+
...node.props.style
|
|
75
|
+
}
|
|
76
|
+
});
|
|
77
|
+
}
|
|
78
|
+
|
|
79
|
+
// src/utils/create-style.ts
|
|
80
|
+
var getAnimation = (animation, animationSpeed, background) => {
|
|
81
|
+
switch (animation) {
|
|
82
|
+
case "animation-1":
|
|
83
|
+
return {
|
|
84
|
+
animation: `react-skeletonify-animation-1 ${animationSpeed}s ease-in-out infinite `,
|
|
85
|
+
background,
|
|
86
|
+
animationDelay: "0.5s"
|
|
87
|
+
};
|
|
88
|
+
case "animation-2":
|
|
89
|
+
return {
|
|
90
|
+
animation: `react-skeletonify-animation-2 ${animationSpeed}s infinite`,
|
|
91
|
+
background: `linear-gradient(120deg, ${background} 30%, #f0f0f0 38%, #f0f0f0 40%, ${background} 48%)`,
|
|
92
|
+
backgroundSize: "200% 100%",
|
|
93
|
+
backgroundPosition: "100% 0"
|
|
94
|
+
};
|
|
95
|
+
case "animation-3":
|
|
96
|
+
return {
|
|
97
|
+
animation: `react-skeletonify-animation-3 ${animationSpeed}s linear infinite alternate`,
|
|
98
|
+
backgroundColor: background
|
|
99
|
+
};
|
|
100
|
+
}
|
|
101
|
+
};
|
|
102
|
+
var create_style_default = (config) => {
|
|
103
|
+
const { animationSpeed, background, border, borderRadius, animation, style } = config;
|
|
104
|
+
const skeletonAnimation = {
|
|
105
|
+
...getAnimation(animation, animationSpeed, background),
|
|
106
|
+
border,
|
|
107
|
+
borderRadius,
|
|
108
|
+
...style
|
|
109
|
+
};
|
|
110
|
+
return skeletonAnimation;
|
|
111
|
+
};
|
|
112
|
+
|
|
57
113
|
// src/constants/tags.ts
|
|
58
114
|
var TEXT_TAGS = [
|
|
59
115
|
"p",
|
|
@@ -64,36 +120,161 @@ var TEXT_TAGS = [
|
|
|
64
120
|
"h4",
|
|
65
121
|
"h5",
|
|
66
122
|
"h6",
|
|
67
|
-
"
|
|
123
|
+
"b",
|
|
124
|
+
"strong",
|
|
125
|
+
"i",
|
|
126
|
+
"em",
|
|
127
|
+
"u",
|
|
128
|
+
"mark",
|
|
129
|
+
"small",
|
|
130
|
+
"sup",
|
|
131
|
+
"sub",
|
|
132
|
+
"abbr",
|
|
133
|
+
"cite",
|
|
134
|
+
"q",
|
|
135
|
+
"blockquote",
|
|
136
|
+
"code",
|
|
137
|
+
"pre",
|
|
138
|
+
"samp",
|
|
139
|
+
"kbd",
|
|
140
|
+
"var",
|
|
141
|
+
"time",
|
|
142
|
+
"br",
|
|
143
|
+
"wbr"
|
|
144
|
+
];
|
|
145
|
+
var STRUCTURE_TAGS = [
|
|
146
|
+
"html",
|
|
147
|
+
"head",
|
|
148
|
+
"body",
|
|
149
|
+
"main",
|
|
150
|
+
"header",
|
|
151
|
+
"footer",
|
|
152
|
+
"nav",
|
|
153
|
+
"section",
|
|
154
|
+
"article",
|
|
155
|
+
"aside"
|
|
156
|
+
];
|
|
157
|
+
var METADATA_TAGS = ["base", "link", "meta", "style", "title"];
|
|
158
|
+
var LIST_TAGS = ["ul", "ol", "li", "dl", "dt", "dd"];
|
|
159
|
+
var TABLE_TAGS = [
|
|
160
|
+
"table",
|
|
161
|
+
"caption",
|
|
162
|
+
"thead",
|
|
163
|
+
"tbody",
|
|
164
|
+
"tfoot",
|
|
165
|
+
"tr",
|
|
166
|
+
"th",
|
|
167
|
+
"td",
|
|
168
|
+
"col",
|
|
169
|
+
"colgroup"
|
|
170
|
+
];
|
|
171
|
+
var FORM_TAGS = [
|
|
172
|
+
"form",
|
|
173
|
+
"input",
|
|
174
|
+
"textarea",
|
|
175
|
+
"button",
|
|
176
|
+
"label",
|
|
177
|
+
"select",
|
|
178
|
+
"option",
|
|
179
|
+
"optgroup",
|
|
180
|
+
"fieldset",
|
|
181
|
+
"legend",
|
|
182
|
+
"datalist",
|
|
183
|
+
"output",
|
|
184
|
+
"meter",
|
|
185
|
+
"progress"
|
|
186
|
+
];
|
|
187
|
+
var MEDIA_TAGS = [
|
|
188
|
+
"img",
|
|
189
|
+
"audio",
|
|
190
|
+
"video",
|
|
191
|
+
"source",
|
|
192
|
+
"track",
|
|
193
|
+
"picture",
|
|
194
|
+
"iframe",
|
|
195
|
+
"embed",
|
|
196
|
+
"object",
|
|
197
|
+
"map",
|
|
198
|
+
"area",
|
|
199
|
+
"canvas"
|
|
200
|
+
];
|
|
201
|
+
var INTERACTIVE_TAGS = [
|
|
202
|
+
"details",
|
|
203
|
+
"summary",
|
|
204
|
+
"dialog",
|
|
205
|
+
"script",
|
|
206
|
+
"noscript",
|
|
207
|
+
"template"
|
|
68
208
|
];
|
|
209
|
+
var MISC_TAGS = ["ins", "del", "s", "bdi", "bdo", "ruby", "rt", "rp"];
|
|
69
210
|
|
|
70
|
-
// src/utils/
|
|
71
|
-
|
|
72
|
-
|
|
73
|
-
|
|
74
|
-
|
|
75
|
-
|
|
211
|
+
// src/utils/check-tag-in-group.ts
|
|
212
|
+
function checkTagInGroup(tag, groups) {
|
|
213
|
+
return groups.some((group) => {
|
|
214
|
+
switch (group) {
|
|
215
|
+
case "TEXT_TAGS":
|
|
216
|
+
return TEXT_TAGS.includes(tag);
|
|
217
|
+
case "STRUCTURE_TAGS":
|
|
218
|
+
return STRUCTURE_TAGS.includes(tag);
|
|
219
|
+
case "METADATA_TAGS":
|
|
220
|
+
return METADATA_TAGS.includes(tag);
|
|
221
|
+
case "LIST_TAGS":
|
|
222
|
+
return LIST_TAGS.includes(tag);
|
|
223
|
+
case "TABLE_TAGS":
|
|
224
|
+
return TABLE_TAGS.includes(tag);
|
|
225
|
+
case "FORM_TAGS":
|
|
226
|
+
return FORM_TAGS.includes(tag);
|
|
227
|
+
case "MEDIA_TAGS":
|
|
228
|
+
return MEDIA_TAGS.includes(tag);
|
|
229
|
+
case "INTERACTIVE_TAGS":
|
|
230
|
+
return INTERACTIVE_TAGS.includes(tag);
|
|
231
|
+
case "MISC_TAGS":
|
|
232
|
+
return MISC_TAGS.includes(tag);
|
|
233
|
+
}
|
|
76
234
|
});
|
|
77
235
|
}
|
|
78
236
|
|
|
237
|
+
// src/utils/is-text-element.ts
|
|
238
|
+
var is_text_element_default = (elementType) => {
|
|
239
|
+
return TEXT_TAGS.includes(elementType) || LIST_TAGS.includes(elementType);
|
|
240
|
+
};
|
|
241
|
+
|
|
79
242
|
// src/hooks/useAddSkelton.ts
|
|
80
|
-
function useAddSkelton() {
|
|
243
|
+
function useAddSkelton(config) {
|
|
244
|
+
const { className, exceptTags, exceptTagGroups, textTagsMargin } = config;
|
|
245
|
+
const CLASS_NAME = `react-skeletonify ${className} `;
|
|
246
|
+
const style = create_style_default(config);
|
|
81
247
|
const addSkeleton = (node) => {
|
|
82
|
-
if (!import_react3.default.isValidElement(node))
|
|
248
|
+
if (!import_react3.default.isValidElement(node))
|
|
249
|
+
return createNodeWrapper(node, CLASS_NAME, style);
|
|
83
250
|
const element = node;
|
|
84
251
|
const { children } = element.props;
|
|
85
252
|
const elementType = element.type;
|
|
253
|
+
if (typeof elementType === "string") {
|
|
254
|
+
if (exceptTags.includes(elementType)) {
|
|
255
|
+
return element;
|
|
256
|
+
}
|
|
257
|
+
const isRestrictedGroupTag = checkTagInGroup(
|
|
258
|
+
elementType,
|
|
259
|
+
exceptTagGroups
|
|
260
|
+
);
|
|
261
|
+
if (isRestrictedGroupTag) return element;
|
|
262
|
+
}
|
|
86
263
|
const hasChildren = import_react3.default.Children.count(children) > 0;
|
|
87
264
|
const isValidChildren = typeof children !== "string";
|
|
88
265
|
if (typeof elementType === "function") {
|
|
89
266
|
const rendered = elementType(element.props);
|
|
90
267
|
return addSkeleton(rendered);
|
|
91
268
|
}
|
|
92
|
-
|
|
93
|
-
|
|
269
|
+
const isTextTag = is_text_element_default(elementType);
|
|
270
|
+
if (isTextTag) {
|
|
271
|
+
return createLeafNode(element, CLASS_NAME, {
|
|
272
|
+
...style,
|
|
273
|
+
margin: textTagsMargin
|
|
274
|
+
});
|
|
94
275
|
}
|
|
95
276
|
if (elementType === "img") {
|
|
96
|
-
return createNodeWrapper(element);
|
|
277
|
+
return createNodeWrapper(element, CLASS_NAME, style);
|
|
97
278
|
}
|
|
98
279
|
if (hasChildren && isValidChildren) {
|
|
99
280
|
const childWithSkeletons = import_react3.default.Children.map(children, addSkeleton);
|
|
@@ -102,36 +283,84 @@ function useAddSkelton() {
|
|
|
102
283
|
children: childWithSkeletons
|
|
103
284
|
});
|
|
104
285
|
}
|
|
105
|
-
return createLeafNode(element);
|
|
286
|
+
return createLeafNode(element, CLASS_NAME, style);
|
|
106
287
|
};
|
|
107
288
|
return addSkeleton;
|
|
108
289
|
}
|
|
109
290
|
var useAddSkelton_default = useAddSkelton;
|
|
110
291
|
|
|
111
292
|
// src/components/SkeletonElement.tsx
|
|
112
|
-
var
|
|
113
|
-
|
|
114
|
-
|
|
115
|
-
|
|
116
|
-
const addSkeleton = useAddSkelton_default();
|
|
117
|
-
return /* @__PURE__ */ (0, import_jsx_runtime.jsx)("div", { className: "skeleton-container", children: import_react4.default.Children.map(children, (child) => addSkeleton(child)) });
|
|
293
|
+
var SkeletonElement = (props) => {
|
|
294
|
+
const { children, config } = props;
|
|
295
|
+
const addSkeleton = useAddSkelton_default(config);
|
|
296
|
+
return import_react4.default.Children.map(children, (child) => addSkeleton(child));
|
|
118
297
|
};
|
|
119
298
|
var SkeletonElement_default = SkeletonElement;
|
|
120
299
|
|
|
300
|
+
// src/context/SkeletonContext.tsx
|
|
301
|
+
var import_react5 = require("react");
|
|
302
|
+
|
|
303
|
+
// src/context/skeleton-config.ts
|
|
304
|
+
var defaultBackground = {
|
|
305
|
+
"animation-1": "#aeaeae",
|
|
306
|
+
"animation-2": "#e5e5e5",
|
|
307
|
+
"animation-3": "hsl(210, 20%, 90%)"
|
|
308
|
+
};
|
|
309
|
+
var defaultValues = {
|
|
310
|
+
animationSpeed: 3,
|
|
311
|
+
background: "#aeaeae",
|
|
312
|
+
border: "none",
|
|
313
|
+
borderRadius: "0",
|
|
314
|
+
textTagsMargin: "0",
|
|
315
|
+
className: "",
|
|
316
|
+
style: {},
|
|
317
|
+
animation: "animation-1",
|
|
318
|
+
exceptTags: [],
|
|
319
|
+
exceptTagGroups: []
|
|
320
|
+
};
|
|
321
|
+
|
|
322
|
+
// src/context/SkeletonContext.tsx
|
|
323
|
+
var import_jsx_runtime = require("react/jsx-runtime");
|
|
324
|
+
var SkeletonContext = (0, import_react5.createContext)(defaultValues);
|
|
325
|
+
var SkeletonProvider = (props) => {
|
|
326
|
+
const { children, config, style } = props;
|
|
327
|
+
const { animation = defaultValues.animation, background } = config || {};
|
|
328
|
+
const value = (0, import_react5.useMemo)(
|
|
329
|
+
() => ({
|
|
330
|
+
...defaultValues,
|
|
331
|
+
...config,
|
|
332
|
+
background: background ? background : defaultBackground[animation],
|
|
333
|
+
style: { ...defaultValues.style, ...config == null ? void 0 : config.style, ...style }
|
|
334
|
+
}),
|
|
335
|
+
[animation, background, config, style]
|
|
336
|
+
);
|
|
337
|
+
return /* @__PURE__ */ (0, import_jsx_runtime.jsx)(SkeletonContext.Provider, { value, children });
|
|
338
|
+
};
|
|
339
|
+
var useSkeleton = () => (0, import_react5.useContext)(SkeletonContext);
|
|
340
|
+
|
|
121
341
|
// src/components/SkeletonWrapper.tsx
|
|
122
342
|
var import_jsx_runtime2 = require("react/jsx-runtime");
|
|
123
|
-
var SkeletonWrapper = ({
|
|
124
|
-
loading,
|
|
125
|
-
|
|
126
|
-
|
|
343
|
+
var SkeletonWrapper = (props) => {
|
|
344
|
+
const { loading, children, overrideConfig, style } = props;
|
|
345
|
+
const mainConfig = useSkeleton();
|
|
346
|
+
const config = (0, import_react6.useMemo)(
|
|
347
|
+
() => ({
|
|
348
|
+
...mainConfig,
|
|
349
|
+
...overrideConfig,
|
|
350
|
+
style: { ...mainConfig.style, ...overrideConfig == null ? void 0 : overrideConfig.style, ...style }
|
|
351
|
+
}),
|
|
352
|
+
[overrideConfig, mainConfig]
|
|
353
|
+
);
|
|
127
354
|
if (loading) {
|
|
128
|
-
return /* @__PURE__ */ (0, import_jsx_runtime2.jsx)(SkeletonElement_default, { children });
|
|
355
|
+
return /* @__PURE__ */ (0, import_jsx_runtime2.jsx)(SkeletonElement_default, { config, children });
|
|
129
356
|
}
|
|
130
|
-
return
|
|
357
|
+
return children;
|
|
131
358
|
};
|
|
132
359
|
var SkeletonWrapper_default = SkeletonWrapper;
|
|
133
360
|
// Annotate the CommonJS export names for ESM import in node:
|
|
134
361
|
0 && (module.exports = {
|
|
135
|
-
|
|
362
|
+
SkeletonProvider,
|
|
363
|
+
SkeletonWrapper,
|
|
364
|
+
useSkeleton
|
|
136
365
|
});
|
|
137
366
|
//# sourceMappingURL=index.js.map
|
package/dist/index.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["../src/index.tsx","../src/components/SkeletonElement.tsx","../src/hooks/useAddSkelton.ts","../src/utils/create-node-wrapper.ts","../src/constants/tags.ts","../src/utils/create-leaf-node.ts","../src/components/SkeletonWrapper.tsx"],"sourcesContent":["import \"./styles/skeleton.css\";\n\nexport { default as SkeletonWrapper } from \"./components/SkeletonWrapper\";\n","import React from \"react\";\nimport useAddSkelton from \"../hooks/useAddSkelton\";\n\nconst SkeletonElement: React.FC<{ children: React.ReactNode }> = ({\n children,\n}) => {\n const addSkeleton = useAddSkelton();\n return (\n <div className=\"skeleton-container\">\n {React.Children.map(children, (child) => addSkeleton(child))}\n </div>\n );\n};\n\nexport default SkeletonElement;\n","import React from \"react\";\nimport createNodeWrapper from \"../utils/create-node-wrapper\";\nimport { TEXT_TAGS } from \"../constants/tags\";\nimport createLeafNode from \"../utils/create-leaf-node\";\n\nfunction useAddSkelton() {\n const addSkeleton = (node: React.ReactNode): React.ReactNode => {\n if (!React.isValidElement(node)) return createNodeWrapper(node as any);\n\n const element = node as React.ReactElement<any>;\n const { children } = element.props;\n const elementType = element.type;\n\n const hasChildren = React.Children.count(children) > 0;\n const isValidChildren = typeof children !== \"string\";\n\n if (typeof elementType === \"function\") {\n const rendered = (elementType as any)(element.props);\n return addSkeleton(rendered);\n }\n\n if (TEXT_TAGS.includes(elementType)) {\n return createLeafNode(node, \"Rss-skeleton-text\");\n }\n\n if (elementType === \"img\") {\n return createNodeWrapper(element);\n }\n\n if (hasChildren && isValidChildren) {\n const childWithSkeletons = React.Children.map(children, addSkeleton);\n\n return React.cloneElement(element, {\n ...element.props,\n children: childWithSkeletons,\n } as typeof element.props);\n }\n\n return createLeafNode(element);\n };\n\n return addSkeleton;\n}\n\nexport default useAddSkelton;\n","import React, { createElement } from \"react\";\n\nexport default function createNodeWrapper(node: React.ReactElement<any>) {\n if (!node) return null;\n\n return createElement(\n \"div\",\n {\n className: (node?.props?.className || \"\") + \" Rss-skeleton\",\n },\n node\n );\n}\n","export const TEXT_TAGS = [\n \"p\",\n \"span\",\n \"h1\",\n \"h2\",\n \"h3\",\n \"h4\",\n \"h5\",\n \"h6\",\n \"li\",\n];\n","import React from \"react\";\n\nexport default function createLeafNode(\n node: React.ReactElement<any>,\n className: string = \"\"\n): React.ReactElement {\n return React.cloneElement(node, {\n ...node.props,\n className: (node.props.className || \"\") + \" Rss-skeleton \" + className,\n } as typeof node.props);\n}\n","import React from \"react\";\nimport SkeletonElement from \"./SkeletonElement\";\n\ninterface SkeletonWrapperProps {\n loading: boolean;\n children: React.ReactNode;\n}\n\nconst SkeletonWrapper: React.FC<SkeletonWrapperProps> = ({\n loading,\n children,\n}) => {\n if (loading) {\n return <SkeletonElement>{children}</SkeletonElement>;\n }\n return <>{children}</>;\n};\n\nexport default SkeletonWrapper;\n"],"mappings":";;;;;;;;;;;;;;;;;;;;;;;;;;;;;;AAAA;AAAA;AAAA;AAAA;AAAA;;;ACAA,IAAAA,gBAAkB;;;ACAlB,IAAAC,gBAAkB;;;ACAlB,mBAAqC;AAEtB,SAAR,kBAAmC,MAA+B;AAFzE;AAGE,MAAI,CAAC,KAAM,QAAO;AAElB,aAAO;AAAA,IACL;AAAA,IACA;AAAA,MACE,cAAY,kCAAM,UAAN,mBAAa,cAAa,MAAM;AAAA,IAC9C;AAAA,IACA;AAAA,EACF;AACF;;;ACZO,IAAM,YAAY;AAAA,EACvB;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AACF;;;ACVA,IAAAC,gBAAkB;AAEH,SAAR,eACL,MACA,YAAoB,IACA;AACpB,SAAO,cAAAC,QAAM,aAAa,MAAM;AAAA,IAC9B,GAAG,KAAK;AAAA,IACR,YAAY,KAAK,MAAM,aAAa,MAAM,mBAAmB;AAAA,EAC/D,CAAsB;AACxB;;;AHLA,SAAS,gBAAgB;AACvB,QAAM,cAAc,CAAC,SAA2C;AAC9D,QAAI,CAAC,cAAAC,QAAM,eAAe,IAAI,EAAG,QAAO,kBAAkB,IAAW;AAErE,UAAM,UAAU;AAChB,UAAM,EAAE,SAAS,IAAI,QAAQ;AAC7B,UAAM,cAAc,QAAQ;AAE5B,UAAM,cAAc,cAAAA,QAAM,SAAS,MAAM,QAAQ,IAAI;AACrD,UAAM,kBAAkB,OAAO,aAAa;AAE5C,QAAI,OAAO,gBAAgB,YAAY;AACrC,YAAM,WAAY,YAAoB,QAAQ,KAAK;AACnD,aAAO,YAAY,QAAQ;AAAA,IAC7B;AAEA,QAAI,UAAU,SAAS,WAAW,GAAG;AACnC,aAAO,eAAe,MAAM,mBAAmB;AAAA,IACjD;AAEA,QAAI,gBAAgB,OAAO;AACzB,aAAO,kBAAkB,OAAO;AAAA,IAClC;AAEA,QAAI,eAAe,iBAAiB;AAClC,YAAM,qBAAqB,cAAAA,QAAM,SAAS,IAAI,UAAU,WAAW;AAEnE,aAAO,cAAAA,QAAM,aAAa,SAAS;AAAA,QACjC,GAAG,QAAQ;AAAA,QACX,UAAU;AAAA,MACZ,CAAyB;AAAA,IAC3B;AAEA,WAAO,eAAe,OAAO;AAAA,EAC/B;AAEA,SAAO;AACT;AAEA,IAAO,wBAAQ;;;ADpCX;AALJ,IAAM,kBAA2D,CAAC;AAAA,EAChE;AACF,MAAM;AACJ,QAAM,cAAc,sBAAc;AAClC,SACE,4CAAC,SAAI,WAAU,sBACZ,wBAAAC,QAAM,SAAS,IAAI,UAAU,CAAC,UAAU,YAAY,KAAK,CAAC,GAC7D;AAEJ;AAEA,IAAO,0BAAQ;;;AKDJ,IAAAC,sBAAA;AALX,IAAM,kBAAkD,CAAC;AAAA,EACvD;AAAA,EACA;AACF,MAAM;AACJ,MAAI,SAAS;AACX,WAAO,6CAAC,2BAAiB,UAAS;AAAA,EACpC;AACA,SAAO,6EAAG,UAAS;AACrB;AAEA,IAAO,0BAAQ;","names":["import_react","import_react","import_react","React","React","React","import_jsx_runtime"]}
|
|
1
|
+
{"version":3,"sources":["../src/index.tsx","../src/components/SkeletonWrapper.tsx","../src/components/SkeletonElement.tsx","../src/hooks/useAddSkelton.ts","../src/utils/create-node-wrapper.ts","../src/utils/create-leaf-node.ts","../src/utils/create-style.ts","../src/constants/tags.ts","../src/utils/check-tag-in-group.ts","../src/utils/is-text-element.ts","../src/context/SkeletonContext.tsx","../src/context/skeleton-config.ts"],"sourcesContent":["import \"./styles/skeleton.css\";\n\nexport { default as SkeletonWrapper } from \"./components/SkeletonWrapper\";\nexport { SkeletonProvider, useSkeleton } from \"./context/SkeletonContext\";\nexport type { SkeletonConfig } from \"./context/skeleton-config\";\n","import React, { CSSProperties, useMemo } from \"react\";\nimport SkeletonElement from \"./SkeletonElement\";\nimport { SkeletonConfig } from \"../context/skeleton-config\";\nimport { useSkeleton } from \"../context/SkeletonContext\";\n\ninterface SkeletonWrapperProps {\n loading: boolean;\n children: React.ReactNode;\n overrideConfig?: Partial<SkeletonConfig>;\n style?: CSSProperties;\n}\n\nconst SkeletonWrapper: React.FC<SkeletonWrapperProps> = (props) => {\n const { loading, children, overrideConfig, style } = props;\n const mainConfig = useSkeleton();\n\n const config: SkeletonConfig = useMemo(\n () => ({\n ...mainConfig,\n ...overrideConfig,\n style: { ...mainConfig.style, ...overrideConfig?.style, ...style },\n }),\n [overrideConfig, mainConfig]\n );\n\n if (loading) {\n return <SkeletonElement config={config}>{children}</SkeletonElement>;\n }\n return children;\n};\n\nexport default SkeletonWrapper;\n","import React from \"react\";\nimport useAddSkelton from \"../hooks/useAddSkelton\";\nimport { SkeletonConfig } from \"../context/skeleton-config\";\n\ninterface SkeletonElementProps {\n children: React.ReactNode;\n config: SkeletonConfig;\n}\n\nconst SkeletonElement: React.FC<SkeletonElementProps> = (props) => {\n const { children, config } = props;\n const addSkeleton = useAddSkelton(config);\n\n return React.Children.map(children, (child) => addSkeleton(child));\n};\n\nexport default SkeletonElement;\n","import React from \"react\";\nimport createNodeWrapper from \"../utils/create-node-wrapper\";\nimport createLeafNode from \"../utils/create-leaf-node\";\nimport { SkeletonConfig } from \"../context/skeleton-config\";\nimport createStyle from \"../utils/create-style\";\nimport checkTagInGroup from \"../utils/check-tag-in-group\";\nimport isTextElement from \"../utils/is-text-element\";\n\nfunction useAddSkelton(config: SkeletonConfig) {\n const { className, exceptTags, exceptTagGroups, textTagsMargin } = config;\n const CLASS_NAME = `react-skeletonify ${className} `;\n const style = createStyle(config);\n\n const addSkeleton = (node: React.ReactNode): React.ReactNode => {\n if (!React.isValidElement(node))\n return createNodeWrapper(node as any, CLASS_NAME, style);\n\n const element = node as React.ReactElement<any>;\n const { children } = element.props;\n const elementType = element.type;\n\n if (typeof elementType === \"string\") {\n if (exceptTags.includes(elementType)) {\n return element;\n }\n const isRestrictedGroupTag = checkTagInGroup(\n elementType,\n exceptTagGroups\n );\n\n if (isRestrictedGroupTag) return element;\n }\n\n const hasChildren = React.Children.count(children) > 0;\n const isValidChildren = typeof children !== \"string\";\n\n if (typeof elementType === \"function\") {\n const rendered = (elementType as any)(element.props);\n return addSkeleton(rendered);\n }\n\n const isTextTag = isTextElement(elementType);\n\n if (isTextTag) {\n return createLeafNode(element, CLASS_NAME, {\n ...style,\n margin: textTagsMargin,\n });\n }\n\n if (elementType === \"img\") {\n return createNodeWrapper(element, CLASS_NAME, style);\n }\n\n if (hasChildren && isValidChildren) {\n const childWithSkeletons = React.Children.map(children, addSkeleton);\n\n return React.cloneElement(element, {\n ...element.props,\n children: childWithSkeletons,\n } as typeof element.props);\n }\n\n return createLeafNode(element, CLASS_NAME, style);\n };\n\n return addSkeleton;\n}\n\nexport default useAddSkelton;\n","import React, { createElement, CSSProperties } from \"react\";\n\nexport default function createNodeWrapper(\n node: React.ReactElement<any>,\n className: string,\n style: CSSProperties\n) {\n if (!node) return null;\n\n return createElement(\n \"div\",\n {\n className: className + (node?.props?.className || \"\"),\n style: {\n ...style,\n ...node?.props?.style,\n },\n },\n node\n );\n}\n","import React, { CSSProperties } from \"react\";\n\nexport default function createLeafNode(\n node: React.ReactElement<any>,\n className: string,\n style: CSSProperties\n): React.ReactElement {\n return React.cloneElement(node, {\n ...node.props,\n className: className + (node.props.className || \"\"),\n style: {\n ...style,\n ...node.props.style,\n },\n } as typeof node.props);\n}\n","import { CSSProperties } from \"react\";\nimport { SkeletonConfig } from \"../context/skeleton-config\";\n\nconst getAnimation = (\n animation: string,\n animationSpeed: number,\n background: string\n) => {\n switch (animation) {\n case \"animation-1\":\n return {\n animation: `react-skeletonify-animation-1 ${animationSpeed}s ease-in-out infinite `,\n background: background,\n animationDelay: \"0.5s\",\n };\n case \"animation-2\":\n return {\n animation: `react-skeletonify-animation-2 ${animationSpeed}s infinite`,\n background: `linear-gradient(120deg, ${background} 30%, #f0f0f0 38%, #f0f0f0 40%, ${background} 48%)`,\n backgroundSize: \"200% 100%\",\n backgroundPosition: \"100% 0\",\n };\n case \"animation-3\":\n return {\n animation: `react-skeletonify-animation-3 ${animationSpeed}s linear infinite alternate`,\n backgroundColor: background,\n };\n }\n};\n\nexport default (config: SkeletonConfig) => {\n const { animationSpeed, background, border, borderRadius, animation, style } =\n config;\n\n const skeletonAnimation: CSSProperties = {\n ...getAnimation(animation, animationSpeed, background),\n border,\n borderRadius,\n ...style,\n };\n\n return skeletonAnimation;\n};\n","// --- Text & Content ---\nexport const TEXT_TAGS = [\n \"p\",\n \"span\",\n \"h1\",\n \"h2\",\n \"h3\",\n \"h4\",\n \"h5\",\n \"h6\",\n \"b\",\n \"strong\",\n \"i\",\n \"em\",\n \"u\",\n \"mark\",\n \"small\",\n \"sup\",\n \"sub\",\n \"abbr\",\n \"cite\",\n \"q\",\n \"blockquote\",\n \"code\",\n \"pre\",\n \"samp\",\n \"kbd\",\n \"var\",\n \"time\",\n \"br\",\n \"wbr\",\n];\n\n// --- Sectioning / Structure ---\nexport const STRUCTURE_TAGS = [\n \"html\",\n \"head\",\n \"body\",\n \"main\",\n \"header\",\n \"footer\",\n \"nav\",\n \"section\",\n \"article\",\n \"aside\",\n];\n\n// --- Metadata ---\nexport const METADATA_TAGS = [\"base\", \"link\", \"meta\", \"style\", \"title\"];\n\n// --- Lists ---\nexport const LIST_TAGS = [\"ul\", \"ol\", \"li\", \"dl\", \"dt\", \"dd\"];\n\n// --- Tables ---\nexport const TABLE_TAGS = [\n \"table\",\n \"caption\",\n \"thead\",\n \"tbody\",\n \"tfoot\",\n \"tr\",\n \"th\",\n \"td\",\n \"col\",\n \"colgroup\",\n];\n\n// --- Forms & Inputs ---\nexport const FORM_TAGS = [\n \"form\",\n \"input\",\n \"textarea\",\n \"button\",\n \"label\",\n \"select\",\n \"option\",\n \"optgroup\",\n \"fieldset\",\n \"legend\",\n \"datalist\",\n \"output\",\n \"meter\",\n \"progress\",\n];\n\n// --- Media ---\nexport const MEDIA_TAGS = [\n \"img\",\n \"audio\",\n \"video\",\n \"source\",\n \"track\",\n \"picture\",\n \"iframe\",\n \"embed\",\n \"object\",\n \"map\",\n \"area\",\n \"canvas\",\n];\n\n// --- Interactive ---\nexport const INTERACTIVE_TAGS = [\n \"details\",\n \"summary\",\n \"dialog\",\n \"script\",\n \"noscript\",\n \"template\",\n];\n\n// --- Other / Inline semantics ---\nexport const MISC_TAGS = [\"ins\", \"del\", \"s\", \"bdi\", \"bdo\", \"ruby\", \"rt\", \"rp\"];\n","import {\n FORM_TAGS,\n INTERACTIVE_TAGS,\n LIST_TAGS,\n MEDIA_TAGS,\n METADATA_TAGS,\n MISC_TAGS,\n STRUCTURE_TAGS,\n TABLE_TAGS,\n TEXT_TAGS,\n} from \"../constants/tags\";\nimport { HtmlTagGroup } from \"../context/skeleton-config\";\n\nexport default function checkTagInGroup(\n tag: string,\n groups: HtmlTagGroup[]\n): boolean {\n return groups.some((group) => {\n switch (group) {\n case \"TEXT_TAGS\":\n return TEXT_TAGS.includes(tag);\n case \"STRUCTURE_TAGS\":\n return STRUCTURE_TAGS.includes(tag);\n case \"METADATA_TAGS\":\n return METADATA_TAGS.includes(tag);\n case \"LIST_TAGS\":\n return LIST_TAGS.includes(tag);\n case \"TABLE_TAGS\":\n return TABLE_TAGS.includes(tag);\n case \"FORM_TAGS\":\n return FORM_TAGS.includes(tag);\n case \"MEDIA_TAGS\":\n return MEDIA_TAGS.includes(tag);\n case \"INTERACTIVE_TAGS\":\n return INTERACTIVE_TAGS.includes(tag);\n case \"MISC_TAGS\":\n return MISC_TAGS.includes(tag);\n }\n });\n}\n","import { LIST_TAGS, TEXT_TAGS } from \"../constants/tags\";\n\nexport default (elementType: string) => {\n return TEXT_TAGS.includes(elementType) || LIST_TAGS.includes(elementType);\n};\n","import React, {\n createContext,\n CSSProperties,\n useContext,\n useMemo,\n} from \"react\";\nimport {\n SkeletonConfig,\n defaultBackground,\n defaultValues,\n} from \"./skeleton-config\";\n\nconst SkeletonContext = createContext<SkeletonConfig>(defaultValues);\ninterface SkeletonProviderProps {\n children: React.ReactNode;\n config?: Partial<SkeletonConfig>;\n style?: CSSProperties;\n}\n\nexport const SkeletonProvider: React.FC<SkeletonProviderProps> = (props) => {\n const { children, config, style } = props;\n const { animation = defaultValues.animation, background } = config || {};\n\n const value: SkeletonConfig = useMemo(\n () => ({\n ...defaultValues,\n ...config,\n background: background ? background : defaultBackground[animation],\n style: { ...defaultValues.style, ...config?.style, ...style },\n }),\n [animation, background, config, style]\n );\n\n return (\n <SkeletonContext.Provider value={value}>\n {children}\n </SkeletonContext.Provider>\n );\n};\n\nexport const useSkeleton = () => useContext(SkeletonContext);\n","import { CSSProperties } from \"react\";\n\nexport const HTML_TAG_GROUPS = [\n \"TEXT_TAGS\",\n \"STRUCTURE_TAGS\",\n \"METADATA_TAGS\",\n \"LIST_TAGS\",\n \"TABLE_TAGS\",\n \"FORM_TAGS\",\n \"MEDIA_TAGS\",\n \"INTERACTIVE_TAGS\",\n \"MISC_TAGS\",\n] as const;\n\nexport type HtmlTagGroup = (typeof HTML_TAG_GROUPS)[number];\n\nexport const defaultBackground = {\n \"animation-1\": \"#aeaeae\",\n \"animation-2\": \"#e5e5e5\",\n \"animation-3\": \"hsl(210, 20%, 90%)\",\n};\n\nexport type SkeletonConfig = {\n animationSpeed: number;\n background: string;\n border: string;\n borderRadius: string | number;\n textTagsMargin: string;\n className?: string;\n style?: CSSProperties;\n animation: \"animation-1\" | \"animation-2\";\n exceptTags: string[];\n exceptTagGroups: HtmlTagGroup[];\n};\n\nexport const defaultValues: SkeletonConfig = {\n animationSpeed: 3,\n background: \"#aeaeae\",\n border: \"none\",\n borderRadius: \"0\",\n textTagsMargin: \"0\",\n className: \"\",\n style: {},\n animation: \"animation-1\",\n exceptTags: [],\n exceptTagGroups: [],\n};\n"],"mappings":"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","names":["import_react","import_react","import_react","import_react","React","React","React","import_react","import_jsx_runtime"]}
|
package/dist/index.mjs
CHANGED
|
@@ -1,3 +1,6 @@
|
|
|
1
|
+
// src/components/SkeletonWrapper.tsx
|
|
2
|
+
import { useMemo as useMemo2 } from "react";
|
|
3
|
+
|
|
1
4
|
// src/components/SkeletonElement.tsx
|
|
2
5
|
import React4 from "react";
|
|
3
6
|
|
|
@@ -6,18 +9,69 @@ import React3 from "react";
|
|
|
6
9
|
|
|
7
10
|
// src/utils/create-node-wrapper.ts
|
|
8
11
|
import { createElement } from "react";
|
|
9
|
-
function createNodeWrapper(node) {
|
|
10
|
-
var _a;
|
|
12
|
+
function createNodeWrapper(node, className, style) {
|
|
13
|
+
var _a, _b;
|
|
11
14
|
if (!node) return null;
|
|
12
15
|
return createElement(
|
|
13
16
|
"div",
|
|
14
17
|
{
|
|
15
|
-
className: (((_a = node == null ? void 0 : node.props) == null ? void 0 : _a.className) || "")
|
|
18
|
+
className: className + (((_a = node == null ? void 0 : node.props) == null ? void 0 : _a.className) || ""),
|
|
19
|
+
style: {
|
|
20
|
+
...style,
|
|
21
|
+
...(_b = node == null ? void 0 : node.props) == null ? void 0 : _b.style
|
|
22
|
+
}
|
|
16
23
|
},
|
|
17
24
|
node
|
|
18
25
|
);
|
|
19
26
|
}
|
|
20
27
|
|
|
28
|
+
// src/utils/create-leaf-node.ts
|
|
29
|
+
import React2 from "react";
|
|
30
|
+
function createLeafNode(node, className, style) {
|
|
31
|
+
return React2.cloneElement(node, {
|
|
32
|
+
...node.props,
|
|
33
|
+
className: className + (node.props.className || ""),
|
|
34
|
+
style: {
|
|
35
|
+
...style,
|
|
36
|
+
...node.props.style
|
|
37
|
+
}
|
|
38
|
+
});
|
|
39
|
+
}
|
|
40
|
+
|
|
41
|
+
// src/utils/create-style.ts
|
|
42
|
+
var getAnimation = (animation, animationSpeed, background) => {
|
|
43
|
+
switch (animation) {
|
|
44
|
+
case "animation-1":
|
|
45
|
+
return {
|
|
46
|
+
animation: `react-skeletonify-animation-1 ${animationSpeed}s ease-in-out infinite `,
|
|
47
|
+
background,
|
|
48
|
+
animationDelay: "0.5s"
|
|
49
|
+
};
|
|
50
|
+
case "animation-2":
|
|
51
|
+
return {
|
|
52
|
+
animation: `react-skeletonify-animation-2 ${animationSpeed}s infinite`,
|
|
53
|
+
background: `linear-gradient(120deg, ${background} 30%, #f0f0f0 38%, #f0f0f0 40%, ${background} 48%)`,
|
|
54
|
+
backgroundSize: "200% 100%",
|
|
55
|
+
backgroundPosition: "100% 0"
|
|
56
|
+
};
|
|
57
|
+
case "animation-3":
|
|
58
|
+
return {
|
|
59
|
+
animation: `react-skeletonify-animation-3 ${animationSpeed}s linear infinite alternate`,
|
|
60
|
+
backgroundColor: background
|
|
61
|
+
};
|
|
62
|
+
}
|
|
63
|
+
};
|
|
64
|
+
var create_style_default = (config) => {
|
|
65
|
+
const { animationSpeed, background, border, borderRadius, animation, style } = config;
|
|
66
|
+
const skeletonAnimation = {
|
|
67
|
+
...getAnimation(animation, animationSpeed, background),
|
|
68
|
+
border,
|
|
69
|
+
borderRadius,
|
|
70
|
+
...style
|
|
71
|
+
};
|
|
72
|
+
return skeletonAnimation;
|
|
73
|
+
};
|
|
74
|
+
|
|
21
75
|
// src/constants/tags.ts
|
|
22
76
|
var TEXT_TAGS = [
|
|
23
77
|
"p",
|
|
@@ -28,36 +82,161 @@ var TEXT_TAGS = [
|
|
|
28
82
|
"h4",
|
|
29
83
|
"h5",
|
|
30
84
|
"h6",
|
|
31
|
-
"
|
|
85
|
+
"b",
|
|
86
|
+
"strong",
|
|
87
|
+
"i",
|
|
88
|
+
"em",
|
|
89
|
+
"u",
|
|
90
|
+
"mark",
|
|
91
|
+
"small",
|
|
92
|
+
"sup",
|
|
93
|
+
"sub",
|
|
94
|
+
"abbr",
|
|
95
|
+
"cite",
|
|
96
|
+
"q",
|
|
97
|
+
"blockquote",
|
|
98
|
+
"code",
|
|
99
|
+
"pre",
|
|
100
|
+
"samp",
|
|
101
|
+
"kbd",
|
|
102
|
+
"var",
|
|
103
|
+
"time",
|
|
104
|
+
"br",
|
|
105
|
+
"wbr"
|
|
106
|
+
];
|
|
107
|
+
var STRUCTURE_TAGS = [
|
|
108
|
+
"html",
|
|
109
|
+
"head",
|
|
110
|
+
"body",
|
|
111
|
+
"main",
|
|
112
|
+
"header",
|
|
113
|
+
"footer",
|
|
114
|
+
"nav",
|
|
115
|
+
"section",
|
|
116
|
+
"article",
|
|
117
|
+
"aside"
|
|
118
|
+
];
|
|
119
|
+
var METADATA_TAGS = ["base", "link", "meta", "style", "title"];
|
|
120
|
+
var LIST_TAGS = ["ul", "ol", "li", "dl", "dt", "dd"];
|
|
121
|
+
var TABLE_TAGS = [
|
|
122
|
+
"table",
|
|
123
|
+
"caption",
|
|
124
|
+
"thead",
|
|
125
|
+
"tbody",
|
|
126
|
+
"tfoot",
|
|
127
|
+
"tr",
|
|
128
|
+
"th",
|
|
129
|
+
"td",
|
|
130
|
+
"col",
|
|
131
|
+
"colgroup"
|
|
132
|
+
];
|
|
133
|
+
var FORM_TAGS = [
|
|
134
|
+
"form",
|
|
135
|
+
"input",
|
|
136
|
+
"textarea",
|
|
137
|
+
"button",
|
|
138
|
+
"label",
|
|
139
|
+
"select",
|
|
140
|
+
"option",
|
|
141
|
+
"optgroup",
|
|
142
|
+
"fieldset",
|
|
143
|
+
"legend",
|
|
144
|
+
"datalist",
|
|
145
|
+
"output",
|
|
146
|
+
"meter",
|
|
147
|
+
"progress"
|
|
148
|
+
];
|
|
149
|
+
var MEDIA_TAGS = [
|
|
150
|
+
"img",
|
|
151
|
+
"audio",
|
|
152
|
+
"video",
|
|
153
|
+
"source",
|
|
154
|
+
"track",
|
|
155
|
+
"picture",
|
|
156
|
+
"iframe",
|
|
157
|
+
"embed",
|
|
158
|
+
"object",
|
|
159
|
+
"map",
|
|
160
|
+
"area",
|
|
161
|
+
"canvas"
|
|
162
|
+
];
|
|
163
|
+
var INTERACTIVE_TAGS = [
|
|
164
|
+
"details",
|
|
165
|
+
"summary",
|
|
166
|
+
"dialog",
|
|
167
|
+
"script",
|
|
168
|
+
"noscript",
|
|
169
|
+
"template"
|
|
32
170
|
];
|
|
171
|
+
var MISC_TAGS = ["ins", "del", "s", "bdi", "bdo", "ruby", "rt", "rp"];
|
|
33
172
|
|
|
34
|
-
// src/utils/
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
173
|
+
// src/utils/check-tag-in-group.ts
|
|
174
|
+
function checkTagInGroup(tag, groups) {
|
|
175
|
+
return groups.some((group) => {
|
|
176
|
+
switch (group) {
|
|
177
|
+
case "TEXT_TAGS":
|
|
178
|
+
return TEXT_TAGS.includes(tag);
|
|
179
|
+
case "STRUCTURE_TAGS":
|
|
180
|
+
return STRUCTURE_TAGS.includes(tag);
|
|
181
|
+
case "METADATA_TAGS":
|
|
182
|
+
return METADATA_TAGS.includes(tag);
|
|
183
|
+
case "LIST_TAGS":
|
|
184
|
+
return LIST_TAGS.includes(tag);
|
|
185
|
+
case "TABLE_TAGS":
|
|
186
|
+
return TABLE_TAGS.includes(tag);
|
|
187
|
+
case "FORM_TAGS":
|
|
188
|
+
return FORM_TAGS.includes(tag);
|
|
189
|
+
case "MEDIA_TAGS":
|
|
190
|
+
return MEDIA_TAGS.includes(tag);
|
|
191
|
+
case "INTERACTIVE_TAGS":
|
|
192
|
+
return INTERACTIVE_TAGS.includes(tag);
|
|
193
|
+
case "MISC_TAGS":
|
|
194
|
+
return MISC_TAGS.includes(tag);
|
|
195
|
+
}
|
|
40
196
|
});
|
|
41
197
|
}
|
|
42
198
|
|
|
199
|
+
// src/utils/is-text-element.ts
|
|
200
|
+
var is_text_element_default = (elementType) => {
|
|
201
|
+
return TEXT_TAGS.includes(elementType) || LIST_TAGS.includes(elementType);
|
|
202
|
+
};
|
|
203
|
+
|
|
43
204
|
// src/hooks/useAddSkelton.ts
|
|
44
|
-
function useAddSkelton() {
|
|
205
|
+
function useAddSkelton(config) {
|
|
206
|
+
const { className, exceptTags, exceptTagGroups, textTagsMargin } = config;
|
|
207
|
+
const CLASS_NAME = `react-skeletonify ${className} `;
|
|
208
|
+
const style = create_style_default(config);
|
|
45
209
|
const addSkeleton = (node) => {
|
|
46
|
-
if (!React3.isValidElement(node))
|
|
210
|
+
if (!React3.isValidElement(node))
|
|
211
|
+
return createNodeWrapper(node, CLASS_NAME, style);
|
|
47
212
|
const element = node;
|
|
48
213
|
const { children } = element.props;
|
|
49
214
|
const elementType = element.type;
|
|
215
|
+
if (typeof elementType === "string") {
|
|
216
|
+
if (exceptTags.includes(elementType)) {
|
|
217
|
+
return element;
|
|
218
|
+
}
|
|
219
|
+
const isRestrictedGroupTag = checkTagInGroup(
|
|
220
|
+
elementType,
|
|
221
|
+
exceptTagGroups
|
|
222
|
+
);
|
|
223
|
+
if (isRestrictedGroupTag) return element;
|
|
224
|
+
}
|
|
50
225
|
const hasChildren = React3.Children.count(children) > 0;
|
|
51
226
|
const isValidChildren = typeof children !== "string";
|
|
52
227
|
if (typeof elementType === "function") {
|
|
53
228
|
const rendered = elementType(element.props);
|
|
54
229
|
return addSkeleton(rendered);
|
|
55
230
|
}
|
|
56
|
-
|
|
57
|
-
|
|
231
|
+
const isTextTag = is_text_element_default(elementType);
|
|
232
|
+
if (isTextTag) {
|
|
233
|
+
return createLeafNode(element, CLASS_NAME, {
|
|
234
|
+
...style,
|
|
235
|
+
margin: textTagsMargin
|
|
236
|
+
});
|
|
58
237
|
}
|
|
59
238
|
if (elementType === "img") {
|
|
60
|
-
return createNodeWrapper(element);
|
|
239
|
+
return createNodeWrapper(element, CLASS_NAME, style);
|
|
61
240
|
}
|
|
62
241
|
if (hasChildren && isValidChildren) {
|
|
63
242
|
const childWithSkeletons = React3.Children.map(children, addSkeleton);
|
|
@@ -66,35 +245,87 @@ function useAddSkelton() {
|
|
|
66
245
|
children: childWithSkeletons
|
|
67
246
|
});
|
|
68
247
|
}
|
|
69
|
-
return createLeafNode(element);
|
|
248
|
+
return createLeafNode(element, CLASS_NAME, style);
|
|
70
249
|
};
|
|
71
250
|
return addSkeleton;
|
|
72
251
|
}
|
|
73
252
|
var useAddSkelton_default = useAddSkelton;
|
|
74
253
|
|
|
75
254
|
// src/components/SkeletonElement.tsx
|
|
76
|
-
|
|
77
|
-
|
|
78
|
-
|
|
79
|
-
|
|
80
|
-
const addSkeleton = useAddSkelton_default();
|
|
81
|
-
return /* @__PURE__ */ jsx("div", { className: "skeleton-container", children: React4.Children.map(children, (child) => addSkeleton(child)) });
|
|
255
|
+
var SkeletonElement = (props) => {
|
|
256
|
+
const { children, config } = props;
|
|
257
|
+
const addSkeleton = useAddSkelton_default(config);
|
|
258
|
+
return React4.Children.map(children, (child) => addSkeleton(child));
|
|
82
259
|
};
|
|
83
260
|
var SkeletonElement_default = SkeletonElement;
|
|
84
261
|
|
|
262
|
+
// src/context/SkeletonContext.tsx
|
|
263
|
+
import {
|
|
264
|
+
createContext,
|
|
265
|
+
useContext,
|
|
266
|
+
useMemo
|
|
267
|
+
} from "react";
|
|
268
|
+
|
|
269
|
+
// src/context/skeleton-config.ts
|
|
270
|
+
var defaultBackground = {
|
|
271
|
+
"animation-1": "#aeaeae",
|
|
272
|
+
"animation-2": "#e5e5e5",
|
|
273
|
+
"animation-3": "hsl(210, 20%, 90%)"
|
|
274
|
+
};
|
|
275
|
+
var defaultValues = {
|
|
276
|
+
animationSpeed: 3,
|
|
277
|
+
background: "#aeaeae",
|
|
278
|
+
border: "none",
|
|
279
|
+
borderRadius: "0",
|
|
280
|
+
textTagsMargin: "0",
|
|
281
|
+
className: "",
|
|
282
|
+
style: {},
|
|
283
|
+
animation: "animation-1",
|
|
284
|
+
exceptTags: [],
|
|
285
|
+
exceptTagGroups: []
|
|
286
|
+
};
|
|
287
|
+
|
|
288
|
+
// src/context/SkeletonContext.tsx
|
|
289
|
+
import { jsx } from "react/jsx-runtime";
|
|
290
|
+
var SkeletonContext = createContext(defaultValues);
|
|
291
|
+
var SkeletonProvider = (props) => {
|
|
292
|
+
const { children, config, style } = props;
|
|
293
|
+
const { animation = defaultValues.animation, background } = config || {};
|
|
294
|
+
const value = useMemo(
|
|
295
|
+
() => ({
|
|
296
|
+
...defaultValues,
|
|
297
|
+
...config,
|
|
298
|
+
background: background ? background : defaultBackground[animation],
|
|
299
|
+
style: { ...defaultValues.style, ...config == null ? void 0 : config.style, ...style }
|
|
300
|
+
}),
|
|
301
|
+
[animation, background, config, style]
|
|
302
|
+
);
|
|
303
|
+
return /* @__PURE__ */ jsx(SkeletonContext.Provider, { value, children });
|
|
304
|
+
};
|
|
305
|
+
var useSkeleton = () => useContext(SkeletonContext);
|
|
306
|
+
|
|
85
307
|
// src/components/SkeletonWrapper.tsx
|
|
86
|
-
import {
|
|
87
|
-
var SkeletonWrapper = ({
|
|
88
|
-
loading,
|
|
89
|
-
|
|
90
|
-
|
|
308
|
+
import { jsx as jsx2 } from "react/jsx-runtime";
|
|
309
|
+
var SkeletonWrapper = (props) => {
|
|
310
|
+
const { loading, children, overrideConfig, style } = props;
|
|
311
|
+
const mainConfig = useSkeleton();
|
|
312
|
+
const config = useMemo2(
|
|
313
|
+
() => ({
|
|
314
|
+
...mainConfig,
|
|
315
|
+
...overrideConfig,
|
|
316
|
+
style: { ...mainConfig.style, ...overrideConfig == null ? void 0 : overrideConfig.style, ...style }
|
|
317
|
+
}),
|
|
318
|
+
[overrideConfig, mainConfig]
|
|
319
|
+
);
|
|
91
320
|
if (loading) {
|
|
92
|
-
return /* @__PURE__ */ jsx2(SkeletonElement_default, { children });
|
|
321
|
+
return /* @__PURE__ */ jsx2(SkeletonElement_default, { config, children });
|
|
93
322
|
}
|
|
94
|
-
return
|
|
323
|
+
return children;
|
|
95
324
|
};
|
|
96
325
|
var SkeletonWrapper_default = SkeletonWrapper;
|
|
97
326
|
export {
|
|
98
|
-
|
|
327
|
+
SkeletonProvider,
|
|
328
|
+
SkeletonWrapper_default as SkeletonWrapper,
|
|
329
|
+
useSkeleton
|
|
99
330
|
};
|
|
100
331
|
//# sourceMappingURL=index.mjs.map
|
package/dist/index.mjs.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["../src/components/SkeletonElement.tsx","../src/hooks/useAddSkelton.ts","../src/utils/create-node-wrapper.ts","../src/constants/tags.ts","../src/utils/create-leaf-node.ts","../src/components/SkeletonWrapper.tsx"],"sourcesContent":["import React from \"react\";\nimport useAddSkelton from \"../hooks/useAddSkelton\";\n\nconst SkeletonElement: React.FC<{ children: React.ReactNode }> = ({\n children,\n}) => {\n const addSkeleton = useAddSkelton();\n return (\n <div className=\"skeleton-container\">\n {React.Children.map(children, (child) => addSkeleton(child))}\n </div>\n );\n};\n\nexport default SkeletonElement;\n","import React from \"react\";\nimport createNodeWrapper from \"../utils/create-node-wrapper\";\nimport { TEXT_TAGS } from \"../constants/tags\";\nimport createLeafNode from \"../utils/create-leaf-node\";\n\nfunction useAddSkelton() {\n const addSkeleton = (node: React.ReactNode): React.ReactNode => {\n if (!React.isValidElement(node)) return createNodeWrapper(node as any);\n\n const element = node as React.ReactElement<any>;\n const { children } = element.props;\n const elementType = element.type;\n\n const hasChildren = React.Children.count(children) > 0;\n const isValidChildren = typeof children !== \"string\";\n\n if (typeof elementType === \"function\") {\n const rendered = (elementType as any)(element.props);\n return addSkeleton(rendered);\n }\n\n if (TEXT_TAGS.includes(elementType)) {\n return createLeafNode(node, \"Rss-skeleton-text\");\n }\n\n if (elementType === \"img\") {\n return createNodeWrapper(element);\n }\n\n if (hasChildren && isValidChildren) {\n const childWithSkeletons = React.Children.map(children, addSkeleton);\n\n return React.cloneElement(element, {\n ...element.props,\n children: childWithSkeletons,\n } as typeof element.props);\n }\n\n return createLeafNode(element);\n };\n\n return addSkeleton;\n}\n\nexport default useAddSkelton;\n","import React, { createElement } from \"react\";\n\nexport default function createNodeWrapper(node: React.ReactElement<any>) {\n if (!node) return null;\n\n return createElement(\n \"div\",\n {\n className: (node?.props?.className || \"\") + \" Rss-skeleton\",\n },\n node\n );\n}\n","export const TEXT_TAGS = [\n \"p\",\n \"span\",\n \"h1\",\n \"h2\",\n \"h3\",\n \"h4\",\n \"h5\",\n \"h6\",\n \"li\",\n];\n","import React from \"react\";\n\nexport default function createLeafNode(\n node: React.ReactElement<any>,\n className: string = \"\"\n): React.ReactElement {\n return React.cloneElement(node, {\n ...node.props,\n className: (node.props.className || \"\") + \" Rss-skeleton \" + className,\n } as typeof node.props);\n}\n","import React from \"react\";\nimport SkeletonElement from \"./SkeletonElement\";\n\ninterface SkeletonWrapperProps {\n loading: boolean;\n children: React.ReactNode;\n}\n\nconst SkeletonWrapper: React.FC<SkeletonWrapperProps> = ({\n loading,\n children,\n}) => {\n if (loading) {\n return <SkeletonElement>{children}</SkeletonElement>;\n }\n return <>{children}</>;\n};\n\nexport default SkeletonWrapper;\n"],"mappings":";AAAA,OAAOA,YAAW;;;ACAlB,OAAOC,YAAW;;;ACAlB,SAAgB,qBAAqB;AAEtB,SAAR,kBAAmC,MAA+B;AAFzE;AAGE,MAAI,CAAC,KAAM,QAAO;AAElB,SAAO;AAAA,IACL;AAAA,IACA;AAAA,MACE,cAAY,kCAAM,UAAN,mBAAa,cAAa,MAAM;AAAA,IAC9C;AAAA,IACA;AAAA,EACF;AACF;;;ACZO,IAAM,YAAY;AAAA,EACvB;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AACF;;;ACVA,OAAOC,YAAW;AAEH,SAAR,eACL,MACA,YAAoB,IACA;AACpB,SAAOA,OAAM,aAAa,MAAM;AAAA,IAC9B,GAAG,KAAK;AAAA,IACR,YAAY,KAAK,MAAM,aAAa,MAAM,mBAAmB;AAAA,EAC/D,CAAsB;AACxB;;;AHLA,SAAS,gBAAgB;AACvB,QAAM,cAAc,CAAC,SAA2C;AAC9D,QAAI,CAACC,OAAM,eAAe,IAAI,EAAG,QAAO,kBAAkB,IAAW;AAErE,UAAM,UAAU;AAChB,UAAM,EAAE,SAAS,IAAI,QAAQ;AAC7B,UAAM,cAAc,QAAQ;AAE5B,UAAM,cAAcA,OAAM,SAAS,MAAM,QAAQ,IAAI;AACrD,UAAM,kBAAkB,OAAO,aAAa;AAE5C,QAAI,OAAO,gBAAgB,YAAY;AACrC,YAAM,WAAY,YAAoB,QAAQ,KAAK;AACnD,aAAO,YAAY,QAAQ;AAAA,IAC7B;AAEA,QAAI,UAAU,SAAS,WAAW,GAAG;AACnC,aAAO,eAAe,MAAM,mBAAmB;AAAA,IACjD;AAEA,QAAI,gBAAgB,OAAO;AACzB,aAAO,kBAAkB,OAAO;AAAA,IAClC;AAEA,QAAI,eAAe,iBAAiB;AAClC,YAAM,qBAAqBA,OAAM,SAAS,IAAI,UAAU,WAAW;AAEnE,aAAOA,OAAM,aAAa,SAAS;AAAA,QACjC,GAAG,QAAQ;AAAA,QACX,UAAU;AAAA,MACZ,CAAyB;AAAA,IAC3B;AAEA,WAAO,eAAe,OAAO;AAAA,EAC/B;AAEA,SAAO;AACT;AAEA,IAAO,wBAAQ;;;ADpCX;AALJ,IAAM,kBAA2D,CAAC;AAAA,EAChE;AACF,MAAM;AACJ,QAAM,cAAc,sBAAc;AAClC,SACE,oBAAC,SAAI,WAAU,sBACZ,UAAAC,OAAM,SAAS,IAAI,UAAU,CAAC,UAAU,YAAY,KAAK,CAAC,GAC7D;AAEJ;AAEA,IAAO,0BAAQ;;;AKDJ,SAEF,UAFE,OAAAC,YAAA;AALX,IAAM,kBAAkD,CAAC;AAAA,EACvD;AAAA,EACA;AACF,MAAM;AACJ,MAAI,SAAS;AACX,WAAO,gBAAAA,KAAC,2BAAiB,UAAS;AAAA,EACpC;AACA,SAAO,gBAAAA,KAAA,YAAG,UAAS;AACrB;AAEA,IAAO,0BAAQ;","names":["React","React","React","React","React","jsx"]}
|
|
1
|
+
{"version":3,"sources":["../src/components/SkeletonWrapper.tsx","../src/components/SkeletonElement.tsx","../src/hooks/useAddSkelton.ts","../src/utils/create-node-wrapper.ts","../src/utils/create-leaf-node.ts","../src/utils/create-style.ts","../src/constants/tags.ts","../src/utils/check-tag-in-group.ts","../src/utils/is-text-element.ts","../src/context/SkeletonContext.tsx","../src/context/skeleton-config.ts"],"sourcesContent":["import React, { CSSProperties, useMemo } from \"react\";\nimport SkeletonElement from \"./SkeletonElement\";\nimport { SkeletonConfig } from \"../context/skeleton-config\";\nimport { useSkeleton } from \"../context/SkeletonContext\";\n\ninterface SkeletonWrapperProps {\n loading: boolean;\n children: React.ReactNode;\n overrideConfig?: Partial<SkeletonConfig>;\n style?: CSSProperties;\n}\n\nconst SkeletonWrapper: React.FC<SkeletonWrapperProps> = (props) => {\n const { loading, children, overrideConfig, style } = props;\n const mainConfig = useSkeleton();\n\n const config: SkeletonConfig = useMemo(\n () => ({\n ...mainConfig,\n ...overrideConfig,\n style: { ...mainConfig.style, ...overrideConfig?.style, ...style },\n }),\n [overrideConfig, mainConfig]\n );\n\n if (loading) {\n return <SkeletonElement config={config}>{children}</SkeletonElement>;\n }\n return children;\n};\n\nexport default SkeletonWrapper;\n","import React from \"react\";\nimport useAddSkelton from \"../hooks/useAddSkelton\";\nimport { SkeletonConfig } from \"../context/skeleton-config\";\n\ninterface SkeletonElementProps {\n children: React.ReactNode;\n config: SkeletonConfig;\n}\n\nconst SkeletonElement: React.FC<SkeletonElementProps> = (props) => {\n const { children, config } = props;\n const addSkeleton = useAddSkelton(config);\n\n return React.Children.map(children, (child) => addSkeleton(child));\n};\n\nexport default SkeletonElement;\n","import React from \"react\";\nimport createNodeWrapper from \"../utils/create-node-wrapper\";\nimport createLeafNode from \"../utils/create-leaf-node\";\nimport { SkeletonConfig } from \"../context/skeleton-config\";\nimport createStyle from \"../utils/create-style\";\nimport checkTagInGroup from \"../utils/check-tag-in-group\";\nimport isTextElement from \"../utils/is-text-element\";\n\nfunction useAddSkelton(config: SkeletonConfig) {\n const { className, exceptTags, exceptTagGroups, textTagsMargin } = config;\n const CLASS_NAME = `react-skeletonify ${className} `;\n const style = createStyle(config);\n\n const addSkeleton = (node: React.ReactNode): React.ReactNode => {\n if (!React.isValidElement(node))\n return createNodeWrapper(node as any, CLASS_NAME, style);\n\n const element = node as React.ReactElement<any>;\n const { children } = element.props;\n const elementType = element.type;\n\n if (typeof elementType === \"string\") {\n if (exceptTags.includes(elementType)) {\n return element;\n }\n const isRestrictedGroupTag = checkTagInGroup(\n elementType,\n exceptTagGroups\n );\n\n if (isRestrictedGroupTag) return element;\n }\n\n const hasChildren = React.Children.count(children) > 0;\n const isValidChildren = typeof children !== \"string\";\n\n if (typeof elementType === \"function\") {\n const rendered = (elementType as any)(element.props);\n return addSkeleton(rendered);\n }\n\n const isTextTag = isTextElement(elementType);\n\n if (isTextTag) {\n return createLeafNode(element, CLASS_NAME, {\n ...style,\n margin: textTagsMargin,\n });\n }\n\n if (elementType === \"img\") {\n return createNodeWrapper(element, CLASS_NAME, style);\n }\n\n if (hasChildren && isValidChildren) {\n const childWithSkeletons = React.Children.map(children, addSkeleton);\n\n return React.cloneElement(element, {\n ...element.props,\n children: childWithSkeletons,\n } as typeof element.props);\n }\n\n return createLeafNode(element, CLASS_NAME, style);\n };\n\n return addSkeleton;\n}\n\nexport default useAddSkelton;\n","import React, { createElement, CSSProperties } from \"react\";\n\nexport default function createNodeWrapper(\n node: React.ReactElement<any>,\n className: string,\n style: CSSProperties\n) {\n if (!node) return null;\n\n return createElement(\n \"div\",\n {\n className: className + (node?.props?.className || \"\"),\n style: {\n ...style,\n ...node?.props?.style,\n },\n },\n node\n );\n}\n","import React, { CSSProperties } from \"react\";\n\nexport default function createLeafNode(\n node: React.ReactElement<any>,\n className: string,\n style: CSSProperties\n): React.ReactElement {\n return React.cloneElement(node, {\n ...node.props,\n className: className + (node.props.className || \"\"),\n style: {\n ...style,\n ...node.props.style,\n },\n } as typeof node.props);\n}\n","import { CSSProperties } from \"react\";\nimport { SkeletonConfig } from \"../context/skeleton-config\";\n\nconst getAnimation = (\n animation: string,\n animationSpeed: number,\n background: string\n) => {\n switch (animation) {\n case \"animation-1\":\n return {\n animation: `react-skeletonify-animation-1 ${animationSpeed}s ease-in-out infinite `,\n background: background,\n animationDelay: \"0.5s\",\n };\n case \"animation-2\":\n return {\n animation: `react-skeletonify-animation-2 ${animationSpeed}s infinite`,\n background: `linear-gradient(120deg, ${background} 30%, #f0f0f0 38%, #f0f0f0 40%, ${background} 48%)`,\n backgroundSize: \"200% 100%\",\n backgroundPosition: \"100% 0\",\n };\n case \"animation-3\":\n return {\n animation: `react-skeletonify-animation-3 ${animationSpeed}s linear infinite alternate`,\n backgroundColor: background,\n };\n }\n};\n\nexport default (config: SkeletonConfig) => {\n const { animationSpeed, background, border, borderRadius, animation, style } =\n config;\n\n const skeletonAnimation: CSSProperties = {\n ...getAnimation(animation, animationSpeed, background),\n border,\n borderRadius,\n ...style,\n };\n\n return skeletonAnimation;\n};\n","// --- Text & Content ---\nexport const TEXT_TAGS = [\n \"p\",\n \"span\",\n \"h1\",\n \"h2\",\n \"h3\",\n \"h4\",\n \"h5\",\n \"h6\",\n \"b\",\n \"strong\",\n \"i\",\n \"em\",\n \"u\",\n \"mark\",\n \"small\",\n \"sup\",\n \"sub\",\n \"abbr\",\n \"cite\",\n \"q\",\n \"blockquote\",\n \"code\",\n \"pre\",\n \"samp\",\n \"kbd\",\n \"var\",\n \"time\",\n \"br\",\n \"wbr\",\n];\n\n// --- Sectioning / Structure ---\nexport const STRUCTURE_TAGS = [\n \"html\",\n \"head\",\n \"body\",\n \"main\",\n \"header\",\n \"footer\",\n \"nav\",\n \"section\",\n \"article\",\n \"aside\",\n];\n\n// --- Metadata ---\nexport const METADATA_TAGS = [\"base\", \"link\", \"meta\", \"style\", \"title\"];\n\n// --- Lists ---\nexport const LIST_TAGS = [\"ul\", \"ol\", \"li\", \"dl\", \"dt\", \"dd\"];\n\n// --- Tables ---\nexport const TABLE_TAGS = [\n \"table\",\n \"caption\",\n \"thead\",\n \"tbody\",\n \"tfoot\",\n \"tr\",\n \"th\",\n \"td\",\n \"col\",\n \"colgroup\",\n];\n\n// --- Forms & Inputs ---\nexport const FORM_TAGS = [\n \"form\",\n \"input\",\n \"textarea\",\n \"button\",\n \"label\",\n \"select\",\n \"option\",\n \"optgroup\",\n \"fieldset\",\n \"legend\",\n \"datalist\",\n \"output\",\n \"meter\",\n \"progress\",\n];\n\n// --- Media ---\nexport const MEDIA_TAGS = [\n \"img\",\n \"audio\",\n \"video\",\n \"source\",\n \"track\",\n \"picture\",\n \"iframe\",\n \"embed\",\n \"object\",\n \"map\",\n \"area\",\n \"canvas\",\n];\n\n// --- Interactive ---\nexport const INTERACTIVE_TAGS = [\n \"details\",\n \"summary\",\n \"dialog\",\n \"script\",\n \"noscript\",\n \"template\",\n];\n\n// --- Other / Inline semantics ---\nexport const MISC_TAGS = [\"ins\", \"del\", \"s\", \"bdi\", \"bdo\", \"ruby\", \"rt\", \"rp\"];\n","import {\n FORM_TAGS,\n INTERACTIVE_TAGS,\n LIST_TAGS,\n MEDIA_TAGS,\n METADATA_TAGS,\n MISC_TAGS,\n STRUCTURE_TAGS,\n TABLE_TAGS,\n TEXT_TAGS,\n} from \"../constants/tags\";\nimport { HtmlTagGroup } from \"../context/skeleton-config\";\n\nexport default function checkTagInGroup(\n tag: string,\n groups: HtmlTagGroup[]\n): boolean {\n return groups.some((group) => {\n switch (group) {\n case \"TEXT_TAGS\":\n return TEXT_TAGS.includes(tag);\n case \"STRUCTURE_TAGS\":\n return STRUCTURE_TAGS.includes(tag);\n case \"METADATA_TAGS\":\n return METADATA_TAGS.includes(tag);\n case \"LIST_TAGS\":\n return LIST_TAGS.includes(tag);\n case \"TABLE_TAGS\":\n return TABLE_TAGS.includes(tag);\n case \"FORM_TAGS\":\n return FORM_TAGS.includes(tag);\n case \"MEDIA_TAGS\":\n return MEDIA_TAGS.includes(tag);\n case \"INTERACTIVE_TAGS\":\n return INTERACTIVE_TAGS.includes(tag);\n case \"MISC_TAGS\":\n return MISC_TAGS.includes(tag);\n }\n });\n}\n","import { LIST_TAGS, TEXT_TAGS } from \"../constants/tags\";\n\nexport default (elementType: string) => {\n return TEXT_TAGS.includes(elementType) || LIST_TAGS.includes(elementType);\n};\n","import React, {\n createContext,\n CSSProperties,\n useContext,\n useMemo,\n} from \"react\";\nimport {\n SkeletonConfig,\n defaultBackground,\n defaultValues,\n} from \"./skeleton-config\";\n\nconst SkeletonContext = createContext<SkeletonConfig>(defaultValues);\ninterface SkeletonProviderProps {\n children: React.ReactNode;\n config?: Partial<SkeletonConfig>;\n style?: CSSProperties;\n}\n\nexport const SkeletonProvider: React.FC<SkeletonProviderProps> = (props) => {\n const { children, config, style } = props;\n const { animation = defaultValues.animation, background } = config || {};\n\n const value: SkeletonConfig = useMemo(\n () => ({\n ...defaultValues,\n ...config,\n background: background ? background : defaultBackground[animation],\n style: { ...defaultValues.style, ...config?.style, ...style },\n }),\n [animation, background, config, style]\n );\n\n return (\n <SkeletonContext.Provider value={value}>\n {children}\n </SkeletonContext.Provider>\n );\n};\n\nexport const useSkeleton = () => useContext(SkeletonContext);\n","import { CSSProperties } from \"react\";\n\nexport const HTML_TAG_GROUPS = [\n \"TEXT_TAGS\",\n \"STRUCTURE_TAGS\",\n \"METADATA_TAGS\",\n \"LIST_TAGS\",\n \"TABLE_TAGS\",\n \"FORM_TAGS\",\n \"MEDIA_TAGS\",\n \"INTERACTIVE_TAGS\",\n \"MISC_TAGS\",\n] as const;\n\nexport type HtmlTagGroup = (typeof HTML_TAG_GROUPS)[number];\n\nexport const defaultBackground = {\n \"animation-1\": \"#aeaeae\",\n \"animation-2\": \"#e5e5e5\",\n \"animation-3\": \"hsl(210, 20%, 90%)\",\n};\n\nexport type SkeletonConfig = {\n animationSpeed: number;\n background: string;\n border: string;\n borderRadius: string | number;\n textTagsMargin: string;\n className?: string;\n style?: CSSProperties;\n animation: \"animation-1\" | \"animation-2\";\n exceptTags: string[];\n exceptTagGroups: HtmlTagGroup[];\n};\n\nexport const defaultValues: SkeletonConfig = {\n animationSpeed: 3,\n background: \"#aeaeae\",\n border: \"none\",\n borderRadius: \"0\",\n textTagsMargin: \"0\",\n className: \"\",\n style: {},\n animation: \"animation-1\",\n exceptTags: [],\n exceptTagGroups: [],\n};\n"],"mappings":"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","names":["useMemo","React","React","React","React","React","jsx","useMemo"]}
|