Skip to content

Commit e613c81

Browse files
authored
feat(arco): add arco design vue resolver (#252)
1 parent 6ae07b0 commit e613c81

File tree

2 files changed

+180
-0
lines changed

2 files changed

+180
-0
lines changed

README.md

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -166,6 +166,7 @@ We have several built-in resolvers for popular UI libraries like **Vuetify**, **
166166
Supported Resolvers:
167167

168168
- [Ant Design Vue](https://github.com/antfu/unplugin-vue-components/blob/main/src/core/resolvers/antdv.ts)
169+
- [Arco Design Vue](https://github.com/antfu/unplugin-vue-components/blob/main/src/core/resolvers/arco.ts)
169170
- [Element Plus](https://github.com/antfu/unplugin-vue-components/blob/main/src/core/resolvers/element-plus.ts)
170171
- [Element UI](https://github.com/antfu/unplugin-vue-components/blob/main/src/core/resolvers/element-ui.ts)
171172
- [Headless UI](https://github.com/antfu/unplugin-vue-components/blob/main/src/core/resolvers/headless-ui.ts)

src/core/resolvers/arco.ts

Lines changed: 179 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,179 @@
1+
import { ComponentResolver } from '../../types'
2+
import { kebabCase } from '../utils'
3+
4+
const matchComponents = [
5+
{
6+
pattern: /^AnchorLink$/,
7+
componentDir: 'anchor',
8+
},
9+
{
10+
pattern: /^AvatarGroup$/,
11+
componentDir: 'avatar',
12+
},
13+
{
14+
pattern: /^BreadcrumbItem$/,
15+
componentDir: 'breadcrumb',
16+
},
17+
18+
{
19+
pattern: /^ButtonGroup$/,
20+
componentDir: 'button',
21+
},
22+
{
23+
pattern: /^(CardMeta|CardGrid)$/,
24+
componentDir: 'card',
25+
},
26+
{
27+
pattern: /^CarouselItem$/,
28+
componentDir: 'carousel',
29+
},
30+
{
31+
pattern: /^CheckboxGroup$/,
32+
componentDir: 'checkbox',
33+
},
34+
{
35+
pattern: /^CollapseItem$/,
36+
componentDir: 'collapse',
37+
},
38+
{
39+
pattern: /^(WeekPicker|MonthPicker|YearPicker|QuarterPicker|RangePicker)$/,
40+
componentDir: 'date-picker',
41+
},
42+
{
43+
pattern: /^(Doption|Dgroup|Dsubmenu)$/,
44+
componentDir: 'dropdown',
45+
},
46+
{
47+
pattern: /^FormItem$/,
48+
componentDir: 'form',
49+
},
50+
{
51+
pattern: /^(Col|Row)$/,
52+
componentDir: 'grid',
53+
},
54+
55+
{
56+
pattern: /^(ImagePreview|ImagePreviewGroup)$/,
57+
componentDir: 'image',
58+
},
59+
{
60+
pattern: /^(InputGroup|InputSearch|InputPassword)$/,
61+
componentDir: 'input',
62+
},
63+
64+
{
65+
pattern: /^(LayoutHeader|LayoutContent|LayoutFooter|LayoutSider)$/,
66+
componentDir: 'layout',
67+
},
68+
{
69+
pattern: /^(ListItem|ListItemMeta)$/,
70+
componentDir: 'list',
71+
},
72+
{
73+
pattern: /^(MenuItem|MenuItemGroup|SubMenu)$/,
74+
componentDir: 'menu',
75+
},
76+
{
77+
pattern: /^RadioGroup$/,
78+
componentDir: 'radio',
79+
},
80+
{
81+
pattern: /^(Option|Optgroup)$/,
82+
componentDir: 'select',
83+
},
84+
85+
{
86+
pattern: /^(SkeletonLine|SkeletonShape)$/,
87+
componentDir: 'table',
88+
},
89+
{
90+
pattern: /^Countdown$/,
91+
componentDir: 'statistic',
92+
},
93+
94+
{
95+
pattern: /^Step$/,
96+
componentDir: 'steps',
97+
},
98+
99+
{
100+
pattern: /^(Thead|Td|Th|Tr|Tbody|TableColumn)$/,
101+
componentDir: 'table',
102+
},
103+
104+
{
105+
pattern: /^TabPane$/,
106+
componentDir: 'tabs',
107+
},
108+
{
109+
pattern: /^TimelineItem$/,
110+
componentDir: 'timeline',
111+
},
112+
113+
{
114+
pattern: /^(TypographyParagraph|TypographyTitle|TypographyText)$/,
115+
componentDir: 'typography',
116+
},
117+
]
118+
119+
function getComponentStyleDir(importName: string, importStyle: boolean | 'css' | 'less') {
120+
let componentDir = kebabCase(importName)
121+
for (const item of matchComponents) {
122+
if (item.pattern.test(importName)) {
123+
componentDir = item.componentDir
124+
break
125+
}
126+
}
127+
if (importStyle === 'less') return `@arco-design/web-vue/es/${componentDir}/style/index.js`
128+
if (importStyle === 'css' || importStyle) return `@arco-design/web-vue/es/${componentDir}/style/css.js`
129+
}
130+
131+
export interface ArcoResolverOptions {
132+
/**
133+
* import style css or less with components
134+
*
135+
* @default 'css'
136+
*/
137+
importStyle?: boolean | 'css' | 'less'
138+
/**
139+
* resolve icons
140+
*
141+
* @default false
142+
*/
143+
resolveIcons?: boolean
144+
}
145+
146+
/**
147+
* Resolver for Arco Design Vue
148+
*
149+
* Requires arco-design/web-vue@2.11.0 or later
150+
*
151+
* @author @flsion
152+
* @link https://arco.design/ for arco-design
153+
*
154+
*/
155+
export function ArcoResolver(
156+
options: ArcoResolverOptions = {},
157+
): ComponentResolver {
158+
return {
159+
type: 'component',
160+
resolve: (name: string) => {
161+
if (options.resolveIcons && name.match(/^Icon/)) {
162+
return {
163+
importName: name,
164+
path: '@arco-design/web-vue/es/icon',
165+
}
166+
}
167+
if (name.match(/^A/)) {
168+
const importStyle = options.importStyle ?? 'css'
169+
170+
const importName = name.slice(1)
171+
return {
172+
importName,
173+
path: '@arco-design/web-vue',
174+
sideEffects: getComponentStyleDir(importName, importStyle),
175+
}
176+
}
177+
},
178+
}
179+
}

0 commit comments

Comments
 (0)