@coffic/cosy-ui 0.3.39 → 0.3.45

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.
@@ -1,29 +1,29 @@
1
1
  ---
2
2
  /**
3
3
  * @component Text
4
- *
4
+ *
5
5
  * @description
6
6
  * Text 组件用于创建各种文本元素,提供一致的排版样式和灵活的定制选项。
7
- *
7
+ *
8
8
  * @design
9
9
  * 设计理念:
10
10
  * 1. 一致性 - 确保整个应用中文本样式的一致性
11
11
  * 2. 可读性 - 优化文本的可读性和舒适度
12
12
  * 3. 可定制性 - 支持多种配置选项,适应不同场景需求
13
13
  * 4. 无障碍性 - 遵循语义化HTML标准,确保屏幕阅读器可以正确解析内容
14
- *
14
+ *
15
15
  * 视觉特点:
16
16
  * - 不同的字体大小和行高
17
17
  * - 可选的字体粗细和样式
18
18
  * - 可定制的颜色和对齐方式
19
19
  * - 支持截断和省略号
20
- *
20
+ *
21
21
  * @usage
22
22
  * 基本用法:
23
23
  * ```astro
24
24
  * <Text>这是一段普通文本</Text>
25
25
  * ```
26
- *
26
+ *
27
27
  * 不同大小:
28
28
  * ```astro
29
29
  * <Text size="xs">超小文本</Text>
@@ -32,7 +32,7 @@
32
32
  * <Text size="lg">大文本</Text>
33
33
  * <Text size="xl">超大文本</Text>
34
34
  * ```
35
- *
35
+ *
36
36
  * 不同颜色:
37
37
  * ```astro
38
38
  * <Text color="primary">主要颜色文本</Text>
@@ -40,7 +40,7 @@
40
40
  * <Text color="accent">强调色文本</Text>
41
41
  * <Text color="muted">柔和色文本</Text>
42
42
  * ```
43
- *
43
+ *
44
44
  * 字体粗细:
45
45
  * ```astro
46
46
  * <Text weight="light">细体文本</Text>
@@ -49,7 +49,7 @@
49
49
  * <Text weight="semibold">半粗体文本</Text>
50
50
  * <Text weight="bold">粗体文本</Text>
51
51
  * ```
52
- *
52
+ *
53
53
  * 文本对齐:
54
54
  * ```astro
55
55
  * <Text align="left">左对齐文本</Text>
@@ -57,25 +57,25 @@
57
57
  * <Text align="right">右对齐文本</Text>
58
58
  * <Text align="justify">两端对齐文本</Text>
59
59
  * ```
60
- *
60
+ *
61
61
  * 文本截断:
62
62
  * ```astro
63
63
  * <Text truncate>这是一段很长的文本,将会被截断并显示省略号...</Text>
64
64
  * ```
65
- *
65
+ *
66
66
  * 组合使用:
67
67
  * ```astro
68
- * <Text
69
- * size="lg"
70
- * color="primary"
71
- * weight="bold"
68
+ * <Text
69
+ * size="lg"
70
+ * color="primary"
71
+ * weight="bold"
72
72
  * align="center"
73
73
  * class="my-4"
74
74
  * >
75
75
  * 这是一段重要的提示文本
76
76
  * </Text>
77
77
  * ```
78
- *
78
+ *
79
79
  * @props
80
80
  * @prop {string} [as='p'] - 要渲染的HTML元素,如 'p', 'span', 'div' 等
81
81
  * @prop {'xs'|'sm'|'md'|'lg'|'xl'} [size='md'] - 文本大小
@@ -86,102 +86,104 @@
86
86
  * @prop {boolean} [underline=false] - 是否添加下划线
87
87
  * @prop {boolean} [truncate=false] - 是否截断文本并显示省略号
88
88
  * @prop {string} [class] - 自定义 CSS 类名
89
- *
89
+ *
90
90
  * @slots
91
91
  * @slot default - 文本内容
92
- *
92
+ *
93
93
  * @accessibility
94
94
  * - 使用语义化的HTML元素
95
95
  * - 确保文本颜色与背景色的对比度符合WCAG标准
96
96
  */
97
97
 
98
+ import '../../app.css';
99
+
98
100
  interface Props {
99
- as?: string;
100
- size?: 'xs' | 'sm' | 'md' | 'lg' | 'xl';
101
- weight?: 'light' | 'normal' | 'medium' | 'semibold' | 'bold';
102
- color?: 'default' | 'primary' | 'secondary' | 'accent' | 'muted';
103
- align?: 'left' | 'center' | 'right' | 'justify';
104
- italic?: boolean;
105
- underline?: boolean;
106
- truncate?: boolean;
107
- class?: string;
101
+ as?: string;
102
+ size?: 'xs' | 'sm' | 'md' | 'lg' | 'xl';
103
+ weight?: 'light' | 'normal' | 'medium' | 'semibold' | 'bold';
104
+ color?: 'default' | 'primary' | 'secondary' | 'accent' | 'muted';
105
+ align?: 'left' | 'center' | 'right' | 'justify';
106
+ italic?: boolean;
107
+ underline?: boolean;
108
+ truncate?: boolean;
109
+ class?: string;
108
110
  }
109
111
 
110
112
  const {
111
- as: Element = 'p',
112
- size = 'md',
113
- weight = 'normal',
114
- color = 'default',
115
- align = 'left',
116
- italic = false,
117
- underline = false,
118
- truncate = false,
119
- class: className = '',
113
+ as: Element = 'p',
114
+ size = 'md',
115
+ weight = 'normal',
116
+ color = 'default',
117
+ align = 'left',
118
+ italic = false,
119
+ underline = false,
120
+ truncate = false,
121
+ class: className = '',
120
122
  } = Astro.props;
121
123
 
122
124
  // 根据大小设置样式
123
125
  const sizeClasses = {
124
- xs: 'text-xs',
125
- sm: 'text-sm',
126
- md: 'text-base',
127
- lg: 'text-lg',
128
- xl: 'text-xl',
126
+ xs: 'cosy:text-xs',
127
+ sm: 'cosy:text-sm',
128
+ md: 'cosy:text-base',
129
+ lg: 'cosy:text-lg',
130
+ xl: 'cosy:text-xl',
129
131
  };
130
132
  const sizeClass = sizeClasses[size as keyof typeof sizeClasses];
131
133
 
132
134
  // 根据粗细设置样式
133
135
  const weightClasses = {
134
- light: 'font-light',
135
- normal: 'font-normal',
136
- medium: 'font-medium',
137
- semibold: 'font-semibold',
138
- bold: 'font-bold',
136
+ light: 'cosy:font-light',
137
+ normal: 'cosy:font-normal',
138
+ medium: 'cosy:font-medium',
139
+ semibold: 'cosy:font-semibold',
140
+ bold: 'cosy:font-bold',
139
141
  };
140
142
  const weightClass = weightClasses[weight as keyof typeof weightClasses];
141
143
 
142
144
  // 根据颜色设置样式
143
145
  const colorClasses = {
144
- default: 'text-gray-900 dark:text-gray-100',
145
- primary: 'text-primary-600 dark:text-primary-400',
146
- secondary: 'text-secondary-600 dark:text-secondary-400',
147
- accent: 'text-accent-600 dark:text-accent-400',
148
- muted: 'text-gray-600 dark:text-gray-400',
146
+ default: 'cosy:text-gray-900 cosy:dark:text-gray-100',
147
+ primary: 'cosy:text-primary-600 cosy:dark:text-primary-400',
148
+ secondary: 'cosy:text-secondary-600 cosy:dark:text-secondary-400',
149
+ accent: 'cosy:text-accent-600 cosy:dark:text-accent-400',
150
+ muted: 'cosy:text-gray-600 cosy:dark:text-gray-400',
149
151
  };
150
152
  const colorClass = colorClasses[color as keyof typeof colorClasses];
151
153
 
152
154
  // 根据对齐方式设置样式
153
155
  const alignClasses = {
154
- left: 'text-left',
155
- center: 'text-center',
156
- right: 'text-right',
157
- justify: 'text-justify',
156
+ left: 'cosy:text-left',
157
+ center: 'cosy:text-center',
158
+ right: 'cosy:text-right',
159
+ justify: 'cosy:text-justify',
158
160
  };
159
161
  const alignClass = alignClasses[align as keyof typeof alignClasses];
160
162
 
161
163
  // 其他样式
162
- const italicClass = italic ? 'italic' : '';
163
- const underlineClass = underline ? 'underline' : '';
164
- const truncateClass = truncate ? 'truncate' : '';
164
+ const italicClass = italic ? 'cosy:italic' : '';
165
+ const underlineClass = underline ? 'cosy:underline' : '';
166
+ const truncateClass = truncate ? 'cosy:truncate' : '';
165
167
 
166
168
  // 组合所有类名
167
169
  const combinedClass = `text ${sizeClass} ${weightClass} ${colorClass} ${alignClass} ${italicClass} ${underlineClass} ${truncateClass} ${className}`;
168
170
  ---
169
171
 
170
172
  <Element class={combinedClass}>
171
- <slot />
173
+ <slot />
172
174
  </Element>
173
175
 
174
176
  <style>
175
- .text {
176
- margin-bottom: 1em;
177
- line-height: 1.5;
178
- }
179
-
180
- /* 确保截断文本正常工作 */
181
- .truncate {
182
- white-space: nowrap;
183
- overflow: hidden;
184
- text-overflow: ellipsis;
185
- max-width: 100%;
186
- }
187
- </style>
177
+ .text {
178
+ margin-bottom: 1em;
179
+ line-height: 1.5;
180
+ }
181
+
182
+ /* 确保截断文本正常工作 */
183
+ .truncate {
184
+ white-space: nowrap;
185
+ overflow: hidden;
186
+ text-overflow: ellipsis;
187
+ max-width: 100%;
188
+ }
189
+ </style>
@@ -3,47 +3,105 @@ interface ThemeManager {
3
3
  handleThemeClick: (this: HTMLElement) => void;
4
4
  initialize: () => void;
5
5
  setTheme: (theme: string) => void;
6
+ detectSystemTheme: () => string;
6
7
  }
7
8
 
9
+ /**
10
+ * 创建主题管理器
11
+ *
12
+ * 提供主题切换、主题持久化存储和系统主题检测等功能
13
+ *
14
+ * @returns ThemeManager 主题管理器对象
15
+ */
8
16
  export function createThemeManager(): ThemeManager {
9
- const getThemeItems = () => document.querySelectorAll<HTMLElement>('[data-set-theme]');
17
+ const getThemeItems = () => document.querySelectorAll<HTMLElement>('[data-theme]');
10
18
 
11
19
  const updateActiveTheme = (currentTheme: string) => {
12
20
  const themeItems = getThemeItems();
13
21
  themeItems.forEach((item) => {
14
- const themeId = item.getAttribute('data-set-theme');
22
+ const themeId = item.getAttribute('data-theme');
15
23
  const isActive = themeId === currentTheme;
16
- item.classList.toggle('bg-primary', isActive);
17
- item.classList.toggle('text-primary-content', isActive);
24
+
25
+ // 设置元素的 data-active 属性
26
+ item.setAttribute('data-active', String(isActive));
27
+
28
+ // 仅对于旧式主题按钮(data-set-theme 属性),保留旧的类切换行为
29
+ if (item.hasAttribute('data-set-theme')) {
30
+ item.classList.toggle('cosy:bg-primary', isActive);
31
+ item.classList.toggle('cosy:text-primary-content', isActive);
32
+ }
18
33
  });
19
34
  };
20
35
 
21
36
  function handleThemeClick(this: HTMLElement) {
22
- const theme = this.getAttribute('data-set-theme');
23
- document.documentElement.setAttribute('data-theme', theme ?? 'default');
24
- localStorage.setItem('theme', theme ?? 'default');
25
- updateActiveTheme(theme ?? 'default');
37
+ const theme = this.getAttribute('data-set-theme') || this.getAttribute('data-theme');
38
+ if (theme) {
39
+ setTheme(theme);
40
+ }
26
41
  }
27
42
 
43
+ /**
44
+ * 设置主题
45
+ *
46
+ * @param theme 主题ID
47
+ */
28
48
  const setTheme = (theme: string) => {
29
49
  document.documentElement.setAttribute('data-theme', theme);
30
50
  localStorage.setItem('theme', theme);
31
51
  updateActiveTheme(theme);
32
52
  };
33
53
 
54
+ /**
55
+ * 检测系统主题偏好(亮色/暗色)
56
+ *
57
+ * @returns 'dark' 或 'light'
58
+ */
59
+ const detectSystemTheme = (): string => {
60
+ return window.matchMedia('(prefers-color-scheme: dark)').matches ? 'dark' : 'light';
61
+ };
62
+
63
+ /**
64
+ * 初始化主题管理器
65
+ *
66
+ * 从本地存储中获取主题设置,如果没有则尝试使用系统主题,最后使用默认主题
67
+ */
34
68
  const initialize = () => {
35
- const themeItems = getThemeItems();
69
+ // 从本地存储中获取主题
70
+ let savedTheme = localStorage.getItem('theme');
71
+
72
+ // 如果没有保存的主题,则尝试使用系统主题
73
+ if (!savedTheme) {
74
+ const systemTheme = detectSystemTheme();
75
+ if (systemTheme === 'dark') {
76
+ savedTheme = 'dark';
77
+ } else {
78
+ savedTheme = 'default'; // 默认使用默认主题
79
+ }
80
+ }
81
+
82
+ // 设置主题
83
+ document.documentElement.setAttribute('data-theme', savedTheme);
84
+ updateActiveTheme(savedTheme);
85
+
86
+ // 添加主题切换事件监听器
87
+ // 支持新旧两种类型的主题切换按钮
88
+ const themeItems = [
89
+ ...Array.from(document.querySelectorAll<HTMLElement>('[data-set-theme]')),
90
+ ...Array.from(document.querySelectorAll<HTMLElement>('.cosy\\:theme-item')),
91
+ ];
36
92
 
37
- // 移除旧的事件监听器并添加新的
38
93
  themeItems.forEach((item) => {
39
94
  item.removeEventListener('click', handleThemeClick);
40
95
  item.addEventListener('click', handleThemeClick);
41
96
  });
42
97
 
43
- // 从本地存储中获取主题并更新激活状态
44
- const savedTheme = localStorage.getItem('theme') || 'default';
45
- document.documentElement.setAttribute('data-theme', savedTheme);
46
- updateActiveTheme(savedTheme);
98
+ // 监听系统主题变化
99
+ window.matchMedia('(prefers-color-scheme: dark)').addEventListener('change', (e) => {
100
+ // 只有当用户没有手动设置过主题时,才跟随系统主题变化
101
+ if (!localStorage.getItem('theme')) {
102
+ setTheme(e.matches ? 'dark' : 'default');
103
+ }
104
+ });
47
105
  };
48
106
 
49
107
  return {
@@ -51,5 +109,6 @@ export function createThemeManager(): ThemeManager {
51
109
  handleThemeClick,
52
110
  initialize,
53
111
  setTheme,
112
+ detectSystemTheme,
54
113
  };
55
- }
114
+ }
package/package.json CHANGED
@@ -1,72 +1,77 @@
1
1
  {
2
- "name": "@coffic/cosy-ui",
3
- "version": "0.3.39",
4
- "description": "An astro component library",
5
- "author": {
6
- "name": "nookery",
7
- "url": "https://github.com/nookery"
8
- },
9
- "repository": {
10
- "url": "https://github.com/CofficLab/cosy-ui"
11
- },
12
- "license": "MIT",
13
- "keywords": [
14
- "astro-integration",
15
- "astro-component",
16
- "withastro",
17
- "astro",
18
- "cosy-ui"
19
- ],
20
- "homepage": "https://github.com/CofficLab/cosy-ui",
21
- "publishConfig": {
22
- "access": "public"
23
- },
24
- "sideEffects": false,
25
- "main": "./dist/index.js",
26
- "exports": {
27
- ".": "./dist/index.js"
28
- },
29
- "files": [
30
- "dist",
31
- "index.ts"
32
- ],
33
- "scripts": {
34
- "build": "vite build && tsx scripts/post-build.ts"
35
- },
36
- "type": "module",
37
- "peerDependencies": {
38
- "astro": "^5.1.3"
39
- },
40
- "dependencies": {
41
- "astro-integration-kit": "^0.18.0",
42
- "fs-extra": "^11.3.0"
43
- },
44
- "devDependencies": {
45
- "@astrojs/check": "^0.9.4",
46
- "@astrojs/mdx": "^4.2.0",
47
- "@astrojs/ts-plugin": "^1.10.4",
48
- "@tailwindcss/typography": "^0.5.16",
49
- "@tailwindcss/vite": "^4.0.14",
50
- "@types/chai": "^5.2.0",
51
- "@types/eslint": "^9.6.1",
52
- "@types/fs-extra": "^11.0.4",
53
- "@types/mocha": "^10.0.10",
54
- "@types/node": "^22.13.10",
55
- "@types/react": "^19.0.10",
56
- "@typescript-eslint/parser": "^8.26.1",
57
- "astro": "^5.5.2",
58
- "chai": "^4.5.0",
59
- "daisyui": "^5.0.4",
60
- "eslint": "^8.57.1",
61
- "eslint-plugin-astro": "^1.3.1",
62
- "mocha": "^10.8.2",
63
- "prettier": "^3.5.3",
64
- "prettier-plugin-astro": "^0.14.1",
65
- "rollup-plugin-copy": "^3.5.0",
66
- "sharp": "^0.33.2",
67
- "tailwindcss": "^4.0.14",
68
- "tsx": "^4.19.3",
69
- "typescript": "^5.8.2",
70
- "vite": "^6.2.2"
71
- }
2
+ "name": "@coffic/cosy-ui",
3
+ "version": "0.3.45",
4
+ "description": "An astro component library",
5
+ "author": {
6
+ "name": "nookery",
7
+ "url": "https://github.com/nookery"
8
+ },
9
+ "repository": {
10
+ "url": "https://github.com/CofficLab/cosy-ui"
11
+ },
12
+ "license": "MIT",
13
+ "keywords": [
14
+ "astro-integration",
15
+ "astro-component",
16
+ "withastro",
17
+ "astro",
18
+ "cosy-ui"
19
+ ],
20
+ "homepage": "https://github.com/CofficLab/cosy-ui",
21
+ "publishConfig": {
22
+ "access": "public"
23
+ },
24
+ "sideEffects": false,
25
+ "main": "./dist/index.js",
26
+ "exports": {
27
+ ".": "./dist/index.js"
28
+ },
29
+ "files": [
30
+ "dist",
31
+ "index.ts"
32
+ ],
33
+ "scripts": {
34
+ "dev": "astro dev --host 0.0.0.0 --port 5678",
35
+ "preview:docs": "astro preview --host 0.0.0.0 --port 4330 --outDir dist-docs",
36
+ "build": "vite build && tsx scripts/post-build.ts",
37
+ "build:docs": "astro build"
38
+ },
39
+ "type": "module",
40
+ "peerDependencies": {
41
+ "astro": "^5.1.3"
42
+ },
43
+ "dependencies": {
44
+ "astro-integration-kit": "^0.18.0",
45
+ "fs-extra": "^11.3.0"
46
+ },
47
+ "devDependencies": {
48
+ "@astrojs/check": "^0.9.4",
49
+ "@astrojs/mdx": "^4.2.0",
50
+ "@astrojs/ts-plugin": "^1.10.4",
51
+ "@astrojs/vue": "^5.0.8",
52
+ "@tailwindcss/typography": "^0.5.16",
53
+ "@tailwindcss/vite": "^4.1.4",
54
+ "@types/chai": "^5.2.0",
55
+ "@types/eslint": "^9.6.1",
56
+ "@types/fs-extra": "^11.0.4",
57
+ "@types/mocha": "^10.0.10",
58
+ "@types/node": "^22.13.10",
59
+ "@types/react": "^19.0.10",
60
+ "@typescript-eslint/parser": "^8.26.1",
61
+ "astro": "^5.5.2",
62
+ "chai": "^4.5.0",
63
+ "daisyui": "^5.0.4",
64
+ "eslint": "^8.57.1",
65
+ "eslint-plugin-astro": "^1.3.1",
66
+ "mocha": "^10.8.2",
67
+ "prettier": "^3.5.3",
68
+ "prettier-plugin-astro": "^0.14.1",
69
+ "rollup-plugin-copy": "^3.5.0",
70
+ "sharp": "^0.33.2",
71
+ "tailwindcss": "^4.1.4",
72
+ "tsx": "^4.19.3",
73
+ "typescript": "^5.8.2",
74
+ "vite": "^6.2.2",
75
+ "vue": "^3.5.13"
76
+ }
72
77
  }