@dialpad/dialtone-css 8.78.0-next.1 → 8.78.0-next.3

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 (108) hide show
  1. package/README.md +0 -2
  2. package/lib/build/js/dialtone_migrate_flex_to_stack/examples-edge-cases.vue +26 -0
  3. package/lib/build/js/dialtone_migrate_flex_to_stack/index.mjs +56 -15
  4. package/lib/build/js/dialtone_migrate_tshirt_to_numeric/index.mjs +233 -0
  5. package/lib/build/js/dialtone_migrate_tshirt_to_numeric/test.mjs +336 -0
  6. package/lib/build/js/dialtone_migration_helper/configs/physical-to-logical.mjs +86 -0
  7. package/lib/build/js/dialtone_migration_helper/configs/size-to-layout.mjs +212 -0
  8. package/lib/build/js/dialtone_migration_helper/configs/space-to-spacing.mjs +48 -0
  9. package/lib/build/js/dialtone_migration_helper/configs/stack-gap-to-spacing.mjs +88 -0
  10. package/lib/build/js/dialtone_migration_helper/configs/utility-class-to-token-stops.mjs +135 -0
  11. package/lib/build/js/dialtone_migration_helper/tests/size-to-layout-test-examples.vue +275 -0
  12. package/lib/build/js/dialtone_migration_helper/tests/space-to-spacing-test-examples.vue +193 -0
  13. package/lib/build/less/components/avatar.less +8 -19
  14. package/lib/build/less/components/badge.less +22 -20
  15. package/lib/build/less/components/banner.less +5 -5
  16. package/lib/build/less/components/breadcrumbs.less +4 -4
  17. package/lib/build/less/components/button.less +39 -39
  18. package/lib/build/less/components/card.less +4 -4
  19. package/lib/build/less/components/chip.less +41 -51
  20. package/lib/build/less/components/codeblock.less +2 -2
  21. package/lib/build/less/components/collapsible.less +2 -2
  22. package/lib/build/less/components/combobox-multi-select.less +8 -8
  23. package/lib/build/less/components/combobox-with-popover.less +1 -1
  24. package/lib/build/less/components/combobox.less +5 -5
  25. package/lib/build/less/components/datepicker.less +6 -6
  26. package/lib/build/less/components/description-list.less +14 -3
  27. package/lib/build/less/components/dropdown.less +4 -4
  28. package/lib/build/less/components/emoji-picker.less +35 -35
  29. package/lib/build/less/components/empty-state.less +5 -5
  30. package/lib/build/less/components/filter-pill.less +5 -5
  31. package/lib/build/less/components/forms.less +10 -10
  32. package/lib/build/less/components/image-viewer.less +2 -2
  33. package/lib/build/less/components/input.less +17 -22
  34. package/lib/build/less/components/item-layout.less +8 -8
  35. package/lib/build/less/components/keyboard-shortcut.less +3 -3
  36. package/lib/build/less/components/link.less +5 -5
  37. package/lib/build/less/components/list-group.less +1 -1
  38. package/lib/build/less/components/list-item-group.less +1 -1
  39. package/lib/build/less/components/list-item.less +9 -9
  40. package/lib/build/less/components/modal.less +20 -20
  41. package/lib/build/less/components/notice.less +11 -11
  42. package/lib/build/less/components/pagination.less +5 -5
  43. package/lib/build/less/components/popover.less +5 -5
  44. package/lib/build/less/components/radio-checkbox.less +11 -10
  45. package/lib/build/less/components/rich-text-editor.less +13 -13
  46. package/lib/build/less/components/scrollbar.less +2 -2
  47. package/lib/build/less/components/segmented-control.less +6 -6
  48. package/lib/build/less/components/selects.less +18 -13
  49. package/lib/build/less/components/skeleton.less +4 -4
  50. package/lib/build/less/components/stack.less +24 -69
  51. package/lib/build/less/components/table.less +6 -7
  52. package/lib/build/less/components/tabs.less +24 -24
  53. package/lib/build/less/components/toast.less +16 -16
  54. package/lib/build/less/components/toggle.less +23 -23
  55. package/lib/build/less/components/tooltip.less +27 -27
  56. package/lib/build/less/dialtone-reset.less +3 -3
  57. package/lib/build/less/dialtone-transitions.less +4 -4
  58. package/lib/build/less/dialtone.less +2 -2
  59. package/lib/build/less/recipes/attachment_carousel.less +13 -13
  60. package/lib/build/less/recipes/callbar_button.less +1 -1
  61. package/lib/build/less/recipes/callbar_button_with_dropdown.less +7 -7
  62. package/lib/build/less/recipes/callbar_button_with_popover.less +8 -8
  63. package/lib/build/less/recipes/callbox.less +6 -6
  64. package/lib/build/less/recipes/contact_info.less +9 -9
  65. package/lib/build/less/recipes/editor.less +12 -12
  66. package/lib/build/less/recipes/emoji_row.less +8 -8
  67. package/lib/build/less/recipes/feed_item_pill.less +13 -13
  68. package/lib/build/less/recipes/feed_item_row.less +10 -10
  69. package/lib/build/less/recipes/grouped_chip.less +2 -2
  70. package/lib/build/less/recipes/ivr_node.less +13 -13
  71. package/lib/build/less/recipes/leftbar_row.less +23 -23
  72. package/lib/build/less/recipes/message_input.less +16 -16
  73. package/lib/build/less/recipes/settings_menu_button.less +10 -10
  74. package/lib/build/less/recipes/time_pill.less +1 -1
  75. package/lib/build/less/recipes/top_banner_info.less +8 -8
  76. package/lib/build/less/recipes/unread_pill.less +2 -2
  77. package/lib/build/less/themes/default.less +1 -1
  78. package/lib/build/less/utilities/backgrounds.less +3 -3
  79. package/lib/build/less/utilities/effects.less +20 -20
  80. package/lib/build/less/utilities/flex.less +11 -11
  81. package/lib/build/less/utilities/layout.less +4 -4
  82. package/lib/build/less/utilities/sizing.less +172 -0
  83. package/lib/build/less/utilities/spacing.less +49 -49
  84. package/lib/build/less/utilities/typography.less +2 -2
  85. package/lib/build/less/variables/sizes.less +8 -8
  86. package/lib/dist/dialtone-default-theme.css +5220 -1117
  87. package/lib/dist/dialtone-default-theme.min.css +1 -1
  88. package/lib/dist/dialtone-docs.json +1 -1
  89. package/lib/dist/dialtone.css +5203 -1117
  90. package/lib/dist/dialtone.min.css +1 -1
  91. package/lib/dist/js/dialtone_migrate_flex_to_stack/examples-edge-cases.vue +26 -0
  92. package/lib/dist/js/dialtone_migrate_flex_to_stack/index.mjs +56 -15
  93. package/lib/dist/js/dialtone_migrate_tshirt_to_numeric/index.mjs +233 -0
  94. package/lib/dist/js/dialtone_migrate_tshirt_to_numeric/test.mjs +336 -0
  95. package/lib/dist/js/dialtone_migration_helper/configs/physical-to-logical.mjs +86 -0
  96. package/lib/dist/js/dialtone_migration_helper/configs/size-to-layout.mjs +212 -0
  97. package/lib/dist/js/dialtone_migration_helper/configs/space-to-spacing.mjs +48 -0
  98. package/lib/dist/js/dialtone_migration_helper/configs/stack-gap-to-spacing.mjs +88 -0
  99. package/lib/dist/js/dialtone_migration_helper/configs/utility-class-to-token-stops.mjs +135 -0
  100. package/lib/dist/js/dialtone_migration_helper/tests/size-to-layout-test-examples.vue +275 -0
  101. package/lib/dist/js/dialtone_migration_helper/tests/space-to-spacing-test-examples.vue +193 -0
  102. package/lib/dist/tokens/tokens-base-dark.css +17 -0
  103. package/lib/dist/tokens/tokens-base-light.css +17 -0
  104. package/lib/dist/tokens/tokens-debug-base.css +17 -0
  105. package/lib/dist/tokens-docs.json +1 -1
  106. package/package.json +3 -3
  107. package/lib/build/js/dialtone_migration_helper/configs/space-to-size.mjs +0 -15
  108. package/lib/dist/js/dialtone_migration_helper/configs/space-to-size.mjs +0 -15
package/README.md CHANGED
@@ -30,14 +30,12 @@ import '@dialpad/dialtone-css';
30
30
  - Light mode
31
31
 
32
32
  ```html
33
-
34
33
  <body class="dialtone-theme-light">...</body>
35
34
  ```
36
35
 
37
36
  - Dark mode
38
37
 
39
38
  ```html
40
-
41
39
  <body class="dialtone-theme-dark">...</body>
42
40
  ```
43
41
 
@@ -292,6 +292,32 @@
292
292
 
293
293
  <!-- TEST 47: Empty element with flex - Should convert -->
294
294
  <div class="d-d-flex d-fd-column"></div>
295
+
296
+ <!-- ============================================ -->
297
+ <!-- NEW TESTS: NEW-FORMAT GAP UTILITIES (d-g-*) -->
298
+ <!-- ============================================ -->
299
+
300
+ <!-- TEST 48: New-format gap d-g-100 (8px) - Should convert to gap="100" -->
301
+ <div class="d-d-flex d-ai-center d-g-100">
302
+ <span>New gap format 8px</span>
303
+ </div>
304
+
305
+ <!-- TEST 49: New-format gap d-g-200 (16px) - Should convert to gap="200" -->
306
+ <div class="d-d-flex d-fd-row d-g-200">
307
+ <span>Item 1</span>
308
+ <span>Item 2</span>
309
+ </div>
310
+
311
+ <!-- TEST 50: New-format gap d-g-400 (32px) with other props - Should convert -->
312
+ <div class="d-d-flex d-fd-column d-ai-center d-jc-between d-g-400">
313
+ <span>Full props with new gap</span>
314
+ <span>Example</span>
315
+ </div>
316
+
317
+ <!-- TEST 51: New-format gap d-g-50 (4px) - Should convert to gap="50" -->
318
+ <div class="d-d-flex d-ai-center d-g-50">
319
+ <span>Small gap 4px</span>
320
+ </div>
295
321
  </template>
296
322
 
297
323
  <script setup>
@@ -142,23 +142,64 @@ const FLEX_TO_PROP = {
142
142
  'd-fd-row-reverse': { prop: 'direction', value: 'row-reverse' },
143
143
  'd-fd-column-reverse': { prop: 'direction', value: 'column-reverse' },
144
144
 
145
- // Gap mappings (d-g* → gap prop)
145
+ // Gap mappings (d-g* → gap prop) — old pixel-based utilities
146
146
  'd-g0': { prop: 'gap', value: '0' },
147
- 'd-g8': { prop: 'gap', value: '400' },
148
- 'd-g16': { prop: 'gap', value: '500' },
149
- 'd-g24': { prop: 'gap', value: '550' },
150
- 'd-g32': { prop: 'gap', value: '600' },
151
- 'd-g48': { prop: 'gap', value: '650' },
152
- 'd-g64': { prop: 'gap', value: '700' },
153
-
154
- // Grid-gap mappings (d-gg* gap prop) - deprecated utilities, same as d-g*
147
+ 'd-g1': { prop: 'gap', value: '1' },
148
+ 'd-g2': { prop: 'gap', value: '25' },
149
+ 'd-g4': { prop: 'gap', value: '50' },
150
+ 'd-g6': { prop: 'gap', value: '75' },
151
+ 'd-g8': { prop: 'gap', value: '100' },
152
+ 'd-g10': { prop: 'gap', value: '125' },
153
+ 'd-g12': { prop: 'gap', value: '150' },
154
+ 'd-g14': { prop: 'gap', value: '175' },
155
+ 'd-g16': { prop: 'gap', value: '200' },
156
+ 'd-g20': { prop: 'gap', value: '250' },
157
+ 'd-g24': { prop: 'gap', value: '300' },
158
+ 'd-g32': { prop: 'gap', value: '400' },
159
+ 'd-g48': { prop: 'gap', value: '600' },
160
+ 'd-g64': { prop: 'gap', value: '800' },
161
+
162
+ // Gap mappings (d-g-* → gap prop) — new token-stop-based utilities
163
+ 'd-g-0': { prop: 'gap', value: '0' },
164
+ 'd-g-1': { prop: 'gap', value: '1' },
165
+ 'd-g-25': { prop: 'gap', value: '25' },
166
+ 'd-g-50': { prop: 'gap', value: '50' },
167
+ 'd-g-75': { prop: 'gap', value: '75' },
168
+ 'd-g-100': { prop: 'gap', value: '100' },
169
+ 'd-g-125': { prop: 'gap', value: '125' },
170
+ 'd-g-150': { prop: 'gap', value: '150' },
171
+ 'd-g-175': { prop: 'gap', value: '175' },
172
+ 'd-g-200': { prop: 'gap', value: '200' },
173
+ 'd-g-250': { prop: 'gap', value: '250' },
174
+ 'd-g-300': { prop: 'gap', value: '300' },
175
+ 'd-g-350': { prop: 'gap', value: '350' },
176
+ 'd-g-400': { prop: 'gap', value: '400' },
177
+ 'd-g-450': { prop: 'gap', value: '450' },
178
+ 'd-g-500': { prop: 'gap', value: '500' },
179
+ 'd-g-525': { prop: 'gap', value: '525' },
180
+ 'd-g-550': { prop: 'gap', value: '550' },
181
+ 'd-g-600': { prop: 'gap', value: '600' },
182
+ 'd-g-650': { prop: 'gap', value: '650' },
183
+ 'd-g-700': { prop: 'gap', value: '700' },
184
+ 'd-g-750': { prop: 'gap', value: '750' },
185
+ 'd-g-800': { prop: 'gap', value: '800' },
186
+
187
+ // Grid-gap mappings (d-gg* → gap prop) — deprecated utilities
155
188
  'd-gg0': { prop: 'gap', value: '0' },
156
- 'd-gg8': { prop: 'gap', value: '400' },
157
- 'd-gg16': { prop: 'gap', value: '500' },
158
- 'd-gg24': { prop: 'gap', value: '550' },
159
- 'd-gg32': { prop: 'gap', value: '600' },
160
- 'd-gg48': { prop: 'gap', value: '650' },
161
- 'd-gg64': { prop: 'gap', value: '700' },
189
+ 'd-gg1': { prop: 'gap', value: '1' },
190
+ 'd-gg2': { prop: 'gap', value: '25' },
191
+ 'd-gg4': { prop: 'gap', value: '50' },
192
+ 'd-gg6': { prop: 'gap', value: '75' },
193
+ 'd-gg8': { prop: 'gap', value: '100' },
194
+ 'd-gg10': { prop: 'gap', value: '125' },
195
+ 'd-gg12': { prop: 'gap', value: '150' },
196
+ 'd-gg14': { prop: 'gap', value: '175' },
197
+ 'd-gg16': { prop: 'gap', value: '200' },
198
+ 'd-gg20': { prop: 'gap', value: '250' },
199
+ 'd-gg24': { prop: 'gap', value: '300' },
200
+ 'd-gg32': { prop: 'gap', value: '400' },
201
+ 'd-gg48': { prop: 'gap', value: '600' },
202
+ 'd-gg64': { prop: 'gap', value: '800' },
162
203
  };
163
204
 
164
205
  // Classes to remove (redundant on dt-stack)
@@ -0,0 +1,233 @@
1
+ #!/usr/bin/env node
2
+
3
+ /**
4
+ * @fileoverview Migration script to convert t-shirt size props to numeric scale on Dialtone components.
5
+ *
6
+ * Transforms: size="sm" → :size="200", label-size="xs" → :label-size="100", speed="md" → :speed="300"
7
+ *
8
+ * Usage:
9
+ * npx dialtone-migrate-tshirt-to-numeric [options]
10
+ *
11
+ * Options:
12
+ * --cwd <path> Working directory (default: current directory)
13
+ * --dry-run Show changes without applying them
14
+ * --yes Apply all changes without prompting
15
+ * --help Show help
16
+ *
17
+ * Examples:
18
+ * npx dialtone-migrate-tshirt-to-numeric
19
+ * npx dialtone-migrate-tshirt-to-numeric --dry-run
20
+ * npx dialtone-migrate-tshirt-to-numeric --cwd ./src
21
+ */
22
+
23
+ import fs from 'fs/promises';
24
+ import { realpathSync } from 'node:fs';
25
+ import path from 'path';
26
+ import readline from 'readline';
27
+ import { fileURLToPath } from 'node:url';
28
+
29
+ // ---------------------------------------------------------------------------
30
+ // Mapping
31
+ // ---------------------------------------------------------------------------
32
+
33
+ const SIZE_MAP = {
34
+ xs: '100',
35
+ sm: '200',
36
+ md: '300',
37
+ lg: '400',
38
+ xl: '500',
39
+ '2xl': '600',
40
+ '3xl': '700',
41
+ };
42
+
43
+ const TSHIRT_VALUES = Object.keys(SIZE_MAP).join('|');
44
+
45
+ // Match any prop ending in size/Size/speed/Speed with a t-shirt value.
46
+ // In the replacer, check that the character before the match is NOT a colon (v-bind).
47
+ const PROP_REGEX = new RegExp(
48
+ `([\\w-]*(?:[Ss]ize|[Ss]peed))="(${TSHIRT_VALUES})"`,
49
+ 'g',
50
+ );
51
+
52
+ // Props that end in "size" but are NOT component scale sizes — exclude from migration
53
+ const EXCLUDED_PROPS = ['button-width-size', 'buttonWidthSize', 'background-size', 'backgroundSize', 'font-size', 'fontSize'];
54
+
55
+ // Only match on Dialtone component tags
56
+ // Use [\s\S] instead of [^>] to match across newlines in multiline tags
57
+ const DT_TAG_PATTERN = /<(dt-[\w-]+|Dt\w+)\b[\s\S]*?>/g;
58
+
59
+ // ---------------------------------------------------------------------------
60
+ // File finder
61
+ // ---------------------------------------------------------------------------
62
+
63
+ async function findFiles (dir, extensions, ignore = []) {
64
+ const results = [];
65
+
66
+ async function walk (currentDir) {
67
+ try {
68
+ const entries = await fs.readdir(currentDir, { withFileTypes: true });
69
+ for (const entry of entries) {
70
+ const fullPath = path.join(currentDir, entry.name);
71
+ if (ignore.some(ig => fullPath.includes(ig))) continue;
72
+ if (entry.isDirectory()) {
73
+ await walk(fullPath);
74
+ } else if (entry.isFile()) {
75
+ if (extensions.some(ext => entry.name.endsWith(ext))) {
76
+ results.push(fullPath);
77
+ }
78
+ }
79
+ }
80
+ } catch {
81
+ // Skip unreadable directories
82
+ }
83
+ }
84
+
85
+ await walk(dir);
86
+ return results;
87
+ }
88
+
89
+ // ---------------------------------------------------------------------------
90
+ // Transform logic
91
+ // ---------------------------------------------------------------------------
92
+
93
+ function transformContent (content) {
94
+ let transformed = content;
95
+ let count = 0;
96
+
97
+ // Replace t-shirt sizes only within Dialtone component tags
98
+ transformed = transformed.replace(DT_TAG_PATTERN, (tag) => {
99
+ PROP_REGEX.lastIndex = 0;
100
+ return tag.replace(PROP_REGEX, (match, propName, tshirt, offset, fullTag) => {
101
+ // Skip if preceded by ':' (already a v-bind expression)
102
+ if (offset > 0 && fullTag[offset - 1] === ':') return match;
103
+ // Skip excluded prop names (not component scale sizes)
104
+ if (EXCLUDED_PROPS.includes(propName)) return match;
105
+ if (SIZE_MAP[tshirt]) {
106
+ count++;
107
+ return `:${propName}="${SIZE_MAP[tshirt]}"`;
108
+ }
109
+ return match;
110
+ });
111
+ });
112
+
113
+ return { transformed, count };
114
+ }
115
+
116
+ export { transformContent, SIZE_MAP };
117
+
118
+ // ---------------------------------------------------------------------------
119
+ // CLI
120
+ // ---------------------------------------------------------------------------
121
+
122
+ function printHelp () {
123
+ console.log(`
124
+ Usage: npx dialtone-migrate-tshirt-to-numeric [options]
125
+
126
+ Converts t-shirt size props to numeric scale on Dialtone components.
127
+
128
+ size="sm" → :size="200"
129
+ label-size="xs" → :label-size="100"
130
+ speed="md" → :speed="300"
131
+
132
+ Options:
133
+ --cwd <path> Working directory (default: current directory)
134
+ --dry-run Show changes without applying them
135
+ --yes Apply all changes without prompting
136
+ --help Show help
137
+
138
+ Size mapping:
139
+ xs → 100 sm → 200 md → 300 lg → 400 xl → 500
140
+ 2xl → 600 3xl → 700
141
+ `);
142
+ }
143
+
144
+ async function prompt (question) {
145
+ const rl = readline.createInterface({ input: process.stdin, output: process.stdout });
146
+ return new Promise(resolve => {
147
+ rl.question(question, answer => {
148
+ rl.close();
149
+ resolve(answer.trim().toLowerCase());
150
+ });
151
+ });
152
+ }
153
+
154
+ // eslint-disable-next-line complexity
155
+ async function main () {
156
+ const args = process.argv.slice(2);
157
+
158
+ if (args.includes('--help')) {
159
+ printHelp();
160
+ process.exit(0);
161
+ }
162
+
163
+ const dryRun = args.includes('--dry-run');
164
+ const autoYes = args.includes('--yes');
165
+ const cwdIndex = args.indexOf('--cwd');
166
+ const cwd = cwdIndex !== -1 && args[cwdIndex + 1]
167
+ ? path.resolve(args[cwdIndex + 1])
168
+ : process.cwd();
169
+
170
+ console.log(`\nScanning ${cwd} for t-shirt size usage on Dialtone components...\n`);
171
+
172
+ const extensions = ['.vue', '.md', '.html', '.js', '.ts', '.jsx', '.tsx'];
173
+ const ignore = ['node_modules', 'dist', '.git', '.vuepress/public'];
174
+ const files = await findFiles(cwd, extensions, ignore);
175
+
176
+ const changes = [];
177
+
178
+ for (const file of files) {
179
+ const content = await fs.readFile(file, 'utf8');
180
+ const { transformed, count } = transformContent(content);
181
+ if (count > 0) {
182
+ changes.push({ file, content, transformed, count });
183
+ }
184
+ }
185
+
186
+ if (changes.length === 0) {
187
+ console.log('No t-shirt size usage found. Nothing to migrate.');
188
+ process.exit(0);
189
+ }
190
+
191
+ console.log(`Found ${changes.reduce((sum, c) => sum + c.count, 0)} t-shirt size references across ${changes.length} files:\n`);
192
+
193
+ for (const { file, count } of changes) {
194
+ const rel = path.relative(cwd, file);
195
+ console.log(` ${rel} (${count} change${count > 1 ? 's' : ''})`);
196
+ }
197
+
198
+ if (dryRun) {
199
+ console.log('\n--dry-run: No files were modified.\n');
200
+ process.exit(0);
201
+ }
202
+
203
+ if (!autoYes) {
204
+ const answer = await prompt('\nApply changes? (y/N) ');
205
+ if (answer !== 'y' && answer !== 'yes') {
206
+ console.log('Cancelled.');
207
+ process.exit(0);
208
+ }
209
+ }
210
+
211
+ for (const { file, transformed } of changes) {
212
+ await fs.writeFile(file, transformed, 'utf8');
213
+ }
214
+
215
+ console.log(`\nMigrated ${changes.reduce((sum, c) => sum + c.count, 0)} references across ${changes.length} files.\n`);
216
+ }
217
+
218
+ // Only run CLI when executed directly (not when imported for testing).
219
+ // Uses realpathSync to resolve symlinks from npx/npm bin shims.
220
+ const isDirectRun = (() => {
221
+ try {
222
+ return realpathSync(process.argv[1]) === fileURLToPath(import.meta.url);
223
+ } catch {
224
+ return false;
225
+ }
226
+ })();
227
+
228
+ if (isDirectRun) {
229
+ main().catch(err => {
230
+ console.error(err);
231
+ process.exit(1);
232
+ });
233
+ }