Skip to content

Commit 72027ae

Browse files
authored
Merge pull request #1542 from easyops-cn/steve/lucide-icons
feat(): new icons lib: lucide
2 parents 50de42d + 947b1ab commit 72027ae

File tree

18 files changed

+777
-14
lines changed

18 files changed

+777
-14
lines changed

bricks/icons/build.config.js

Lines changed: 17 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -8,6 +8,10 @@ const easyopsIconsDir = path.resolve(
88
require.resolve("@next-shared/icons/package.json"),
99
"../src/icons"
1010
);
11+
const lucideIconsDir = path.resolve(
12+
require.resolve("lucide-static/package.json"),
13+
"../icons"
14+
);
1115

1216
/** @type {import("@next-core/build-next-bricks").BuildNextBricksConfig} */
1317
export default {
@@ -46,6 +50,19 @@ export default {
4650
// Terser skip this file for minimization
4751
info: { minimized: true },
4852
},
53+
{
54+
context: lucideIconsDir,
55+
from: "*.svg",
56+
to: "chunks/lucide-icons",
57+
// Terser skip this file for minimization
58+
info: { minimized: true },
59+
},
60+
{
61+
from: "src/lucide-icon/generated",
62+
to: "chunks/lucide-icons",
63+
// Terser skip this file for minimization
64+
info: { minimized: true },
65+
},
4966
],
5067
}),
5168
],

bricks/icons/docs/eo-icon.md

Lines changed: 93 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -20,6 +20,10 @@ Your favorite icons, including [Ant Design Icons](https://ant.design/components/
2020
properties:
2121
lib: easyops
2222
icon: honeycomb
23+
- brick: eo-icon
24+
properties:
25+
lib: lucide
26+
icon: activity
2327
```
2428
2529
## Examples
@@ -80,6 +84,32 @@ Your favorite icons, including [Ant Design Icons](https://ant.design/components/
8084
icon: github
8185
```
8286
87+
### Lucide
88+
89+
[View all Lucide icons.](https://lucide.dev/icons/)
90+
91+
```yaml preview
92+
- brick: div
93+
properties:
94+
style:
95+
display: flex
96+
gap: 1em
97+
fontSize: 32px
98+
children:
99+
- brick: eo-icon
100+
properties:
101+
lib: lucide
102+
icon: activity
103+
- brick: eo-icon
104+
properties:
105+
lib: lucide
106+
icon: languages
107+
- brick: eo-icon
108+
properties:
109+
lib: lucide
110+
icon: ambulance
111+
```
112+
83113
### EasyOps
84114
85115
```yaml preview
@@ -142,7 +172,7 @@ children:
142172
properties:
143173
style:
144174
display: grid
145-
gridTemplateColumns: repeat(3, 1fr)
175+
gridTemplateColumns: repeat(4, 1fr)
146176
justifyItems: center
147177
fontSize: 32px
148178
gap: 0.5em
@@ -162,6 +192,10 @@ children:
162192
lib: easyops
163193
category: default
164194
icon: account
195+
- brick: eo-icon
196+
properties:
197+
lib: lucide
198+
icon: ambulance
165199
- brick: eo-icon
166200
properties:
167201
lib: antd
@@ -183,6 +217,12 @@ children:
183217
icon: account
184218
style:
185219
color: gray
220+
- brick: eo-icon
221+
properties:
222+
lib: lucide
223+
icon: ambulance
224+
style:
225+
color: red
186226
- brick: eo-icon
187227
properties:
188228
lib: antd
@@ -205,6 +245,13 @@ children:
205245
icon: bell
206246
startColor: pink
207247
endColor: purple
248+
- brick: eo-icon
249+
properties:
250+
lib: lucide
251+
icon: ambulance
252+
gradientDirection: left-to-right
253+
startColor: pink
254+
endColor: red
208255
```
209256
210257
### Spinning
@@ -234,6 +281,11 @@ children:
234281
lib: easyops
235282
category: third-menu
236283
icon: placeholder-third-menu
284+
- brick: eo-icon
285+
properties:
286+
spinning: true
287+
lib: lucide
288+
icon: loader-circle
237289
```
238290
239291
### Fallback
@@ -267,6 +319,13 @@ children:
267319
fallback:
268320
lib: fa
269321
icon: question
322+
- brick: eo-icon
323+
properties:
324+
lib: lucide
325+
icon: oops
326+
fallback:
327+
lib: fa
328+
icon: question
270329
- brick: eo-icon
271330
properties:
272331
lib: antd
@@ -284,3 +343,36 @@ children:
284343
fallback:
285344
imgSrc: "https://cdn.jsdelivr.net/npm/[email protected]/icons/y-chart.svg"
286345
```
346+
347+
### Lucide stroke width
348+
349+
Lucide icons support setting `strokeWidth` which defaults to `2` (and restrict to range `[0.5, 3]`).
350+
351+
```yaml preview
352+
- brick: div
353+
properties:
354+
style:
355+
display: grid
356+
gridTemplateColumns: repeat(6, 1fr)
357+
width: fit-content
358+
gap: 0.25em 1em
359+
fontSize: 36px
360+
children:
361+
- brick: :forEach
362+
dataSource: [0.5, 1, 1.5, 2, 2.5, 3]
363+
children:
364+
- brick: eo-icon
365+
properties:
366+
lib: lucide
367+
icon: ambulance
368+
strokeWidth: <% ITEM %>
369+
- brick: :forEach
370+
dataSource: [0.5, 1, 1.5, 2, 2.5, 3]
371+
children:
372+
- brick: span
373+
properties:
374+
textContent: <% ITEM %>
375+
style:
376+
fontSize: 16px
377+
justifySelf: center
378+
```
Lines changed: 23 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,23 @@
1+
[View all Lucide icons.](https://lucide.dev/icons/)
2+
3+
```yaml preview
4+
- brick: div
5+
properties:
6+
style:
7+
display: flex
8+
gap: 1em
9+
fontSize: 32px
10+
children:
11+
- brick: eo-icon
12+
properties:
13+
lib: lucide
14+
icon: activity
15+
- brick: eo-icon
16+
properties:
17+
lib: lucide
18+
icon: languages
19+
- brick: eo-icon
20+
properties:
21+
lib: lucide
22+
icon: ambulance
23+
```

bricks/icons/package.json

Lines changed: 5 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -25,15 +25,17 @@
2525
"{projectRoot}/deploy",
2626
"{projectRoot}/src/antd-icon/generated",
2727
"{projectRoot}/src/easyops-icon/generated",
28-
"{projectRoot}/src/fa-icon/generated"
28+
"{projectRoot}/src/fa-icon/generated",
29+
"{projectRoot}/src/lucide-icon/generated"
2930
]
3031
},
3132
"build:types": {
3233
"outputs": [
3334
"{projectRoot}/dist-types",
3435
"{projectRoot}/src/antd-icon/generated",
3536
"{projectRoot}/src/easyops-icon/generated",
36-
"{projectRoot}/src/fa-icon/generated"
37+
"{projectRoot}/src/fa-icon/generated",
38+
"{projectRoot}/src/lucide-icon/generated"
3739
]
3840
},
3941
"build:main": {
@@ -80,6 +82,7 @@
8082
"@next-core/runtime": "^1.65.0",
8183
"@next-core/utils": "^1.8.2",
8284
"lodash": "^4.17.21",
85+
"lucide-static": "0.539.0",
8386
"react": "0.0.0-experimental-ee8509801-20230117"
8487
},
8588
"devDependencies": {

bricks/icons/scripts/pre-build.js

Lines changed: 79 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -305,6 +305,85 @@ const tasks = [];
305305
);
306306
}
307307

308+
{
309+
// --- Lucide Icons start ---
310+
const lucideIconsPath = path.resolve(
311+
require.resolve("lucide-static/package.json"),
312+
"../icons"
313+
);
314+
const generatedDir = path.resolve(__dirname, "../src/lucide-icon/generated");
315+
if (existsSync(generatedDir)) {
316+
rmSync(generatedDir, { recursive: true, force: true });
317+
}
318+
mkdirSync(generatedDir);
319+
320+
const defaultCategory = "default";
321+
const allIcons = {
322+
[defaultCategory]: [],
323+
};
324+
325+
const ranges = {};
326+
const allSvg = [];
327+
const iconsWithPath = [];
328+
let cursor = -2;
329+
330+
tasks.push(
331+
(async () => {
332+
const icons = await readdir(lucideIconsPath);
333+
for (const icon of icons) {
334+
const [_m, iconName, ext] = icon.match(/^(.*?)(\.[^.]+)?$/);
335+
if (ext === ".svg") {
336+
allIcons[defaultCategory].push(iconName);
337+
iconsWithPath.push([
338+
defaultCategory,
339+
path.join(lucideIconsPath, icon),
340+
]);
341+
}
342+
}
343+
344+
const hashes = [];
345+
346+
// Have to be sequential
347+
for (const [category, iconPath] of iconsWithPath) {
348+
const svg = await readFile(iconPath);
349+
allSvg.push(svg);
350+
351+
let groupRanges = ranges[category];
352+
if (!_.has(ranges, category)) {
353+
groupRanges = ranges[category] = [];
354+
}
355+
cursor += svg.length + 1;
356+
groupRanges.push(cursor);
357+
358+
const sha1 = createHash("sha1");
359+
sha1.update(svg);
360+
hashes.push(sha1.digest("hex").substring(0, 8));
361+
}
362+
363+
// Let final hash to be irrelevant to the order of icons
364+
hashes.sort();
365+
const sha1 = createHash("sha1");
366+
sha1.update(hashes.join(""));
367+
ranges._hash = sha1.digest("hex").substring(0, 8);
368+
369+
await Promise.all([
370+
writeFile(
371+
path.resolve(generatedDir, "icons.json"),
372+
JSON.stringify(allIcons)
373+
),
374+
writeFile(
375+
path.resolve(generatedDir, "ranges.json"),
376+
JSON.stringify(ranges)
377+
),
378+
writeFile(
379+
path.resolve(generatedDir, `all.${ranges._hash}.svg`),
380+
allSvg.join("\n")
381+
),
382+
]);
383+
})()
384+
);
385+
}
386+
308387
Promise.all(tasks).then(
309388
() => {
310389
console.log("Generate icon files done!");

bricks/icons/src/data-providers/get-icons.ts

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,7 @@ import { createProviderClass } from "@next-core/utils/general";
22
import antdIcons from "../antd-icon/generated/icons.json";
33
import easyopsIcons from "../easyops-icon/generated/icons.json";
44
import faIcons from "../fa-icon/generated/icons.json";
5+
import lucideIcons from "../lucide-icon/generated/icons.json";
56

67
export async function getEasyopsIcons(): Promise<Record<string, string[]>> {
78
return easyopsIcons;
@@ -15,6 +16,10 @@ export async function getAntdIcons(): Promise<Record<string, string[]>> {
1516
return antdIcons;
1617
}
1718

19+
export async function getLucideIcons(): Promise<Record<string, string[]>> {
20+
return lucideIcons;
21+
}
22+
1823
customElements.define(
1924
"icons.get-easyops-icons",
2025
createProviderClass(getEasyopsIcons)
@@ -26,3 +31,8 @@ customElements.define(
2631
"icons.get-antd-icons",
2732
createProviderClass(getAntdIcons)
2833
);
34+
35+
customElements.define(
36+
"icons.get-lucide-icons",
37+
createProviderClass(getLucideIcons)
38+
);

bricks/icons/src/data-providers/get-libs.spec.ts

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -29,6 +29,14 @@ describe("getLibs", () => {
2929
}),
3030
]),
3131
}),
32+
expect.objectContaining({
33+
lib: "lucide",
34+
icons: expect.arrayContaining([
35+
expect.objectContaining({
36+
title: "activity",
37+
}),
38+
]),
39+
}),
3240
])
3341
);
3442
});

0 commit comments

Comments
 (0)