@firerian/fireui 1.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.
Files changed (63) hide show
  1. package/LICENSE +21 -0
  2. package/README.md +74 -0
  3. package/dist/fireui.cjs +2 -0
  4. package/dist/fireui.cjs.map +1 -0
  5. package/dist/fireui.css +1 -0
  6. package/dist/fireui.es.mjs +3867 -0
  7. package/dist/fireui.es.mjs.map +1 -0
  8. package/dist/fireui.umd.js +2 -0
  9. package/dist/fireui.umd.js.map +1 -0
  10. package/dist/types/index.d.ts +1590 -0
  11. package/package.json +132 -0
  12. package/src/components/button/button.test.ts +357 -0
  13. package/src/components/button/button.vue +366 -0
  14. package/src/components/button/index.ts +17 -0
  15. package/src/components/button/types.ts +76 -0
  16. package/src/components/form/form-item.vue +136 -0
  17. package/src/components/form/form.vue +76 -0
  18. package/src/components/form/index.ts +16 -0
  19. package/src/components/grid/col.vue +99 -0
  20. package/src/components/grid/index.ts +16 -0
  21. package/src/components/grid/row.vue +85 -0
  22. package/src/components/grid/types.ts +66 -0
  23. package/src/components/index.ts +36 -0
  24. package/src/components/input/index.ts +8 -0
  25. package/src/components/input/input.test.ts +129 -0
  26. package/src/components/input/input.vue +256 -0
  27. package/src/components/input/types.ts +100 -0
  28. package/src/components/layout/aside.vue +89 -0
  29. package/src/components/layout/container.vue +53 -0
  30. package/src/components/layout/footer.vue +57 -0
  31. package/src/components/layout/header.vue +56 -0
  32. package/src/components/layout/index.ts +28 -0
  33. package/src/components/layout/main.vue +36 -0
  34. package/src/components/layout/types.ts +74 -0
  35. package/src/components/table/index.ts +16 -0
  36. package/src/components/table/table-column.vue +69 -0
  37. package/src/components/table/table.vue +354 -0
  38. package/src/components/tips/index.ts +12 -0
  39. package/src/components/tips/tips.test.ts +96 -0
  40. package/src/components/tips/tips.vue +206 -0
  41. package/src/components/tips/types.ts +56 -0
  42. package/src/components/tooltip/index.ts +8 -0
  43. package/src/components/tooltip/tooltip.test.ts +187 -0
  44. package/src/components/tooltip/tooltip.vue +261 -0
  45. package/src/components/tooltip/types.ts +60 -0
  46. package/src/hooks/useForm.ts +233 -0
  47. package/src/hooks/useTable.ts +153 -0
  48. package/src/index.ts +48 -0
  49. package/src/styles/main.scss +6 -0
  50. package/src/styles/mixins.scss +48 -0
  51. package/src/styles/reset.scss +49 -0
  52. package/src/styles/variables.scss +137 -0
  53. package/src/types/component.ts +9 -0
  54. package/src/types/form.ts +149 -0
  55. package/src/types/global.d.ts +49 -0
  56. package/src/types/grid.ts +76 -0
  57. package/src/types/index.ts +23 -0
  58. package/src/types/table.ts +181 -0
  59. package/src/types/tooltip.ts +44 -0
  60. package/src/utils/auto-import.ts +41 -0
  61. package/src/utils/index.ts +2 -0
  62. package/src/utils/install.ts +20 -0
  63. package/src/utils/useNamespace.ts +29 -0
@@ -0,0 +1,366 @@
1
+ <template>
2
+ <button
3
+ ref="buttonRef"
4
+ :class="buttonClasses"
5
+ :disabled="disabled || loading"
6
+ :type="nativeType"
7
+ :style="buttonStyles"
8
+ @click="handleClick"
9
+ >
10
+ <!-- 加载图标 -->
11
+ <template v-if="loading">
12
+ <slot name="loading">
13
+ <span :class="`${prefixCls}-loading-icon`">
14
+ <svg
15
+ v-if="!loadingIcon"
16
+ :class="`${prefixCls}-loading-svg`"
17
+ viewBox="0 0 16 16"
18
+ width="1em"
19
+ height="1em"
20
+ >
21
+ <circle
22
+ cx="8"
23
+ cy="8"
24
+ r="7"
25
+ stroke="currentColor"
26
+ stroke-width="2"
27
+ fill="none"
28
+ stroke-linecap="round"
29
+ stroke-dasharray="44"
30
+ stroke-dashoffset="11"
31
+ />
32
+ </svg>
33
+ <img v-else :src="loadingIcon" :alt="loadingIcon" :class="`${prefixCls}-loading-img`" />
34
+ </span>
35
+ </slot>
36
+ </template>
37
+
38
+ <!-- 自定义图标 -->
39
+ <template v-else-if="icon">
40
+ <slot name="icon">
41
+ <span :class="`${prefixCls}-icon`">
42
+ <component :is="icon" />
43
+ </span>
44
+ </slot>
45
+ </template>
46
+
47
+ <!-- 默认内容 -->
48
+ <span :class="`${prefixCls}-content`">
49
+ <slot />
50
+ </span>
51
+ </button>
52
+ </template>
53
+
54
+ <script setup lang="ts">
55
+ import { computed, ref } from 'vue'
56
+ // 类型定义内联,避免模块解析问题
57
+ type ButtonType = 'default' | 'primary' | 'success' | 'warning' | 'danger' | 'info'
58
+ type ButtonSize = 'small' | 'default' | 'large'
59
+ type ButtonNativeType = 'button' | 'submit' | 'reset'
60
+
61
+ /**
62
+ * @file Button 组件
63
+ * @description 常用的操作按钮组件,支持多种类型、尺寸和状态
64
+ * @example
65
+ * ```vue
66
+ * <template>
67
+ * <FButton type="primary">主要按钮</FButton>
68
+ * <FButton type="success" size="large">成功按钮</FButton>
69
+ * <FButton :loading="true">加载中</FButton>
70
+ * </template>
71
+ * ```
72
+ */
73
+
74
+ defineOptions({
75
+ name: 'FButton',
76
+ inheritAttrs: false,
77
+ })
78
+
79
+ // Props 定义 - 使用接口避免类型推断问题
80
+ interface Props {
81
+ type?: ButtonType
82
+ size?: ButtonSize
83
+ nativeType?: ButtonNativeType
84
+ disabled?: boolean
85
+ loading?: boolean
86
+ circle?: boolean
87
+ block?: boolean
88
+ loadingIcon?: string
89
+ icon?: string
90
+ }
91
+
92
+ const props = withDefaults(defineProps<Props>(), {
93
+ type: 'default',
94
+ size: 'default',
95
+ nativeType: 'button',
96
+ disabled: false,
97
+ loading: false,
98
+ circle: false,
99
+ block: false,
100
+ loadingIcon: '',
101
+ icon: '',
102
+ })
103
+
104
+ // Emits 定义
105
+ const emit = defineEmits<{
106
+ click: [event: MouseEvent]
107
+ }>()
108
+
109
+ // 组件前缀
110
+ const prefixCls = 'f-button'
111
+
112
+ // 组件引用
113
+ const buttonRef = ref<HTMLButtonElement>()
114
+
115
+ // 解构 props 以避免响应式丢失
116
+ const { type, size, disabled, loading, circle, block, nativeType, loadingIcon, icon } = props
117
+
118
+ /**
119
+ * 计算按钮的 class 列表
120
+ */
121
+ const buttonClasses = computed(() => [
122
+ prefixCls,
123
+ `${prefixCls}--${type}`,
124
+ `${prefixCls}--${size}`,
125
+ {
126
+ [`${prefixCls}--disabled`]: disabled,
127
+ [`${prefixCls}--loading`]: loading,
128
+ [`${prefixCls}--circle`]: circle,
129
+ [`${prefixCls}--block`]: block,
130
+ },
131
+ ])
132
+
133
+ /**
134
+ * 计算按钮的内联样式(用于 CSS 变量)
135
+ */
136
+ const buttonStyles = computed(() => ({
137
+ '--f-button-primary-color': `var(--f-color-${type})`,
138
+ '--f-button-primary-hover': `var(--f-color-${type}-hover)`,
139
+ '--f-button-primary-active': `var(--f-color-${type}-active)`,
140
+ }))
141
+
142
+ /**
143
+ * 处理点击事件
144
+ */
145
+ const handleClick = (event: MouseEvent) => {
146
+ if (disabled || loading) return
147
+ emit('click', event)
148
+ }
149
+
150
+ // 暴露组件方法
151
+ defineExpose({
152
+ ref: buttonRef,
153
+ })
154
+ </script>
155
+
156
+ <style lang="scss" scoped>
157
+ @use 'sass:color';
158
+ @use '../../styles/mixins' as *;
159
+ @use '../../styles/variables' as *;
160
+
161
+ // Button 基础样式
162
+ .f-button {
163
+ // 使用 CSS 变量实现主题
164
+ --f-button-bg-color: #{$button-default-bg};
165
+ --f-button-border-color: #{$button-default-border};
166
+ --f-button-text-color: #{$button-default-text};
167
+ --f-button-hover-bg: #{color.adjust($button-default-bg, $lightness: -5%)};
168
+ --f-button-hover-border: #{color.adjust($button-default-border, $lightness: -10%)};
169
+
170
+ // 基础样式
171
+ @include button-base;
172
+
173
+ // 布局
174
+ display: inline-flex;
175
+ align-items: center;
176
+ justify-content: center;
177
+ gap: $spacing-xs;
178
+ position: relative;
179
+
180
+ // 尺寸
181
+ padding: $button-padding-vertical $button-padding-horizontal;
182
+ font-size: $button-font-size;
183
+ line-height: 1.5;
184
+ font-weight: 500;
185
+
186
+ // 外观
187
+ background-color: var(--f-button-bg-color);
188
+ border: 1px solid var(--f-button-border-color);
189
+ color: var(--f-button-text-color);
190
+ border-radius: $button-border-radius;
191
+
192
+ // 过渡
193
+ transition: all 0.2s ease-in-out;
194
+
195
+ // 禁用状态
196
+ &--disabled {
197
+ cursor: not-allowed;
198
+ opacity: 0.6;
199
+ pointer-events: none;
200
+
201
+ &:hover {
202
+ background-color: var(--f-button-bg-color);
203
+ border-color: var(--f-button-border-color);
204
+ }
205
+ }
206
+
207
+ // 加载状态
208
+ &--loading {
209
+ cursor: wait;
210
+ pointer-events: none;
211
+
212
+ .f-button-loading-icon {
213
+ animation: f-button-loading-spin 1s linear infinite;
214
+ }
215
+ }
216
+
217
+ // 圆形按钮
218
+ &--circle {
219
+ border-radius: 50%;
220
+ padding: $button-padding-vertical;
221
+ aspect-ratio: 1;
222
+
223
+ .f-button-content {
224
+ display: none;
225
+ }
226
+ }
227
+
228
+ // 块级按钮
229
+ &--block {
230
+ width: 100%;
231
+ }
232
+
233
+ // 类型变体
234
+ &--default {
235
+ --f-button-bg-color: #{$button-default-bg};
236
+ --f-button-border-color: #{$button-default-border};
237
+ --f-button-text-color: #{$button-default-text};
238
+ --f-button-hover-bg: #{color.adjust($button-default-bg, $lightness: -5%)};
239
+ --f-button-hover-border: #{color.adjust($button-default-border, $lightness: -10%)};
240
+ }
241
+
242
+ &--primary {
243
+ --f-button-bg-color: #{$button-primary-bg};
244
+ --f-button-border-color: #{$button-primary-border};
245
+ --f-button-text-color: #{$button-primary-text};
246
+ --f-button-hover-bg: #{$button-primary-hover};
247
+ --f-button-hover-border: #{$button-primary-hover};
248
+ }
249
+
250
+ &--success {
251
+ --f-button-bg-color: #{$button-success-bg};
252
+ --f-button-border-color: #{$button-success-border};
253
+ --f-button-text-color: #{$button-success-text};
254
+ --f-button-hover-bg: #{$button-success-hover};
255
+ --f-button-hover-border: #{$button-success-hover};
256
+ }
257
+
258
+ &--warning {
259
+ --f-button-bg-color: #{$button-warning-bg};
260
+ --f-button-border-color: #{$button-warning-border};
261
+ --f-button-text-color: #{$button-warning-text};
262
+ --f-button-hover-bg: #{$button-warning-hover};
263
+ --f-button-hover-border: #{$button-warning-hover};
264
+ }
265
+
266
+ &--danger {
267
+ --f-button-bg-color: #{$button-danger-bg};
268
+ --f-button-border-color: #{$button-danger-border};
269
+ --f-button-text-color: #{$button-danger-text};
270
+ --f-button-hover-bg: #{$button-danger-hover};
271
+ --f-button-hover-border: #{$button-danger-hover};
272
+ }
273
+
274
+ &--info {
275
+ --f-button-bg-color: #{$button-info-bg};
276
+ --f-button-border-color: #{$button-info-border};
277
+ --f-button-text-color: #{$button-info-text};
278
+ --f-button-hover-bg: #{$button-info-hover};
279
+ --f-button-hover-border: #{$button-info-hover};
280
+ }
281
+
282
+ // 尺寸变体
283
+ &--small {
284
+ padding: $button-padding-vertical-sm $button-padding-horizontal-sm;
285
+ font-size: $button-font-size-sm;
286
+
287
+ &.f-button--circle {
288
+ width: 24px;
289
+ height: 24px;
290
+ }
291
+ }
292
+
293
+ &--default {
294
+ padding: $button-padding-vertical $button-padding-horizontal;
295
+ font-size: $button-font-size;
296
+
297
+ &.f-button--circle {
298
+ width: 32px;
299
+ height: 32px;
300
+ }
301
+ }
302
+
303
+ &--large {
304
+ padding: $button-padding-vertical-lg $button-padding-horizontal-lg;
305
+ font-size: $button-font-size-lg;
306
+
307
+ &.f-button--circle {
308
+ width: 40px;
309
+ height: 40px;
310
+ }
311
+ }
312
+
313
+ // 图标和内容对齐
314
+ &-icon,
315
+ &-loading-icon {
316
+ display: inline-flex;
317
+ align-items: center;
318
+ justify-content: center;
319
+ flex-shrink: 0;
320
+ }
321
+
322
+ &-loading-svg {
323
+ width: 1em;
324
+ height: 1em;
325
+ }
326
+
327
+ &-loading-img {
328
+ width: 1em;
329
+ height: 1em;
330
+ object-fit: contain;
331
+ }
332
+
333
+ &-content {
334
+ display: inline-block;
335
+ flex: 1;
336
+ text-align: center;
337
+ }
338
+
339
+ // 悬停效果(非禁用状态)
340
+ &:hover:not(&--disabled):not(&--loading) {
341
+ background-color: var(--f-button-hover-bg);
342
+ border-color: var(--f-button-hover-border);
343
+ }
344
+
345
+ // 激活效果
346
+ &:active:not(&--disabled):not(&--loading) {
347
+ transform: scale(0.98);
348
+ }
349
+
350
+ // 焦点效果
351
+ &:focus-visible {
352
+ outline: 2px solid var(--f-button-primary-color);
353
+ outline-offset: 2px;
354
+ }
355
+ }
356
+
357
+ // 加载动画
358
+ @keyframes f-button-loading-spin {
359
+ 0% {
360
+ transform: rotate(0deg);
361
+ }
362
+ 100% {
363
+ transform: rotate(360deg);
364
+ }
365
+ }
366
+ </style>
@@ -0,0 +1,17 @@
1
+ /**
2
+ * @file Button 组件导出
3
+ * @description 导出 Button 组件及其类型
4
+ */
5
+
6
+ import Button from './button.vue'
7
+ import type { ButtonProps, ButtonEmits, ButtonSlots } from './types'
8
+
9
+ // 导出组件实例类型
10
+ export type ButtonInstance = InstanceType<typeof Button>
11
+
12
+ // 导出组件
13
+ export { Button as FButton }
14
+ export default Button
15
+
16
+ // 导出类型
17
+ export type { ButtonProps, ButtonEmits, ButtonSlots }
@@ -0,0 +1,76 @@
1
+ /**
2
+ * @file Button 组件类型定义
3
+ * @description 定义 Button 组件的 Props、Emits 和 Slots 接口
4
+ */
5
+
6
+ /**
7
+ * Button 组件尺寸类型
8
+ */
9
+ export type ButtonSize = 'small' | 'default' | 'large'
10
+
11
+ /**
12
+ * Button 组件类型
13
+ */
14
+ export type ButtonType = 'default' | 'primary' | 'success' | 'warning' | 'danger' | 'info'
15
+
16
+ /**
17
+ * Button 组件原生类型
18
+ */
19
+ export type ButtonNativeType = 'button' | 'submit' | 'reset'
20
+
21
+ /**
22
+ * Button 组件 Props 接口
23
+ */
24
+ export interface ButtonProps {
25
+ /** 按钮类型 - 用于区分不同的视觉样式 */
26
+ type?: ButtonType
27
+
28
+ /** 按钮尺寸 - 控制按钮的大小 */
29
+ size?: ButtonSize
30
+
31
+ /** 按钮原生类型 - 用于表单提交等场景 */
32
+ nativeType?: ButtonNativeType
33
+
34
+ /** 是否禁用 - 禁用状态下按钮不可点击 */
35
+ disabled?: boolean
36
+
37
+ /** 是否加载中 - 显示加载状态和动画 */
38
+ loading?: boolean
39
+
40
+ /** 是否为圆形按钮 - 常用于图标按钮 */
41
+ circle?: boolean
42
+
43
+ /** 是否为块级元素 - 按钮宽度占满容器 */
44
+ block?: boolean
45
+
46
+ /** 自定义加载图标 - 可自定义加载时的图标 */
47
+ loadingIcon?: string
48
+
49
+ /** 自定义图标 - 按钮左侧的图标 */
50
+ icon?: string
51
+
52
+ /** 原生 HTML 属性 - 透传到 button 元素 */
53
+ [key: string]: any
54
+ }
55
+
56
+ /**
57
+ * Button 组件 Emits 接口
58
+ */
59
+ export interface ButtonEmits {
60
+ /** 点击事件 - 当按钮被点击时触发 */
61
+ (e: 'click', event: MouseEvent): void
62
+ }
63
+
64
+ /**
65
+ * Button 组件 Slots 接口
66
+ */
67
+ export interface ButtonSlots {
68
+ /** 默认插槽 - 按钮内容 */
69
+ default?: () => any
70
+
71
+ /** 图标插槽 - 自定义图标内容 */
72
+ icon?: () => any
73
+
74
+ /** 加载插槽 - 自定义加载状态内容 */
75
+ loading?: () => any
76
+ }
@@ -0,0 +1,136 @@
1
+ <template>
2
+ <div
3
+ :class="[
4
+ ns.b,
5
+ {
6
+ [ns.m('error')]: errorMessage
7
+ }
8
+ ]"
9
+ >
10
+ <label v-if="label" class="fire-form-item__label" :style="labelStyle">
11
+ <span v-if="isRequired && !formContext.hideRequiredAsterisk" class="fire-form-item__asterisk">*</span>
12
+ {{ label }}
13
+ </label>
14
+ <div class="fire-form-item__content">
15
+ <slot></slot>
16
+ <div v-if="errorMessage" class="fire-form-item__error">{{ errorMessage }}</div>
17
+ </div>
18
+ </div>
19
+ </template>
20
+
21
+ <script setup lang="ts">
22
+ import { computed, watch, onMounted, onUnmounted } from 'vue'
23
+ import { useFormItem } from '../../hooks/useForm'
24
+ import { useNamespace } from '../../utils'
25
+ import type { FormItemProps, FormItemEmits } from '../../types/form'
26
+
27
+ const ns = useNamespace('form-item')
28
+
29
+ const props = withDefaults(defineProps<FormItemProps>(), {
30
+ prop: '',
31
+ label: '',
32
+ labelWidth: '',
33
+ required: false,
34
+ error: ''
35
+ })
36
+
37
+ defineEmits<FormItemEmits>()
38
+
39
+ const { formContext, error, validate, resetField, clearValidate } = useFormItem(props.prop)
40
+
41
+ const errorMessage = computed(() => {
42
+ return props.error || error.value
43
+ })
44
+
45
+ const isRequired = computed(() => {
46
+ if (props.required) return true
47
+ if (!props.prop) return false
48
+
49
+ const rules = formContext.rules[props.prop as keyof typeof formContext.rules]
50
+ if (!rules) return false
51
+
52
+ const ruleArray = Array.isArray(rules) ? rules : [rules]
53
+ return ruleArray.some(rule => rule.required)
54
+ })
55
+
56
+ const labelStyle = computed(() => {
57
+ const width = props.labelWidth || formContext.labelWidth
58
+ return width ? { width: typeof width === 'number' ? `${width}px` : width } : {}
59
+ })
60
+
61
+ // 注册 FormItem 到 Form
62
+ onMounted(() => {
63
+ formContext.addFormItem({
64
+ validate,
65
+ resetField,
66
+ clearValidate
67
+ } as any)
68
+ })
69
+
70
+ onUnmounted(() => {
71
+ formContext.removeFormItem({
72
+ validate,
73
+ resetField,
74
+ clearValidate
75
+ } as any)
76
+ })
77
+
78
+ // 监听 model 变化,自动校验
79
+ if (props.prop) {
80
+ watch(() => formContext.model[props.prop as keyof typeof formContext.model], () => {
81
+ validate('change')
82
+ })
83
+ }
84
+ </script>
85
+
86
+ <style scoped lang="scss">
87
+ @import '../../styles/variables.scss';
88
+
89
+ .#{$namespace}-form-item {
90
+ display: flex;
91
+ margin-bottom: 16px;
92
+
93
+ &--error {
94
+ .#{$namespace}-form-item__error {
95
+ color: $danger-color;
96
+ }
97
+
98
+ .#{$namespace}-form-item__content input,
99
+ .#{$namespace}-form-item__content textarea,
100
+ .#{$namespace}-form-item__content select {
101
+ border-color: $danger-color;
102
+
103
+ &:focus {
104
+ border-color: $danger-color;
105
+ box-shadow: 0 0 0 2px rgba($danger-color, 0.2);
106
+ }
107
+ }
108
+ }
109
+
110
+ &__label {
111
+ display: inline-block;
112
+ font-size: 14px;
113
+ color: $text-color;
114
+ font-weight: 500;
115
+ text-align: right;
116
+ margin-right: 12px;
117
+ white-space: nowrap;
118
+ }
119
+
120
+ &__asterisk {
121
+ color: $danger-color;
122
+ margin-right: 4px;
123
+ }
124
+
125
+ &__content {
126
+ flex: 1;
127
+ min-width: 0;
128
+ }
129
+
130
+ &__error {
131
+ font-size: 12px;
132
+ line-height: 1;
133
+ margin-top: 4px;
134
+ }
135
+ }
136
+ </style>
@@ -0,0 +1,76 @@
1
+ <template>
2
+ <form
3
+ :class="[
4
+ ns.b,
5
+ ns.m(labelPosition),
6
+ {
7
+ [ns.m('inline')]: inline
8
+ }
9
+ ]"
10
+ @submit.prevent="handleSubmit"
11
+ @reset="handleReset"
12
+ >
13
+ <slot></slot>
14
+ </form>
15
+ </template>
16
+
17
+ <script setup lang="ts">
18
+
19
+ import { provideForm } from '../../hooks/useForm'
20
+ import { useNamespace } from '../../utils'
21
+ import type { FormProps, FormEmits } from '../../types/form'
22
+
23
+ const ns = useNamespace('form')
24
+
25
+ const props = withDefaults(defineProps<FormProps>(), {
26
+ model: () => ({}),
27
+ rules: () => ({}),
28
+ labelWidth: '',
29
+ labelPosition: 'left',
30
+ inline: false,
31
+ hideRequiredAsterisk: false
32
+ })
33
+
34
+ const emit = defineEmits<FormEmits>()
35
+
36
+ const formContext = provideForm(props)
37
+
38
+ const handleSubmit = (evt: Event) => {
39
+ emit('submit', evt)
40
+ }
41
+
42
+ const handleReset = () => {
43
+ formContext.form.resetFields()
44
+ emit('reset')
45
+ }
46
+ </script>
47
+
48
+ <style scoped lang="scss">
49
+ @import '../../styles/variables.scss';
50
+
51
+ .#{$namespace}-form {
52
+ width: 100%;
53
+
54
+ &--inline {
55
+ display: flex;
56
+ flex-wrap: wrap;
57
+ gap: 16px;
58
+ }
59
+
60
+ &--top {
61
+ .#{$namespace}-form-item {
62
+ align-items: flex-start;
63
+
64
+ .#{$namespace}-form-item__label {
65
+ margin-bottom: 8px;
66
+ }
67
+ }
68
+ }
69
+
70
+ &--left {
71
+ .#{$namespace}-form-item {
72
+ align-items: center;
73
+ }
74
+ }
75
+ }
76
+ </style>
@@ -0,0 +1,16 @@
1
+ import Form from './form.vue'
2
+ import FormItem from './form-item.vue'
3
+ import { withInstall } from '../../utils'
4
+
5
+ const FireForm = withInstall(Form)
6
+ const FireFormItem = withInstall(FormItem)
7
+
8
+ export {
9
+ FireForm,
10
+ FireFormItem
11
+ }
12
+
13
+ export default {
14
+ FireForm,
15
+ FireFormItem
16
+ }