@muonic/muon 0.0.2-beta.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 (124) hide show
  1. package/.nycrc +17 -0
  2. package/.versionrc +3 -0
  3. package/CHANGELOG.md +389 -0
  4. package/components/card/index.js +1 -0
  5. package/components/card/src/card-component.js +43 -0
  6. package/components/card/src/card-styles.css +25 -0
  7. package/components/card/src/config-tokens.json +11 -0
  8. package/components/card/src/design-tokens.json +34 -0
  9. package/components/card/story.js +52 -0
  10. package/components/cta/index.js +1 -0
  11. package/components/cta/src/config-tokens.json +11 -0
  12. package/components/cta/src/cta-component.js +174 -0
  13. package/components/cta/src/cta-styles.css +105 -0
  14. package/components/cta/src/design-tokens.json +132 -0
  15. package/components/cta/story.js +99 -0
  16. package/components/detail/index.js +1 -0
  17. package/components/detail/src/config-tokens.json +11 -0
  18. package/components/detail/src/design-tokens.json +102 -0
  19. package/components/detail/src/detail-component.js +27 -0
  20. package/components/detail/src/detail-styles.css +83 -0
  21. package/components/detail/story.js +33 -0
  22. package/components/form/index.js +1 -0
  23. package/components/form/src/config-tokens.json +11 -0
  24. package/components/form/src/design-tokens.json +9 -0
  25. package/components/form/src/form-component.js +197 -0
  26. package/components/form/src/form-styles.css +10 -0
  27. package/components/form/story.js +71 -0
  28. package/components/icon/index.js +1 -0
  29. package/components/icon/src/config-tokens.json +31 -0
  30. package/components/icon/src/design-tokens.json +8 -0
  31. package/components/icon/src/icon-component.js +91 -0
  32. package/components/icon/src/icon-styles.css +26 -0
  33. package/components/icon/story.js +26 -0
  34. package/components/image/index.js +1 -0
  35. package/components/image/src/config-tokens.json +26 -0
  36. package/components/image/src/image-component.js +96 -0
  37. package/components/image/src/image-styles.css +71 -0
  38. package/components/image/story.js +31 -0
  39. package/components/inputter/index.js +1 -0
  40. package/components/inputter/src/config-tokens.json +14 -0
  41. package/components/inputter/src/design-tokens.json +308 -0
  42. package/components/inputter/src/inputter-component.js +227 -0
  43. package/components/inputter/src/inputter-styles-detail.css +59 -0
  44. package/components/inputter/src/inputter-styles.css +305 -0
  45. package/components/inputter/src/inputter-styles.slotted.css +64 -0
  46. package/components/inputter/story.js +243 -0
  47. package/css/accessibility.css +3 -0
  48. package/css/default.css +9 -0
  49. package/css/global.css +8 -0
  50. package/directives/image-loader-directive.js +116 -0
  51. package/directives/svg-loader-directive.js +94 -0
  52. package/index.js +52 -0
  53. package/mixins/card-mixin.js +27 -0
  54. package/mixins/detail-mixin.js +128 -0
  55. package/mixins/form-associate-mixin.js +36 -0
  56. package/mixins/form-element-mixin.js +378 -0
  57. package/mixins/image-holder-mixin.js +20 -0
  58. package/mixins/mask-mixin.js +159 -0
  59. package/mixins/validation-mixin.js +272 -0
  60. package/muon-element/index.js +97 -0
  61. package/package.json +72 -0
  62. package/rollup.config.mjs +30 -0
  63. package/scripts/build/storybook/index.mjs +11 -0
  64. package/scripts/build/storybook/run.mjs +47 -0
  65. package/scripts/rollup-plugins.mjs +116 -0
  66. package/scripts/serve/index.mjs +11 -0
  67. package/scripts/serve/run.mjs +27 -0
  68. package/scripts/style-dictionary.mjs +64 -0
  69. package/scripts/utils/config.mjs +30 -0
  70. package/scripts/utils/index.mjs +283 -0
  71. package/storybook/find-stories.js +36 -0
  72. package/storybook/server.config.mjs +19 -0
  73. package/storybook/stories.js +86 -0
  74. package/storybook/tokens/color.js +87 -0
  75. package/storybook/tokens/font.js +52 -0
  76. package/storybook/tokens/spacer.js +48 -0
  77. package/tests/README.md +3 -0
  78. package/tests/components/card/__snapshots__/card.test.snap.js +70 -0
  79. package/tests/components/card/card.test.js +81 -0
  80. package/tests/components/cta/__snapshots__/cta.test.snap.js +246 -0
  81. package/tests/components/cta/cta.test.js +212 -0
  82. package/tests/components/form/__snapshots__/form.test.snap.js +115 -0
  83. package/tests/components/form/form.test.js +336 -0
  84. package/tests/components/icon/__snapshots__/icon.test.snap.js +95 -0
  85. package/tests/components/icon/icon.test.js +197 -0
  86. package/tests/components/image/__snapshots__/image.test.snap.js +205 -0
  87. package/tests/components/image/image.test.js +314 -0
  88. package/tests/components/image/images/15.png +0 -0
  89. package/tests/components/image/images/150.png +0 -0
  90. package/tests/components/inputter/__snapshots__/inputter.test.snap.js +357 -0
  91. package/tests/components/inputter/inputter.test.js +427 -0
  92. package/tests/helpers/index.js +30 -0
  93. package/tests/mixins/__snapshots__/card.test.snap.js +35 -0
  94. package/tests/mixins/__snapshots__/detail.test.snap.js +237 -0
  95. package/tests/mixins/__snapshots__/form-element.test.snap.js +137 -0
  96. package/tests/mixins/__snapshots__/mask.test.snap.js +53 -0
  97. package/tests/mixins/__snapshots__/validation.test.snap.js +297 -0
  98. package/tests/mixins/card.test.js +63 -0
  99. package/tests/mixins/detail.test.js +223 -0
  100. package/tests/mixins/form-element.test.js +473 -0
  101. package/tests/mixins/mask.test.js +261 -0
  102. package/tests/mixins/muon-element.test.js +52 -0
  103. package/tests/mixins/validation.test.js +423 -0
  104. package/tests/runner/commands.mjs +19 -0
  105. package/tests/scripts/utils/card-component.js +26 -0
  106. package/tests/scripts/utils/muon.config.test.json +13 -0
  107. package/tests/scripts/utils/single.component.config.json +5 -0
  108. package/tests/scripts/utils/test-runner.mjs +1 -0
  109. package/tests/scripts/utils/utils-test.mjs +284 -0
  110. package/tests/utils/validation.functions.test.js +199 -0
  111. package/tokens/theme/color.json +482 -0
  112. package/tokens/theme/font.json +61 -0
  113. package/tokens/theme/size.json +27 -0
  114. package/tokens/theme/spacer.json +73 -0
  115. package/tokens/utils/formats/reference.js +17 -0
  116. package/tokens/utils/modular-scale.js +33 -0
  117. package/tokens/utils/templates/font-face.css.template +30 -0
  118. package/tokens/utils/transforms/color.js +27 -0
  119. package/tokens/utils/transforms/string.js +6 -0
  120. package/tokens/utils/validation.json +76 -0
  121. package/utils/scroll/index.js +31 -0
  122. package/utils/validation/index.js +205 -0
  123. package/web-test-runner.browserstack.config.mjs +123 -0
  124. package/web-test-runner.config.mjs +44 -0
@@ -0,0 +1,64 @@
1
+ import path from 'path';
2
+
3
+ import { fileURLToPath } from 'url';
4
+
5
+ const __filename = fileURLToPath(import.meta.url);
6
+
7
+ const prefix = 'mn';
8
+ const root = path.join(__filename, '..', '..');
9
+ const buildPath = path.join(root, 'build', 'tokens');
10
+
11
+ export default {
12
+ include: [root + '/tokens/**/*.js', root + '/tokens/**/*.json', root + '/tokens/*.json', root + '/components/**/**/config-tokens.json', root + '/components/**/**/design-tokens.json'],
13
+ platforms: {
14
+ js: {
15
+ buildPath: path.join(buildPath, 'es6/'),
16
+ transforms: ['color/css', 'size/rem'],
17
+ files: [
18
+ {
19
+ destination: 'muon-tokens-module.js',
20
+ format: 'es6/module'
21
+ }
22
+ ]
23
+ },
24
+ ref: {
25
+ buildPath: path.join(buildPath, 'json/'),
26
+ transforms: ['color/css', 'size/rem'],
27
+ files: [
28
+ {
29
+ destination: 'muon-tokens-reference.json',
30
+ format: 'json/reference'
31
+ }
32
+ ]
33
+ },
34
+ es6: {
35
+ buildPath: path.join(buildPath, 'es6/'),
36
+ transforms: ['name/cti/constant', 'color/css', 'size/rem'],
37
+ files: [
38
+ {
39
+ destination: 'muon-tokens.js',
40
+ format: 'javascript/es6'
41
+ },
42
+ {
43
+ destination: 'muon-tokens.mjs',
44
+ format: 'javascript/es6'
45
+ }
46
+ ]
47
+ },
48
+ 'font-face': {
49
+ buildPath: path.join(buildPath, 'css/'),
50
+ files: [
51
+ {
52
+ destination: prefix + '-fonts.css',
53
+ format: 'css/fonts'
54
+ }
55
+ ],
56
+ filter: {
57
+ attributes: {
58
+ category: 'asset',
59
+ type: 'font'
60
+ }
61
+ }
62
+ }
63
+ }
64
+ };
@@ -0,0 +1,30 @@
1
+ import path from 'path';
2
+ import appRoot from 'app-root-path';
3
+ import fs from 'fs';
4
+
5
+ const getConfig = (configFile = 'muon.config.json') => {
6
+ let config = {};
7
+ try {
8
+ let configPath = path.join(process.cwd(), configFile);
9
+
10
+ if (!fs.existsSync(configPath)) {
11
+ configPath = path.join(`${appRoot}/${configFile}`);
12
+ }
13
+ config = JSON.parse(fs.readFileSync(configPath).toString());
14
+ } catch (e) {
15
+ console.error('Missing config, is this the right folder?', e);
16
+ process.exit(1);
17
+ }
18
+
19
+ return config;
20
+ };
21
+
22
+ const getDestination = () => {
23
+ const config = getConfig();
24
+ return config?.destination || 'dist';
25
+ };
26
+
27
+ export {
28
+ getConfig,
29
+ getDestination
30
+ };
@@ -0,0 +1,283 @@
1
+ import ts from 'typescript';
2
+ import { analyzeText, analyzeSourceFile, transformAnalyzerResult } from 'web-component-analyzer';
3
+ import StyleDictionary from 'style-dictionary';
4
+ import formatHelpers from 'style-dictionary/lib/common/formatHelpers/index.js';
5
+ import _ from 'lodash';
6
+ import appRoot from 'app-root-path';
7
+ import glob from 'glob';
8
+ import globToRegExp from 'glob-to-regexp';
9
+ import fs from 'fs';
10
+ import path from 'path';
11
+
12
+ import styleConfig from '../style-dictionary.mjs';
13
+ import colorTransform from '../../tokens/utils/transforms/color.js';
14
+ import stringTransform from '../../tokens/utils/transforms/string.js';
15
+ import jsonReference from '../../tokens/utils/formats/reference.js';
16
+ import { getConfig, getDestination } from './config.mjs';
17
+ import { fileURLToPath } from 'url';
18
+
19
+ const __filename = fileURLToPath(import.meta.url);
20
+ const __dirname = path.dirname(__filename);
21
+
22
+ const cleanup = (destination, cleanOnRollup = false) => {
23
+ return new Promise((resolve) => {
24
+ const cemFilePath = path.join(destination, 'custom-elements.json');
25
+ const buildPath = path.join(__filename, '..', '..', '..', 'build');
26
+
27
+ if (fs.existsSync(destination)) {
28
+ if (cleanOnRollup) {
29
+ // eslint-disable-next-line no-unused-expressions
30
+ fs.rmSync(cemFilePath, { force: true });
31
+ } else {
32
+ fs.rmSync(destination, { force: true, recursive: true });
33
+ }
34
+ }
35
+
36
+ if (!fs.existsSync(destination)) {
37
+ fs.mkdirSync(destination);
38
+ }
39
+ if (!cleanOnRollup) {
40
+ fs.rmSync(buildPath, { force: true, recursive: true });
41
+ fs.mkdirSync(buildPath);
42
+ }
43
+ return resolve();
44
+ });
45
+ };
46
+
47
+ const filterPathToCustomElements = async (componentsList) => {
48
+ let pathPattern = '*';
49
+ if (Array.isArray(componentsList) && componentsList?.length > 0) {
50
+ if (componentsList.length > 1) {
51
+ pathPattern = `{${componentsList.toString()}}`;
52
+ } else {
53
+ pathPattern = componentsList[0] === 'all' ? '*' : componentsList[0]; // single component defined within array
54
+ }
55
+ } else {
56
+ pathPattern = componentsList === 'all' ? '*' : componentsList; // single component defined as string
57
+ }
58
+ return pathPattern;
59
+ };
60
+
61
+ const findComponents = async () => {
62
+ const config = getConfig();
63
+ const additional = config?.components?.dir;
64
+ const componentsList = config?.components?.included;
65
+ const pathPattern = await filterPathToCustomElements(componentsList);
66
+ // initial Muon components
67
+ let muonComponents = path.join(__filename, '..', '..', '..', 'components', '**', `${pathPattern}-component.js`);
68
+ // additional components
69
+ if (additional) {
70
+ muonComponents = `{${muonComponents},${additional}}`;
71
+ }
72
+
73
+ return glob.sync(muonComponents).map((f) => path.resolve(f));
74
+ };
75
+
76
+ const analyze = async () => {
77
+ const files = (await findComponents()).map((file) => {
78
+ const code = fs.readFileSync(file);
79
+
80
+ return { fileName: file, text: code.toString() };
81
+ });
82
+
83
+ const { results } = analyzeText(files);
84
+
85
+ return results.map((result) => {
86
+ // @TODO: An assumption that the first component in the file is the component we are looking for
87
+ return {
88
+ file: result.sourceFile.fileName,
89
+ name: result.componentDefinitions[0].tagName,
90
+ exportName: result.sourceFile?.symbol?.exports?.keys()?.next()?.value
91
+ };
92
+ });
93
+ };
94
+
95
+ const getAliasPaths = (type) => {
96
+ const defaultPaths = {
97
+ '@muon/components/*': '@muonic/muon/components/*',
98
+ '@muon/mixins/*': '@muonic/muon/mixins/*',
99
+ '@muon/directives/*': '@muonic/muon/directives/*',
100
+ '@muon/utils/*': '@muonic/muon/utils/*',
101
+ '@muon/tokens': '@muonic/muon/build/tokens/es6/muon-tokens'
102
+ };
103
+
104
+ const config = getConfig();
105
+ const alias = config?.alias || {};
106
+
107
+ if (type === 'glob') {
108
+ const paths = {
109
+ ...alias,
110
+ ...defaultPaths
111
+ };
112
+ const obj = {};
113
+
114
+ Object.keys(paths).forEach((key) => {
115
+ const value = paths[key];
116
+ if (
117
+ value.startsWith('./') ||
118
+ value.startsWith('../') ||
119
+ value.startsWith('/')
120
+ ) {
121
+ obj[key] = [value];
122
+ } else {
123
+ // @TODO: This needs a better way to find the node_modules folder
124
+ obj[key] = [`${appRoot}/node_modules/${value}`];
125
+ }
126
+ });
127
+
128
+ return obj;
129
+ }
130
+
131
+ if (type === 'regex') {
132
+ const objGlobToRegexArr = (paths) => {
133
+ if (!paths) {
134
+ return [];
135
+ }
136
+
137
+ return Object.keys(paths).map((key) => {
138
+ //TODO: What happens if someone uses ** in their glob?
139
+ const regKey = globToRegExp(key.replaceAll('*', '{*}'), { extended: true });
140
+ //@TODO: See how to replace * better
141
+ return { find: regKey, replacement: paths[key].replaceAll('*', '$1') };
142
+ });
143
+ };
144
+
145
+ const additionalAlias = objGlobToRegexArr(config?.alias)?.map(({ find, replacement }) => {
146
+ return {
147
+ find,
148
+ replacement: path.join(process.cwd(), replacement)
149
+ };
150
+ }).filter((alias) => alias);
151
+
152
+ const defaultAlias = objGlobToRegexArr(defaultPaths);
153
+
154
+ return [...additionalAlias, ...defaultAlias];
155
+ }
156
+
157
+ return undefined;
158
+ };
159
+
160
+ const sourceFilesAnalyzer = async () => {
161
+ const files = await findComponents();
162
+ const paths = getAliasPaths('glob');
163
+ const options = {
164
+ noEmitOnError: false,
165
+ allowJs: true,
166
+ maxNodeModuleJsDepth: 3,
167
+ experimentalDecorators: true,
168
+ target: ts.ScriptTarget.Latest,
169
+ downlevelIteration: true,
170
+ module: ts.ModuleKind.ESNext,
171
+ strictNullChecks: true,
172
+ moduleResolution: ts.ModuleResolutionKind.NodeJs,
173
+ esModuleInterop: true,
174
+ noEmit: true,
175
+ allowSyntheticDefaultImports: true,
176
+ allowUnreachableCode: true,
177
+ allowUnusedLabels: true,
178
+ skipLibCheck: true,
179
+ baseUrl: '.',
180
+ paths
181
+ };
182
+ const program = ts.createProgram(files, options);
183
+ const sourceFiles = program.getSourceFiles().filter((sf) => files.includes(sf.fileName));
184
+
185
+ const results = sourceFiles.map((sourceFile) => analyzeSourceFile(sourceFile, {
186
+ ts,
187
+ program,
188
+ verbose: true,
189
+ config: {
190
+ format: 'json',
191
+ discoverNodeModules: true,
192
+ excludedDeclarationNames: ['ScopedElementsMixin']
193
+ }
194
+ }));
195
+
196
+ const tagNames = results?.map((result) => result.componentDefinitions[0].tagName);
197
+ const tagsSet = new Set(tagNames);
198
+ if (tagsSet?.size !== tagNames?.length) {
199
+ console.error('---------------------------------------------');
200
+ console.error('No two custom elements can have same tag name `%s`', tagNames);
201
+ console.error('---------------------------------------------');
202
+ process.exit(1);
203
+ }
204
+ return transformAnalyzerResult('json', results, program);
205
+ };
206
+
207
+ const styleDictionary = async () => {
208
+ const config = getConfig();
209
+
210
+ // Set the overriding tokens if there are any
211
+ if (config.tokens && config.tokens.dir) {
212
+ styleConfig.source = config.tokens.dir;
213
+ }
214
+
215
+ const tokenUtils = path.join(__dirname, '..', '..', 'tokens', 'utils');
216
+ const cssFontTemplate = _.template(fs.readFileSync(path.join(tokenUtils, 'templates', 'font-face.css.template')));
217
+
218
+ const styleDict = StyleDictionary.extend(styleConfig);
219
+
220
+ styleDict.registerFormat(jsonReference);
221
+
222
+ styleDict.registerFormat({
223
+ name: 'css/fonts',
224
+ formatter: cssFontTemplate
225
+ });
226
+
227
+ styleDict.registerFormat({
228
+ name: 'es6/module',
229
+ formatter: function ({ dictionary, file }) {
230
+ return formatHelpers.fileHeader({ file }) +
231
+ 'export default ' +
232
+ JSON.stringify(dictionary.tokens, null, 2) + ';';
233
+ }
234
+ });
235
+
236
+ styleDict.registerTransform(stringTransform);
237
+ styleDict.registerTransform(colorTransform);
238
+
239
+ return styleDict;
240
+ };
241
+
242
+ const createTokens = async () => {
243
+ const dictionary = await styleDictionary();
244
+
245
+ return dictionary.buildAllPlatforms();
246
+ };
247
+
248
+ const componentDefiner = async () => {
249
+ const config = getConfig();
250
+ const compList = await analyze();
251
+ const prefix = config?.components?.prefix || 'muon';
252
+ let componentDefinition = `import '@webcomponents/scoped-custom-element-registry';`;
253
+
254
+ componentDefinition += compList.map(({ file, name, exportName }) => {
255
+ const elName = `${prefix}-${name}`;
256
+
257
+ return `import { ${exportName} } from '${file}';
258
+ customElements.define('${elName}', ${exportName});
259
+ `;
260
+ }).join('');
261
+
262
+ return componentDefinition;
263
+ };
264
+
265
+ const runner = async (file, overrideDestination) => {
266
+ const destination = overrideDestination || getDestination();
267
+
268
+ cleanup(destination).then(async () => {
269
+ import(file);
270
+ });
271
+ };
272
+
273
+ export {
274
+ cleanup,
275
+ getConfig,
276
+ getDestination,
277
+ filterPathToCustomElements,
278
+ createTokens,
279
+ componentDefiner,
280
+ runner,
281
+ sourceFilesAnalyzer,
282
+ getAliasPaths
283
+ };
@@ -0,0 +1,36 @@
1
+ const path = require('path');
2
+ const fs = require('fs');
3
+ const pathIsInside = require('path-is-inside');
4
+
5
+ const findStories = async (dir = process.cwd()) => {
6
+ const { getConfig, getDestination, filterPathToCustomElements } = await import('../scripts/utils/index.mjs');
7
+
8
+ const config = getConfig();
9
+ const componentsList = config?.components?.included;
10
+
11
+ if (!componentsList) {
12
+ return [];
13
+ }
14
+
15
+ const pathPattern = await filterPathToCustomElements(componentsList);
16
+ const patterns = path.join(__filename, '..', '..', 'components', pathPattern, 'story.js');
17
+
18
+ if (
19
+ pathIsInside(process.cwd(), path.join(__filename, '..', '..')) ||
20
+ pathIsInside(path.join(__filename, '..', '..'), process.cwd())
21
+ ) {
22
+ return [path.relative(dir, patterns)];
23
+ } else {
24
+ const destination = getDestination();
25
+ const symlink = path.join(destination, 'stories');
26
+
27
+ if (!fs.existsSync(symlink)) {
28
+ fs.symlinkSync(path.join(__filename, '..', '..', 'components'),
29
+ symlink, 'dir');
30
+ }
31
+
32
+ return [path.relative(dir, path.join(symlink, pathPattern, 'story.js'))];
33
+ }
34
+ };
35
+
36
+ module.exports = findStories;
@@ -0,0 +1,19 @@
1
+ import { fromRollup } from '@web/dev-server-rollup';
2
+ import { storybookPlugin } from '@web/dev-server-storybook';
3
+ import rollupJson from '@rollup/plugin-json';
4
+ import { serverPlugins } from '@muonic/muon/scripts/rollup-plugins.mjs';
5
+
6
+ const json = fromRollup(rollupJson);
7
+
8
+ export default {
9
+ nodeResolve: true,
10
+ mimeTypes: {
11
+ '**/*.json': 'js',
12
+ '**/*.css': 'js'
13
+ },
14
+ plugins: [
15
+ json(),
16
+ ...serverPlugins,
17
+ storybookPlugin({ type: 'web-components' })
18
+ ]
19
+ };
@@ -0,0 +1,86 @@
1
+ import { staticHTML, unsafeStatic } from '@muonic/muon';
2
+ export default (name, el) => {
3
+ const prefix = process.env.MUON_PREFIX;
4
+ const element = `${prefix}-${name}`;
5
+
6
+ if (!customElements.get(element)) {
7
+ customElements.define(element, el);
8
+ }
9
+
10
+ const elName = name ? name : element;
11
+ const defaultValues = {
12
+ title: element,
13
+ component: elName,
14
+ argTypes: {
15
+ registry: {
16
+ table: {
17
+ disable: true
18
+ }
19
+ },
20
+ renderOptions: {
21
+ table: {
22
+ disable: true
23
+ }
24
+ },
25
+ shadowRootOptions: {
26
+ table: {
27
+ disable: true
28
+ }
29
+ },
30
+ scopedElements: {
31
+ table: {
32
+ disable: true
33
+ }
34
+ },
35
+ slottedStyles: {
36
+ table: {
37
+ disable: true
38
+ }
39
+ }
40
+ }
41
+ };
42
+
43
+ const getTagEl = () => {
44
+ return unsafeStatic(element);
45
+ };
46
+
47
+ const dynamicArgs = (args) => {
48
+ const dArgs = args && Object.keys(args).map((arg) => {
49
+ if (arg === 'text') {
50
+ return undefined;
51
+ }
52
+
53
+ if (typeof args[arg] === 'boolean') {
54
+ return args[arg] === true ? arg : undefined;
55
+ } else if (typeof args[arg] === 'number') {
56
+ return `${arg}=${args[arg]}`;
57
+ } else if (Array.isArray(args[arg])) {
58
+ const arrayArgs = args[arg].map((arrayVal) => {
59
+ return `"${arrayVal}"`;
60
+ });
61
+ return `${arg}=[${arrayArgs}]`;
62
+ } else {
63
+ return `${arg}="${args[arg]}"`;
64
+ }
65
+ }).filter((arg) => arg).join(' ');
66
+
67
+ return unsafeStatic(dArgs);
68
+ };
69
+
70
+ const template = (args, inner) => {
71
+ const tag = getTagEl();
72
+ const dArgs = dynamicArgs(args);
73
+ return staticHTML`
74
+ <${tag} ${dArgs}>${inner ? inner(args) : ''}</${tag}>`;
75
+ };
76
+
77
+ return {
78
+ defaultValues,
79
+ element,
80
+ elName,
81
+ template,
82
+ getTagEl,
83
+ dynamicArgs
84
+ };
85
+
86
+ };
@@ -0,0 +1,87 @@
1
+ import tokens from '@muonic/muon/build/tokens/es6/muon-tokens-module.js';
2
+
3
+ const colorDetails = ([key, data]) => {
4
+ return `
5
+ <div class='swatch'>
6
+ <div style="background: ${data.value}" class='colour slide-right'></div>
7
+ <div class='details ${key}-decoration'>
8
+ <p class='name'>
9
+ <span class='value'>${key}</span>
10
+ </p>
11
+ <p class='value'>
12
+ <span class='value'>${data.value}</span>
13
+ </p>
14
+ </div>
15
+ </div>`;
16
+ };
17
+
18
+ const colorLoop = (entries) => {
19
+ let palletteHtml = '';
20
+
21
+ for (const [key, data] of entries) {
22
+
23
+ if (data.value) {
24
+ palletteHtml += colorDetails([key, data]);
25
+ } else {
26
+ const entries = Object.entries(data);
27
+ palletteHtml += `<h2>${key}</h2>`;
28
+ palletteHtml += colorLoop(entries);
29
+ palletteHtml += `<hr>`;
30
+ }
31
+ }
32
+
33
+ return palletteHtml;
34
+ };
35
+
36
+ const generatePallette = () => {
37
+ const entries = Object.entries(tokens.theme.color);
38
+
39
+ return colorLoop(entries);
40
+ };
41
+
42
+ export default {
43
+ title: 'Tokens/Theme'
44
+ };
45
+
46
+ export const color = () => {
47
+ return `<div class="inner" type="page">
48
+ <style>
49
+ body {
50
+ padding: 2em;
51
+ }
52
+ .swatch {
53
+ position: relative;
54
+ margin: 24px;
55
+ min-width: 175px;
56
+ border: 2px solid #EEE;
57
+ border-radius: 8px;
58
+ overflow: hidden;
59
+ display: inline-block;
60
+ }
61
+ .swatch .colour {
62
+ width: 100%;
63
+ height: 100px;
64
+ }
65
+ .swatch .details {
66
+ padding: 16px;
67
+ background: #fff;
68
+ }
69
+ .swatch .name {
70
+ text-transform: capitalize;
71
+ font-size: 18px;
72
+
73
+ }
74
+ .colour-value {
75
+ font-size: 0.75em;
76
+ display: block;
77
+ }
78
+
79
+ h1, h2 {
80
+ text-transform: capitalize;
81
+ color: currentColor;
82
+ }
83
+ </style>
84
+ <h1>Colors</h1>
85
+ ${generatePallette()}
86
+ </div>`;
87
+ };
@@ -0,0 +1,52 @@
1
+ import tokens from '@muonic/muon/build/tokens/es6/muon-tokens-module.js';
2
+
3
+ export default {
4
+ title: 'Tokens/Theme'
5
+ };
6
+
7
+ const fontHTML = (key, data, type, args) => {
8
+ return `
9
+ <h3>${key} - ${data.value}</h3>
10
+
11
+ <span style="font-${type}: ${data.value}">${args.text}</span>
12
+ `;
13
+ };
14
+
15
+ const generate = (type, args) => {
16
+ const entries = Object.entries(tokens.theme.font[type]);
17
+ let allHTML = `<h2>${type}</h2>`;
18
+
19
+ for (const [key, data] of entries) {
20
+
21
+ if (data.value) {
22
+ allHTML += fontHTML(key, data, type, args);
23
+ }
24
+ }
25
+
26
+ return allHTML;
27
+ };
28
+
29
+ const generateAll = (args) => {
30
+ return Object.entries(tokens.theme.font).map((entry) => {
31
+ const key = entry[0];
32
+ return generate(key, args);
33
+ }).join('');
34
+ };
35
+
36
+ export const font = (args) => {
37
+ return `<div class="inner" type="page">
38
+ <style>
39
+ body {
40
+ padding: 2em;
41
+ }
42
+
43
+ h2 {
44
+ text-transform: capitalize;
45
+ }
46
+ </style>
47
+ <h1>Font</h1>
48
+ ${generateAll(args)}
49
+ </div>`;
50
+ };
51
+
52
+ font.args = { text: 'The quick brown fox jumps over the lazy dog' };
@@ -0,0 +1,48 @@
1
+ import tokens from '@muonic/muon/build/tokens/es6/muon-tokens-module.js';
2
+
3
+ export default {
4
+ title: 'Tokens/Theme'
5
+ };
6
+
7
+ const spacerHTML = (key, data) => {
8
+ const size = data.value;
9
+ return `
10
+ <h2>${key}</h2>
11
+ <span>${size}</span>
12
+ <div style="width: ${size}; height: ${size};" class="square"></div>
13
+ `;
14
+ };
15
+
16
+ const generateAll = () => {
17
+ return Object.entries(tokens.theme.spacer).map((entry) => {
18
+ const key = entry[0];
19
+ const data = entry[1];
20
+
21
+ if (data.value) {
22
+ return spacerHTML(key, data);
23
+ }
24
+
25
+ return undefined;
26
+ }).filter((entry) => entry).join('');
27
+ };
28
+
29
+ export const spacer = () => {
30
+ return `<div class="inner" type="page">
31
+ <style>
32
+ body {
33
+ padding: 2em;
34
+ }
35
+
36
+ h2 {
37
+ text-transform: uppercase;
38
+ }
39
+
40
+ .square {
41
+ background: #888;
42
+ border: 2px solid #FFF;
43
+ }
44
+ </style>
45
+ <h1>Spacers</h1>
46
+ ${generateAll()}
47
+ </div>`;
48
+ };