@coffic/cosy-ui 0.1.29 → 0.2.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 (97) hide show
  1. package/README.md +67 -23
  2. package/dist/app.css +1 -0
  3. package/dist/assets/logo-rounded.png +0 -0
  4. package/dist/assets/logo.png +0 -0
  5. package/dist/components/base/Alert.astro +186 -0
  6. package/dist/components/base/Button.astro +103 -0
  7. package/dist/components/base/Image.astro +291 -0
  8. package/dist/components/base/Link.astro +131 -0
  9. package/dist/components/base/README.md +53 -0
  10. package/dist/components/base/index.ts +6 -0
  11. package/dist/components/containers/Container.astro +103 -0
  12. package/dist/components/containers/Main.astro +167 -0
  13. package/dist/components/containers/Section.astro +145 -0
  14. package/dist/components/containers/index.ts +3 -0
  15. package/dist/components/data-display/Blog.astro +195 -0
  16. package/dist/components/data-display/README.md +37 -0
  17. package/dist/components/data-display/TeamMember.astro +135 -0
  18. package/dist/components/data-display/TeamMembers.astro +101 -0
  19. package/dist/components/data-display/index.ts +3 -0
  20. package/dist/components/display/Banner.astro +57 -0
  21. package/dist/components/display/Card.astro +135 -0
  22. package/dist/components/display/CodeBlock.astro +147 -0
  23. package/dist/components/display/CodeExample.astro +330 -0
  24. package/dist/components/display/Hero.astro +119 -0
  25. package/dist/components/display/Modal.astro +115 -0
  26. package/dist/components/display/README.md +32 -0
  27. package/dist/components/display/index.ts +6 -0
  28. package/dist/components/icons/AlertTriangle.astro +35 -0
  29. package/dist/components/icons/CalendarIcon.astro +38 -0
  30. package/dist/components/icons/CheckCircle.astro +36 -0
  31. package/dist/components/icons/CheckIcon.astro +38 -0
  32. package/dist/components/icons/ClipboardIcon.astro +39 -0
  33. package/dist/components/icons/CloseIcon.astro +38 -0
  34. package/dist/components/icons/ErrorIcon.astro +35 -0
  35. package/dist/components/icons/GithubIcon.astro +31 -0
  36. package/dist/components/icons/InfoCircle.astro +37 -0
  37. package/dist/components/icons/InfoIcon.astro +38 -0
  38. package/dist/components/icons/LinkIcon.astro +39 -0
  39. package/dist/components/icons/LinkedinIcon.astro +31 -0
  40. package/dist/components/icons/MenuIcon.astro +41 -0
  41. package/dist/components/icons/SearchIcon.astro +40 -0
  42. package/dist/components/icons/SocialIcon.astro +100 -0
  43. package/dist/components/icons/SuccessIcon.astro +35 -0
  44. package/dist/components/icons/SunCloudyIcon.astro +45 -0
  45. package/dist/components/icons/TwitterIcon.astro +31 -0
  46. package/dist/components/icons/UserIcon.astro +35 -0
  47. package/dist/components/icons/WarningIcon.astro +38 -0
  48. package/dist/components/icons/XCircle.astro +37 -0
  49. package/dist/components/icons/index.ts +23 -0
  50. package/dist/components/layouts/BaseLayout.astro +144 -0
  51. package/dist/components/layouts/DashboardLayout.astro +660 -0
  52. package/dist/components/layouts/DefaultLayout.astro +170 -0
  53. package/dist/components/layouts/DocumentationLayout.astro +469 -0
  54. package/dist/components/layouts/Flex.astro +138 -0
  55. package/dist/components/layouts/Footer.astro +284 -0
  56. package/dist/components/layouts/Grid.astro +182 -0
  57. package/dist/components/layouts/Header.astro +114 -0
  58. package/dist/components/layouts/LandingLayout.astro +388 -0
  59. package/dist/components/layouts/README.md +37 -0
  60. package/dist/components/layouts/Stack.astro +149 -0
  61. package/dist/components/layouts/index.ts +6 -0
  62. package/dist/components/navigation/LanguageSwitcher.astro +81 -0
  63. package/dist/components/navigation/README.md +24 -0
  64. package/dist/components/navigation/TableOfContents.astro +352 -0
  65. package/dist/components/navigation/ThemeSwitcher.astro +89 -0
  66. package/dist/components/navigation/index.ts +3 -0
  67. package/dist/components/typography/Article.astro +144 -0
  68. package/dist/components/typography/Heading.astro +205 -0
  69. package/dist/components/typography/README.md +29 -0
  70. package/dist/components/typography/Text.astro +187 -0
  71. package/dist/components/typography/index.ts +3 -0
  72. package/dist/index.ts +9 -0
  73. package/dist/integration.ts +14 -0
  74. package/dist/style.ts +1 -0
  75. package/{src → dist}/types/footer.ts +1 -0
  76. package/dist/utils/theme.ts +55 -0
  77. package/package.json +65 -59
  78. package/index.ts +0 -18
  79. package/src/components/Alert.astro +0 -78
  80. package/src/components/Article.astro +0 -11
  81. package/src/components/Banner.astro +0 -49
  82. package/src/components/Blog.astro +0 -115
  83. package/src/components/Button.astro +0 -49
  84. package/src/components/Card.astro +0 -113
  85. package/src/components/CodeBlock.astro +0 -186
  86. package/src/components/Footer.astro +0 -148
  87. package/src/components/Header.astro +0 -305
  88. package/src/components/Hero.astro +0 -69
  89. package/src/components/Image.astro +0 -251
  90. package/src/components/Link.astro +0 -82
  91. package/src/components/Modal.astro +0 -67
  92. package/src/components/SocialIcon.astro +0 -36
  93. package/src/components/TeamMember.astro +0 -68
  94. package/src/components/TeamMembers.astro +0 -43
  95. package/src/env.d.ts +0 -0
  96. /package/{src/components → dist/components/base}/ThemeItem.astro +0 -0
  97. /package/{src → dist}/utils/social.ts +0 -0
@@ -0,0 +1,291 @@
1
+ ---
2
+ /**
3
+ * @component Image
4
+ *
5
+ * @description
6
+ * Image 组件是一个增强的图片组件,提供了丰富的功能,包括懒加载、加载状态指示、错误处理、
7
+ * 以及各种视觉效果。它旨在提供更好的用户体验和性能优化。
8
+ *
9
+ * @design
10
+ * 设计理念:
11
+ * 1. 用户体验优先 - 提供加载状态反馈,减少用户等待焦虑
12
+ * 2. 性能优化 - 支持懒加载,减少初始加载时间
13
+ * 3. 错误处理 - 优雅地处理图片加载失败的情况
14
+ * 4. 视觉一致性 - 提供统一的圆角、阴影和过渡效果
15
+ * 5. 灵活配置 - 支持多种自定义选项,适应不同场景
16
+ *
17
+ * @usage
18
+ * 基本用法:
19
+ * ```astro
20
+ * <Image src="/images/photo.jpg" alt="一张照片" />
21
+ * ```
22
+ *
23
+ * 带样式效果:
24
+ * ```astro
25
+ * <Image
26
+ * src="/images/photo.jpg"
27
+ * alt="一张照片"
28
+ * rounded="lg"
29
+ * shadow="md"
30
+ * hover="scale"
31
+ * />
32
+ * ```
33
+ *
34
+ * 自定义加载指示器:
35
+ * ```astro
36
+ * <Image
37
+ * src="https://example.com/large-image.jpg"
38
+ * alt="远程大图"
39
+ * loadingIndicator="progress"
40
+ * />
41
+ * ```
42
+ */
43
+
44
+ import "../../app.css";
45
+ import { AlertTriangle } from '../icons';
46
+
47
+ // 自定义图片元数据接口
48
+ interface ImageMetadata {
49
+ src: string;
50
+ width: number;
51
+ height: number;
52
+ format: string;
53
+ }
54
+
55
+ interface Props {
56
+ /**
57
+ * 图片源,可以是本地图片或远程URL
58
+ */
59
+ src: ImageMetadata | string;
60
+ /**
61
+ * 图片的替代文本
62
+ */
63
+ alt: string;
64
+ /**
65
+ * 图片的宽度
66
+ */
67
+ width?: number;
68
+ /**
69
+ * 图片的高度
70
+ */
71
+ height?: number;
72
+ /**
73
+ * 图片的加载方式
74
+ * @default "lazy"
75
+ */
76
+ loading?: 'lazy' | 'eager';
77
+ /**
78
+ * 图片的填充方式
79
+ * @default "cover"
80
+ */
81
+ objectFit?: 'contain' | 'cover' | 'fill' | 'none' | 'scale-down';
82
+ /**
83
+ * 图片的位置
84
+ * @default "center"
85
+ */
86
+ objectPosition?: string;
87
+ /**
88
+ * 是否显示加载中的占位图
89
+ * @default true
90
+ */
91
+ showPlaceholder?: boolean;
92
+ /**
93
+ * 是否显示加载失败的错误图
94
+ * @default true
95
+ */
96
+ showError?: boolean;
97
+ /**
98
+ * 自定义类名
99
+ */
100
+ class?: string;
101
+ /**
102
+ * 是否启用图片懒加载
103
+ * @default true
104
+ */
105
+ lazy?: boolean;
106
+ /**
107
+ * 图片的圆角大小
108
+ * @default "none"
109
+ */
110
+ rounded?: 'none' | 'sm' | 'md' | 'lg' | 'xl' | '2xl' | '3xl' | 'full';
111
+ /**
112
+ * 图片的阴影效果
113
+ * @default "none"
114
+ */
115
+ shadow?: 'none' | 'sm' | 'md' | 'lg' | 'xl' | '2xl';
116
+ /**
117
+ * 图片的悬停效果
118
+ * @default "none"
119
+ */
120
+ hover?: 'none' | 'scale' | 'brightness' | 'blur';
121
+ /**
122
+ * 图片的过渡动画
123
+ * @default "none"
124
+ */
125
+ transition?: 'none' | 'fade' | 'slide' | 'zoom';
126
+
127
+ /**
128
+ * 加载指示器类型
129
+ * @default "skeleton"
130
+ */
131
+ loadingIndicator?: 'pulse' | 'spinner' | 'progress' | 'skeleton';
132
+ }
133
+
134
+ const {
135
+ src,
136
+ alt,
137
+ width,
138
+ height,
139
+ loading = 'lazy',
140
+ objectFit = 'cover',
141
+ objectPosition = 'center',
142
+ showPlaceholder = true,
143
+ showError = true,
144
+ class: className = '',
145
+ lazy = true,
146
+ rounded = 'none',
147
+ shadow = 'none',
148
+ hover = 'none',
149
+ transition = 'none',
150
+ loadingIndicator = 'skeleton',
151
+ } = Astro.props;
152
+
153
+ // 判断是否为本地图片
154
+ const isLocalImage = typeof src !== 'string' && 'src' in src;
155
+ // 判断是否为远程图片
156
+ const isRemoteImage = typeof src === 'string' && (src.startsWith('http') || src.startsWith('//'));
157
+ // 获取图片源
158
+ const imgSrc = typeof src === 'string' ? src : src.src;
159
+
160
+ // 构建图片类名
161
+ const imgClasses = [
162
+ // DaisyUI 和 Tailwind 类
163
+ 'object-center',
164
+ objectFit === 'cover' ? 'object-cover' : `object-${objectFit}`,
165
+ rounded !== 'none' ? `rounded-${rounded}` : '',
166
+ shadow !== 'none' ? `shadow-${shadow}` : '',
167
+ hover === 'scale' ? 'hover:scale-110' : '',
168
+ hover === 'brightness' ? 'hover:brightness-110' : '',
169
+ hover === 'blur' ? 'hover:blur-sm' : '',
170
+ transition !== 'none' ? 'transition-all duration-300' : '',
171
+ className
172
+ ].filter(Boolean).join(' ');
173
+
174
+ // 构建占位图类名
175
+ const placeholderClasses = [
176
+ 'absolute inset-0',
177
+ rounded !== 'none' ? `rounded-${rounded}` : '',
178
+ loadingIndicator === 'skeleton' ? 'animate-pulse bg-base-300' : '',
179
+ loadingIndicator === 'pulse' ? 'animate-pulse bg-base-300' : '',
180
+ ].filter(Boolean).join(' ');
181
+
182
+ // 构建错误占位图类名
183
+ const errorClasses = [
184
+ 'absolute inset-0 flex items-center justify-center',
185
+ rounded !== 'none' ? `rounded-${rounded}` : '',
186
+ 'bg-error bg-opacity-10',
187
+ ].filter(Boolean).join(' ');
188
+ ---
189
+
190
+ <div class="relative w-full h-full">
191
+ <img
192
+ src={imgSrc}
193
+ alt={alt}
194
+ width={width}
195
+ height={height}
196
+ loading={loading}
197
+ class={imgClasses}
198
+ style={{ objectPosition }}
199
+ data-remote={isRemoteImage ? 'true' : 'false'}
200
+ />
201
+
202
+ {/* 加载占位图 */}
203
+ {showPlaceholder && (
204
+ <div class={placeholderClasses} data-placeholder>
205
+ {/* 远程图片加载指示器 */}
206
+ {isRemoteImage && loadingIndicator === 'spinner' && (
207
+ <div class="loading loading-spinner loading-lg text-primary absolute inset-0 m-auto" />
208
+ )}
209
+
210
+ {isRemoteImage && loadingIndicator === 'progress' && (
211
+ <div class="absolute bottom-0 left-0 right-0">
212
+ <progress class="progress progress-primary w-full" />
213
+ </div>
214
+ )}
215
+ </div>
216
+ )}
217
+
218
+ {/* 错误占位图 */}
219
+ {showError && (
220
+ <div class={errorClasses} data-error hidden>
221
+ <AlertTriangle size="32px" class="text-error" />
222
+ </div>
223
+ )}
224
+ </div>
225
+
226
+ <script is:inline>
227
+ function handleImageLoad(img) {
228
+ if (!(img instanceof HTMLImageElement)) return;
229
+ const placeholder = img.parentElement?.querySelector('[data-placeholder]');
230
+ if (placeholder) {
231
+ placeholder.classList.add('opacity-0');
232
+ setTimeout(() => placeholder.remove(), 300);
233
+ }
234
+ }
235
+
236
+ function handleImageError(img) {
237
+ if (!(img instanceof HTMLImageElement)) return;
238
+ const placeholder = img.parentElement?.querySelector('[data-placeholder]');
239
+ if (placeholder) {
240
+ placeholder.remove();
241
+ }
242
+ const errorElement = img.parentElement?.querySelector('[data-error]');
243
+ if (errorElement) {
244
+ errorElement.classList.remove('hidden');
245
+ }
246
+ }
247
+
248
+ function simulateLoadingProgress(img) {
249
+ if (!(img instanceof HTMLImageElement) || img.getAttribute('data-remote') !== 'true') return;
250
+ const progressBar = img.parentElement?.querySelector('progress');
251
+ if (!progressBar) return;
252
+
253
+ let progress = 0;
254
+ const interval = setInterval(() => {
255
+ progress += Math.random() * 15;
256
+ if (progress >= 100 || img.complete) {
257
+ clearInterval(interval);
258
+ progress = 100;
259
+ }
260
+ progressBar.value = Math.min(progress, 100);
261
+ }, 200);
262
+
263
+ img.addEventListener('load', () => {
264
+ clearInterval(interval);
265
+ progressBar.value = 100;
266
+ });
267
+
268
+ img.addEventListener('error', () => {
269
+ clearInterval(interval);
270
+ });
271
+ }
272
+
273
+ function initializeImageHandlers() {
274
+ document.querySelectorAll('img[data-remote]').forEach(img => {
275
+ if (img instanceof HTMLImageElement) {
276
+ if (img.complete) {
277
+ handleImageLoad(img);
278
+ } else {
279
+ img.addEventListener('load', () => handleImageLoad(img));
280
+ img.addEventListener('error', () => handleImageError(img));
281
+ if (img.getAttribute('data-remote') === 'true') {
282
+ simulateLoadingProgress(img);
283
+ }
284
+ }
285
+ }
286
+ });
287
+ }
288
+
289
+ document.addEventListener('astro:page-load', initializeImageHandlers);
290
+ initializeImageHandlers();
291
+ </script>
@@ -0,0 +1,131 @@
1
+ ---
2
+ /**
3
+ * @component Link
4
+ *
5
+ * @description
6
+ * Link 组件是一个增强的链接组件,提供了丰富的样式变体和动画效果。
7
+ * 它可以用于导航、按钮、行动号召等多种场景。
8
+ *
9
+ * @design
10
+ * 设计理念:
11
+ * 1. 灵活多变 - 提供多种样式变体,适应不同场景
12
+ * 2. 视觉反馈 - 通过悬停效果提供用户交互反馈
13
+ * 3. 一致性 - 保持与整体设计系统的一致性
14
+ * 4. 可访问性 - 确保链接可被键盘导航和屏幕阅读器识别
15
+ *
16
+ * @usage
17
+ * 基本用法:
18
+ * ```astro
19
+ * <Link href="/about">关于我们</Link>
20
+ * ```
21
+ *
22
+ * 外部链接:
23
+ * ```astro
24
+ * <Link href="https://example.com" external>访问外部网站</Link>
25
+ * ```
26
+ *
27
+ * 样式变体:
28
+ * ```astro
29
+ * <Link href="/signup" variant="primary">注册</Link>
30
+ * <Link href="/learn-more" variant="secondary">了解更多</Link>
31
+ * <Link href="/docs" variant="text">查看文档</Link>
32
+ * <Link href="/get-started" variant="cta">立即开始</Link>
33
+ * <Link href="/preview" variant="ghost">预览</Link>
34
+ * ```
35
+ *
36
+ * 块级显示:
37
+ * ```astro
38
+ * <Link href="/contact" block>独占一行的链接</Link>
39
+ * <p>这是一段文字,其中包含一个<Link href="/inline">内联链接</Link>。</p>
40
+ * ```
41
+ *
42
+ * 动画效果:
43
+ * ```astro
44
+ * <Link href="/contact" animation="hover-lift">联系我们</Link>
45
+ * <Link href="/features" animation="hover-glow">功能特性</Link>
46
+ * <Link href="/pricing" animation="hover-scale">查看价格</Link>
47
+ * ```
48
+ *
49
+ * 尺寸变体:
50
+ * ```astro
51
+ * <Link href="/small" size="sm">小型链接</Link>
52
+ * <Link href="/medium" size="md">中型链接</Link>
53
+ * <Link href="/large" size="lg">大型链接</Link>
54
+ * ```
55
+ */
56
+
57
+ import "../../app.css";
58
+
59
+ import type { HTMLAttributes } from 'astro/types';
60
+
61
+ // 定义链接尺寸类型
62
+ type LinkSize = 'sm' | 'md' | 'lg';
63
+
64
+ // 定义链接变体类型
65
+ type LinkVariant = 'default' | 'primary' | 'secondary' | 'text' | 'cta' | 'ghost';
66
+
67
+ // 定义链接动画类型
68
+ type LinkAnimation = 'none' | 'hover-lift' | 'hover-glow' | 'hover-scale';
69
+
70
+ interface Props extends HTMLAttributes<'a'> {
71
+ href: string;
72
+ external?: boolean;
73
+ block?: boolean;
74
+ class?: string;
75
+ 'class:list'?: any;
76
+ variant?: LinkVariant;
77
+ animation?: LinkAnimation;
78
+ size?: LinkSize;
79
+ }
80
+
81
+ const {
82
+ href,
83
+ external = false,
84
+ block = false,
85
+ variant = 'default',
86
+ animation = 'none',
87
+ size = 'md',
88
+ class: className = '',
89
+ 'class:list': classList,
90
+ ...rest
91
+ } = Astro.props;
92
+
93
+ // 构建类名
94
+ const classes = [
95
+ // 基础链接样式
96
+ 'items-center cursor-pointer no-underline transition-all duration-200',
97
+
98
+ // 显示方式
99
+ block ? 'flex w-full' : 'inline-flex',
100
+
101
+ // 变体样式
102
+ variant === 'primary' && 'text-primary hover:text-primary-focus',
103
+ variant === 'secondary' && 'text-secondary hover:text-secondary-focus',
104
+ variant === 'text' && 'text-neutral hover:text-neutral-focus',
105
+ variant === 'cta' && 'text-accent hover:text-accent-focus font-medium',
106
+ variant === 'ghost' && 'text-base-content hover:text-base-content/80',
107
+ variant === 'default' && 'text-base-content hover:text-base-content/90',
108
+
109
+ // 尺寸样式
110
+ size === 'sm' && 'text-sm',
111
+ size === 'md' && 'text-base',
112
+ size === 'lg' && 'text-lg',
113
+
114
+ // 动画效果
115
+ animation === 'hover-lift' && 'hover:-translate-y-0.5 transition-transform',
116
+ animation === 'hover-glow' && 'hover:brightness-125 transition-[filter]',
117
+ animation === 'hover-scale' && 'hover:scale-105 transition-transform',
118
+
119
+ // 自定义类名
120
+ className
121
+ ];
122
+ ---
123
+
124
+ <a
125
+ href={href}
126
+ class:list={[classes, classList]}
127
+ {...external ? { target: '_blank', rel: 'noopener noreferrer' } : {}}
128
+ {...rest}
129
+ >
130
+ <slot />
131
+ </a>
@@ -0,0 +1,53 @@
1
+ # 基础组件 (Base Components)
2
+
3
+ 这个目录包含了最基础和常用的UI组件,它们是构建用户界面的基础构建块。
4
+
5
+ ## 设计原则
6
+
7
+ 1. **简单性**:每个组件都应该专注于单一功能
8
+ 2. **可复用性**:组件应该足够通用,可以在各种场景下使用
9
+ 3. **可定制性**:提供足够的props来满足不同的使用需求
10
+
11
+ ## 包含的组件
12
+
13
+ - `Root.astro`: 根组件,负责全局样式和配置的管理
14
+ - `Button.astro`: 按钮组件,用于触发操作
15
+ - `Link.astro`: 链接组件,用于页面导航
16
+ - `Image.astro`: 图片组件,提供图片加载优化
17
+ - `ThemeItem.astro`: 主题项组件,用于主题切换
18
+ - `Alert.astro`: 提示组件,用于显示重要信息
19
+
20
+ ## 使用指南
21
+
22
+ ### Root 组件
23
+
24
+ Root 组件是所有其他组件的容器,负责:
25
+
26
+ - 导入全局样式
27
+ - 提供主题支持
28
+ - 设置语言环境
29
+ - 管理过渡动画
30
+
31
+ 必须将其他组件包裹在 Root 组件内使用:
32
+
33
+ ```astro
34
+ ---
35
+ import { Root, Button, Alert } from '@coffic/cosy-ui';
36
+ ---
37
+
38
+ <Root theme="light" lang="zh">
39
+ <Button variant="primary">点击我</Button>
40
+ <Alert type="info">这是一条信息</Alert>
41
+ </Root>
42
+ ```
43
+
44
+ ### 其他基础组件
45
+
46
+ 所有基础组件都需要在 Root 组件内使用:
47
+
48
+ ```astro
49
+ <Root>
50
+ <Button variant="primary" size="md">点击我</Button>
51
+ <Alert type="info">这是一条信息</Alert>
52
+ </Root>
53
+ ```
@@ -0,0 +1,6 @@
1
+
2
+ export { default as Button } from './Button.astro';
3
+ export { default as Link } from './Link.astro';
4
+ export { default as Image } from './Image.astro';
5
+ export { default as ThemeItem } from './ThemeItem.astro';
6
+ export { default as Alert } from './Alert.astro';
@@ -0,0 +1,103 @@
1
+ ---
2
+ /**
3
+ * @component Container
4
+ *
5
+ * @description
6
+ * Container 组件是一个基础的布局容器,用于限制内容宽度并居中显示。
7
+ * 它提供了多种尺寸和内边距选项,适用于各种布局需求。
8
+ *
9
+ * @design
10
+ * 设计理念:
11
+ * 1. 内容约束 - 限制内容宽度,提高可读性和视觉美感
12
+ * 2. 响应式设计 - 在不同屏幕尺寸下自动调整内边距
13
+ * 3. 灵活配置 - 支持多种尺寸和内边距选项
14
+ * 4. 简单易用 - 提供直观的API,易于集成到各种页面布局中
15
+ *
16
+ * @usage
17
+ * 基本用法:
18
+ * ```astro
19
+ * <Container>
20
+ * <p>内容将被限制在一个合理的宽度内并居中显示</p>
21
+ * </Container>
22
+ * ```
23
+ *
24
+ * 自定义尺寸和内边距:
25
+ * ```astro
26
+ * <Container size="sm" padding="lg">
27
+ * <p>小尺寸容器,大内边距</p>
28
+ * </Container>
29
+ * ```
30
+ *
31
+ * 全宽容器:
32
+ * ```astro
33
+ * <Container size="full" padding="none">
34
+ * <p>全宽容器,无内边距</p>
35
+ * </Container>
36
+ * ```
37
+ *
38
+ * 不居中的容器:
39
+ * ```astro
40
+ * <Container centered={false}>
41
+ * <p>不居中的容器,靠左对齐</p>
42
+ * </Container>
43
+ * ```
44
+ */
45
+
46
+ import type { HTMLAttributes } from 'astro/types';
47
+
48
+ // 导入样式
49
+ import '../../app.css';
50
+
51
+ interface Props extends HTMLAttributes<'div'> {
52
+ /**
53
+ * 容器尺寸
54
+ * @default "md"
55
+ */
56
+ size?: 'xs' | 'sm' | 'md' | 'lg' | 'xl' | 'full';
57
+
58
+ /**
59
+ * 内边距大小
60
+ * @default "md"
61
+ */
62
+ padding?: 'none' | 'sm' | 'md' | 'lg' | 'xl';
63
+
64
+ /**
65
+ * 是否居中显示
66
+ * @default true
67
+ */
68
+ centered?: boolean;
69
+
70
+ /**
71
+ * 自定义类名
72
+ */
73
+ class?: string;
74
+
75
+ /**
76
+ * 类名列表
77
+ */
78
+ 'class:list'?: any;
79
+ }
80
+
81
+ const {
82
+ size = 'md',
83
+ padding = 'md',
84
+ centered = true,
85
+ class: className = '',
86
+ 'class:list': classList,
87
+ ...rest
88
+ } = Astro.props;
89
+
90
+ // 构建CSS类名
91
+ const containerClasses = [
92
+ 'container',
93
+ `container-${size}`,
94
+ `container-padding-${padding}`,
95
+ centered ? 'container-centered' : '',
96
+ className
97
+ ];
98
+ ---
99
+
100
+ <div class:list={[containerClasses, classList]} {...rest}>
101
+ <slot />
102
+ </div>
103
+