@rmdes/indiekit-frontend 1.0.0-beta.25
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.
- package/README.md +10 -0
- package/assets/app-icon-any.svg +5 -0
- package/assets/app-icon-maskable.svg +5 -0
- package/assets/icon.svg +3 -0
- package/assets/not-found.svg +7 -0
- package/assets/offline.svg +7 -0
- package/assets/plug-in.svg +4 -0
- package/components/actions/macro.njk +3 -0
- package/components/actions/styles.css +19 -0
- package/components/actions/template.njk +19 -0
- package/components/add-another/index.js +170 -0
- package/components/add-another/macro.njk +3 -0
- package/components/add-another/styles.css +63 -0
- package/components/add-another/template.njk +39 -0
- package/components/app/styles.css +45 -0
- package/components/authorize/macro.njk +3 -0
- package/components/authorize/styles.css +23 -0
- package/components/authorize/template.njk +14 -0
- package/components/avatar/macro.njk +3 -0
- package/components/avatar/styles.css +23 -0
- package/components/avatar/template.njk +1 -0
- package/components/back-link/macro.njk +3 -0
- package/components/back-link/styles.css +46 -0
- package/components/back-link/template.njk +5 -0
- package/components/badge/macro.njk +3 -0
- package/components/badge/styles.css +85 -0
- package/components/badge/template.njk +7 -0
- package/components/bookmarklet/macro.njk +3 -0
- package/components/bookmarklet/styles.css +18 -0
- package/components/bookmarklet/template.njk +1 -0
- package/components/button/macro.njk +3 -0
- package/components/button/styles.css +108 -0
- package/components/button/template.njk +17 -0
- package/components/card/macro.njk +3 -0
- package/components/card/styles.css +93 -0
- package/components/card/template.njk +46 -0
- package/components/card-grid/macro.njk +3 -0
- package/components/card-grid/styles.css +9 -0
- package/components/card-grid/template.njk +8 -0
- package/components/character-count/index.js +185 -0
- package/components/character-count/macro.njk +3 -0
- package/components/character-count/styles.css +3 -0
- package/components/character-count/template.njk +14 -0
- package/components/checkboxes/index.js +130 -0
- package/components/checkboxes/macro.njk +3 -0
- package/components/checkboxes/styles.css +96 -0
- package/components/checkboxes/template.njk +96 -0
- package/components/details/macro.njk +3 -0
- package/components/details/styles.css +24 -0
- package/components/details/template.njk +12 -0
- package/components/error-message/macro.njk +3 -0
- package/components/error-message/styles.css +5 -0
- package/components/error-message/template.njk +9 -0
- package/components/error-summary/index.js +147 -0
- package/components/error-summary/macro.njk +3 -0
- package/components/error-summary/styles.css +24 -0
- package/components/error-summary/template.njk +27 -0
- package/components/event-duration/index.js +26 -0
- package/components/event-duration/styles.css +7 -0
- package/components/field/macro.njk +3 -0
- package/components/field/styles.css +14 -0
- package/components/field/template.njk +4 -0
- package/components/fieldset/macro.njk +3 -0
- package/components/fieldset/styles.css +27 -0
- package/components/fieldset/template.njk +13 -0
- package/components/file-input/index.js +123 -0
- package/components/file-input/macro.njk +3 -0
- package/components/file-input/styles.css +3 -0
- package/components/file-input/template.njk +45 -0
- package/components/footer/macro.njk +3 -0
- package/components/footer/styles.css +18 -0
- package/components/footer/template.njk +8 -0
- package/components/geo-input/index.js +105 -0
- package/components/geo-input/macro.njk +3 -0
- package/components/geo-input/styles.css +3 -0
- package/components/geo-input/template.njk +35 -0
- package/components/header/macro.njk +3 -0
- package/components/header/styles.css +60 -0
- package/components/header/template.njk +11 -0
- package/components/heading/macro.njk +3 -0
- package/components/heading/styles.css +24 -0
- package/components/heading/template.njk +20 -0
- package/components/hint/macro.njk +3 -0
- package/components/hint/styles.css +10 -0
- package/components/hint/template.njk +3 -0
- package/components/icon/styles.css +14 -0
- package/components/input/macro.njk +3 -0
- package/components/input/styles.css +111 -0
- package/components/input/template.njk +45 -0
- package/components/label/macro.njk +3 -0
- package/components/label/styles.css +4 -0
- package/components/label/template.njk +4 -0
- package/components/logo/macro.njk +3 -0
- package/components/logo/styles.css +24 -0
- package/components/logo/template.njk +3 -0
- package/components/main/styles.css +14 -0
- package/components/mention/macro.njk +3 -0
- package/components/mention/styles.css +9 -0
- package/components/mention/template.njk +6 -0
- package/components/navigation/macro.njk +3 -0
- package/components/navigation/styles.css +19 -0
- package/components/navigation/template.njk +11 -0
- package/components/notification-banner/index.js +24 -0
- package/components/notification-banner/macro.njk +3 -0
- package/components/notification-banner/styles.css +49 -0
- package/components/notification-banner/template.njk +20 -0
- package/components/pagination/macro.njk +3 -0
- package/components/pagination/styles.css +91 -0
- package/components/pagination/template.njk +42 -0
- package/components/progress/macro.njk +3 -0
- package/components/progress/styles.css +38 -0
- package/components/progress/template.njk +10 -0
- package/components/prose/macro.njk +3 -0
- package/components/prose/styles.css +12 -0
- package/components/prose/template.njk +3 -0
- package/components/radios/index.js +83 -0
- package/components/radios/macro.njk +3 -0
- package/components/radios/styles.css +104 -0
- package/components/radios/template.njk +87 -0
- package/components/section/macro.njk +3 -0
- package/components/section/styles.css +12 -0
- package/components/section/template.njk +19 -0
- package/components/select/macro.njk +3 -0
- package/components/select/styles.css +37 -0
- package/components/select/template.njk +48 -0
- package/components/share-preview/index.js +54 -0
- package/components/share-preview/macro.njk +3 -0
- package/components/share-preview/styles.css +36 -0
- package/components/share-preview/template.njk +14 -0
- package/components/skip-link/macro.njk +3 -0
- package/components/skip-link/styles.css +12 -0
- package/components/skip-link/template.njk +3 -0
- package/components/summary/macro.njk +3 -0
- package/components/summary/styles.css +60 -0
- package/components/summary/template.njk +19 -0
- package/components/tag/macro.njk +3 -0
- package/components/tag/styles.css +14 -0
- package/components/tag/template.njk +5 -0
- package/components/tag-input/index.js +69 -0
- package/components/tag-input/macro.njk +3 -0
- package/components/tag-input/sanitizer.js +27 -0
- package/components/tag-input/styles.css +161 -0
- package/components/tag-input/template.njk +29 -0
- package/components/textarea/index.js +298 -0
- package/components/textarea/macro.njk +3 -0
- package/components/textarea/styles.css +42 -0
- package/components/textarea/template.njk +40 -0
- package/components/user/macro.njk +3 -0
- package/components/user/styles.css +20 -0
- package/components/user/template.njk +15 -0
- package/components/warning-text/macro.njk +3 -0
- package/components/warning-text/styles.css +15 -0
- package/components/warning-text/template.njk +8 -0
- package/components/widget/macro.njk +3 -0
- package/components/widget/styles.css +28 -0
- package/components/widget/template.njk +20 -0
- package/index.js +10 -0
- package/layouts/default.njk +122 -0
- package/layouts/document.njk +15 -0
- package/layouts/error.njk +19 -0
- package/layouts/form.njk +22 -0
- package/lib/esbuild.js +22 -0
- package/lib/filters/index.js +10 -0
- package/lib/filters/locale.js +17 -0
- package/lib/filters/string.js +29 -0
- package/lib/filters/url.js +69 -0
- package/lib/globals/attributes.js +23 -0
- package/lib/globals/classes.js +19 -0
- package/lib/globals/error-list.js +21 -0
- package/lib/globals/field-data.js +20 -0
- package/lib/globals/icon.js +80 -0
- package/lib/globals/index.js +12 -0
- package/lib/globals/item-id.js +17 -0
- package/lib/globals/summary-rows.js +39 -0
- package/lib/lightningcss.js +41 -0
- package/lib/markdown-it.js +27 -0
- package/lib/nunjucks.js +43 -0
- package/lib/serviceworker.js +240 -0
- package/lib/sharp.js +39 -0
- package/lib/utils/theme.js +115 -0
- package/lib/utils/wrap-element.js +11 -0
- package/locales/de.json +60 -0
- package/locales/en.json +60 -0
- package/locales/es-419.json +60 -0
- package/locales/es.json +60 -0
- package/locales/fr.json +60 -0
- package/locales/hi.json +60 -0
- package/locales/id.json +60 -0
- package/locales/it.json +60 -0
- package/locales/nl.json +60 -0
- package/locales/pl.json +60 -0
- package/locales/pt-BR.json +60 -0
- package/locales/pt.json +60 -0
- package/locales/sr.json +60 -0
- package/locales/sv.json +60 -0
- package/locales/zh-Hans-CN.json +60 -0
- package/package.json +64 -0
- package/scripts/app.js +23 -0
- package/styles/app.css +73 -0
- package/styles/base/embedded.css +29 -0
- package/styles/base/forms.css +55 -0
- package/styles/base/grouping.css +43 -0
- package/styles/base/interactive.css +19 -0
- package/styles/base/sections.css +59 -0
- package/styles/base/tables.css +30 -0
- package/styles/base/text.css +71 -0
- package/styles/config/custom-properties.css +211 -0
- package/styles/scopes/flow.css +114 -0
- package/styles/utilities/container.css +6 -0
- package/styles/utilities/visually-hidden.css +10 -0
- package/styles/vendor/codemirror.css +116 -0
- package/styles/vendor/easy-markdown-editor.css +219 -0
- package/styles/vendor/markdown-it-prism.css +79 -0
package/README.md
ADDED
|
@@ -0,0 +1,5 @@
|
|
|
1
|
+
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 512 512">
|
|
2
|
+
<path fill="#333" d="M0 0h512v512H0z"/>
|
|
3
|
+
<circle fill="#ccc" cx="156" cy="156" r="94"/>
|
|
4
|
+
<path fill="#ccc" d="M79.4 264h153.2c5.4 0 7.3.6 9.3 1.6 2 1 3.5 2.6 4.5 4.5 1 2 1.6 4 1.6 9.3v153.2c0 5.4-.6 7.3-1.6 9.3-1 2-2.6 3.5-4.5 4.5-2 1-4 1.6-9.3 1.6H79.4c-5.4 0-7.3-.6-9.3-1.6-2-1-3.5-2.6-4.5-4.5-1-2-1.6-4-1.6-9.3V279.4c0-5.4.6-7.3 1.6-9.3 1-2 2.6-3.5 4.5-4.5 2-1 4-1.6 9.3-1.6Zm191.1 0h162.1c5.4 0 7.3.6 9.3 1.6 2 1 3.5 2.6 4.5 4.5 1 2 1.6 4 1.6 9.3v162.1a6 6 0 0 1-10.2 4.3L266.2 274.2a6 6 0 0 1 4.3-10.2Zm3.2-16C379.3 248 448 174 448 73.7c0-6.5-3.2-9.7-9.7-9.7H276a12 12 0 0 0-12 12v162.3c0 6.5 3.2 9.7 9.7 9.7Z"/>
|
|
5
|
+
</svg>
|
|
@@ -0,0 +1,5 @@
|
|
|
1
|
+
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 512 512">
|
|
2
|
+
<path fill="#333" d="M0 0h512v512H0z"/>
|
|
3
|
+
<circle fill="#ccc" cx="180" cy="180" r="72" />
|
|
4
|
+
<path fill="#ccc" d="M125.4 262h109.2c5.4 0 7.3.6 9.3 1.6 2 1 3.5 2.6 4.5 4.5 1 2 1.6 4 1.6 9.3v109.2c0 5.4-.6 7.3-1.6 9.3-1 2-2.6 3.5-4.5 4.5-2 1-4 1.6-9.3 1.6H125.4c-5.4 0-7.3-.6-9.3-1.6-2-1-3.5-2.6-4.5-4.5-1-2-1.6-4-1.6-9.3V277.4c0-5.4.6-7.3 1.6-9.3 1-2 2.6-3.5 4.5-4.5 2-1 4-1.6 9.3-1.6Zm145.1 0h116.1c5.4 0 7.3.6 9.3 1.6 2 1 3.5 2.6 4.5 4.5 1 2 1.6 4 1.6 9.3v116.1a6 6 0 0 1-10.2 4.3L266.2 272.2a6 6 0 0 1 4.3-10.2Zm-1.1-12c80.3 0 132.6-56.3 132.6-132.6 0-5-2.5-7.4-7.4-7.4H274a12 12 0 0 0-12 12v120.6c0 5 2.5 7.4 7.4 7.4Z"/>
|
|
5
|
+
</svg>
|
package/assets/icon.svg
ADDED
|
@@ -0,0 +1,7 @@
|
|
|
1
|
+
<svg xmlns="http://www.w3.org/2000/svg">
|
|
2
|
+
<defs>
|
|
3
|
+
<path id="icon" fill="#AAA" d="m14 17 12 12 6-6 12 12v1a8 8 0 0 1-8 8H12a8 8 0 0 1-8-8v-9l10-10Zm0 5-6 6v8a4 4 0 0 0 3.8 4H36a4 4 0 0 0 4-3.8V36l-8-8-6 6-12-12ZM32.3 4c1 0 2.1.4 2.9 1.2l7.6 7.6a4 4 0 0 1 1.2 2.9V32l-4-4V16h-8V8H12c-2 0-4 2-4 4v8l-4 4V12a8 8 0 0 1 8-8h20.3Z" opacity=".7"/>
|
|
4
|
+
</defs>
|
|
5
|
+
<rect fill="#000" width="100%" height="100%" opacity="0.075"/>
|
|
6
|
+
<use href="#icon" x="50%" y="50%" transform="translate(-24 -24)"/>
|
|
7
|
+
</svg>
|
|
@@ -0,0 +1,7 @@
|
|
|
1
|
+
<svg xmlns="http://www.w3.org/2000/svg">
|
|
2
|
+
<defs>
|
|
3
|
+
<path id="icon" fill="#AAA" d="M24 32a5 5 0 1 1 0 10 5 5 0 0 1 0-10Zm-6.9-11.9 4.1 4.1a17 17 0 0 0-9.7 5.3L8 26a22 22 0 0 1 9-6Zm22.5 5.4L36 29l-.8-.8L26 19a22 22 0 0 1 13.5 6.4ZM8.2 11.2l3.7 3.7a24.7 24.7 0 0 0-8.4 6.6l-3.6-3.6c2.4-2.7 5.2-5 8.3-6.7ZM24 7a32 32 0 0 1 23.4 10.2l-3.5 3.6a27 27 0 0 0-24.5-8.4l-4.2-4.2A32 32 0 0 1 24 7ZM2 5l3-3 41 41-3 3L2 5Z" opacity=".7"/>
|
|
4
|
+
</defs>
|
|
5
|
+
<rect fill="#000" width="100%" height="100%" opacity="0.075"/>
|
|
6
|
+
<use href="#icon" x="50%" y="50%" transform="translate(-24 -24)"/>
|
|
7
|
+
</svg>
|
|
@@ -0,0 +1,4 @@
|
|
|
1
|
+
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 96 96">
|
|
2
|
+
<path fill="#17181C" d="M0 0h96v96H0z"/>
|
|
3
|
+
<path fill="#FFF" d="M14 70V36a4 4 0 0 1 4-4h60a4 4 0 0 1 4 4v34a4 4 0 0 1-4 4H18a4 4 0 0 1-4-4Zm12-48h12a2 2 0 0 1 2 2v5H24v-5c0-1.1.9-2 2-2Zm32 0h12a2 2 0 0 1 2 2v5H56v-5c0-1.1.9-2 2-2Z"/>
|
|
4
|
+
</svg>
|
|
@@ -0,0 +1,19 @@
|
|
|
1
|
+
.actions {
|
|
2
|
+
--anchor-decoration-color: transparent;
|
|
3
|
+
--icon-margin: var(--space-2xs);
|
|
4
|
+
display: flex;
|
|
5
|
+
flex-wrap: wrap;
|
|
6
|
+
font: var(--font-body);
|
|
7
|
+
gap: var(--space-2xs) var(--space-l);
|
|
8
|
+
}
|
|
9
|
+
|
|
10
|
+
.actions__link {
|
|
11
|
+
margin: calc(var(--space-s) * -1);
|
|
12
|
+
padding: var(--space-s);
|
|
13
|
+
white-space: nowrap;
|
|
14
|
+
}
|
|
15
|
+
|
|
16
|
+
.actions__link--warning {
|
|
17
|
+
--anchor-color: var(--color-error);
|
|
18
|
+
--anchor-color-hover: var(--color-error-variant);
|
|
19
|
+
}
|
|
@@ -0,0 +1,19 @@
|
|
|
1
|
+
{% macro _actionLink(action) %}
|
|
2
|
+
<a class="{{ classes("actions__link", action) }}" href="{{ action.href }}"{{ attributes(action.attributes) }}>
|
|
3
|
+
{{- icon(action.icon) if action.icon -}}
|
|
4
|
+
{{- action.text | safe -}}
|
|
5
|
+
</a>
|
|
6
|
+
{% endmacro %}
|
|
7
|
+
{%- if opts.items.length === 1 %}
|
|
8
|
+
<div class="{{ classes("actions", opts) }}">
|
|
9
|
+
{{ _actionLink(opts.items[0]) | trim }}
|
|
10
|
+
</div>
|
|
11
|
+
{%- else %}
|
|
12
|
+
<ul class="{{ classes("actions", opts) }}" role="list">
|
|
13
|
+
{% for item in opts.items %}{% if item.text %}
|
|
14
|
+
<li class="actions__list-item">
|
|
15
|
+
{{ _actionLink(item) | trim }}
|
|
16
|
+
</li>
|
|
17
|
+
{% endif %}{% endfor %}
|
|
18
|
+
</ul>
|
|
19
|
+
{%- endif %}
|
|
@@ -0,0 +1,170 @@
|
|
|
1
|
+
const focusableSelector = `button:not([disabled]), input:not([disabled]):not([type="hidden"]), select:not([disabled]), textarea:not([disabled]), [tabindex]:not([tabindex="-1"]`;
|
|
2
|
+
|
|
3
|
+
export const AddAnotherComponent = class extends HTMLElement {
|
|
4
|
+
connectedCallback() {
|
|
5
|
+
this.$addButtonTemplate = this.querySelector("#add-button");
|
|
6
|
+
this.$deleteButtonTemplate = this.querySelector("#delete-button");
|
|
7
|
+
this.$$fields = this.querySelectorAll(".field");
|
|
8
|
+
this.$list = this.querySelector(".add-another__list");
|
|
9
|
+
|
|
10
|
+
this.updateItems();
|
|
11
|
+
this.createAddButton();
|
|
12
|
+
}
|
|
13
|
+
|
|
14
|
+
/**
|
|
15
|
+
* Add item to list
|
|
16
|
+
* @param {Event} event - Add button event
|
|
17
|
+
*/
|
|
18
|
+
add(event) {
|
|
19
|
+
event.preventDefault();
|
|
20
|
+
const $newItem = this.createItem();
|
|
21
|
+
this.$list.append($newItem);
|
|
22
|
+
this.updateItems();
|
|
23
|
+
$newItem.querySelector(focusableSelector).focus();
|
|
24
|
+
}
|
|
25
|
+
|
|
26
|
+
/**
|
|
27
|
+
* Delete item from list
|
|
28
|
+
* @param {Event} event - Delete button event
|
|
29
|
+
*/
|
|
30
|
+
delete(event) {
|
|
31
|
+
event.preventDefault();
|
|
32
|
+
event.target.closest("li").remove();
|
|
33
|
+
this.updateItems();
|
|
34
|
+
this.focusHeading();
|
|
35
|
+
}
|
|
36
|
+
|
|
37
|
+
/**
|
|
38
|
+
* Get heading
|
|
39
|
+
* @returns {HTMLLegendElement} - Group legend
|
|
40
|
+
*/
|
|
41
|
+
getHeading() {
|
|
42
|
+
return this.querySelector("legend");
|
|
43
|
+
}
|
|
44
|
+
|
|
45
|
+
/**
|
|
46
|
+
* Focus heading
|
|
47
|
+
*/
|
|
48
|
+
focusHeading() {
|
|
49
|
+
const $heading = this.getHeading();
|
|
50
|
+
|
|
51
|
+
$heading.setAttribute("tabindex", "-1");
|
|
52
|
+
$heading.focus();
|
|
53
|
+
}
|
|
54
|
+
|
|
55
|
+
/**
|
|
56
|
+
* Create add button
|
|
57
|
+
*/
|
|
58
|
+
createAddButton() {
|
|
59
|
+
let $addButton = this.$addButtonTemplate.content.cloneNode(true);
|
|
60
|
+
|
|
61
|
+
this.append($addButton);
|
|
62
|
+
|
|
63
|
+
$addButton = this.querySelector(".add-another__add");
|
|
64
|
+
$addButton.addEventListener("click", (event) => this.add(event));
|
|
65
|
+
}
|
|
66
|
+
|
|
67
|
+
/**
|
|
68
|
+
* Get delete button
|
|
69
|
+
* @param {HTMLElement} element - Containing element
|
|
70
|
+
* @returns {HTMLButtonElement} - Delete button
|
|
71
|
+
*/
|
|
72
|
+
getDeleteButton(element) {
|
|
73
|
+
return element.querySelector(".add-another__delete");
|
|
74
|
+
}
|
|
75
|
+
|
|
76
|
+
/**
|
|
77
|
+
* Create delete button
|
|
78
|
+
* @param {HTMLElement} element - Containing element
|
|
79
|
+
*/
|
|
80
|
+
createDeleteButton(element) {
|
|
81
|
+
const $deleteButton =
|
|
82
|
+
this.$deleteButtonTemplate.content.firstElementChild.cloneNode(true);
|
|
83
|
+
|
|
84
|
+
element.append($deleteButton);
|
|
85
|
+
}
|
|
86
|
+
|
|
87
|
+
/**
|
|
88
|
+
* Update delete button
|
|
89
|
+
* @param {HTMLElement} element - Containing element
|
|
90
|
+
*/
|
|
91
|
+
updateDeleteButton(element) {
|
|
92
|
+
const $deleteButton = this.getDeleteButton(element);
|
|
93
|
+
$deleteButton.setAttribute("aria-labelledby", `delete-title ${element.id}`);
|
|
94
|
+
$deleteButton.addEventListener("click", (event) => this.delete(event));
|
|
95
|
+
}
|
|
96
|
+
|
|
97
|
+
/**
|
|
98
|
+
* Create new item by cloning first item in list and updating its attributes
|
|
99
|
+
* @returns {HTMLLIElement} - List item containing form field(s)
|
|
100
|
+
*/
|
|
101
|
+
createItem() {
|
|
102
|
+
const $$items = this.querySelectorAll(".add-another__list-item");
|
|
103
|
+
const $item = $$items[0].cloneNode(true);
|
|
104
|
+
const uid = Date.now().toString();
|
|
105
|
+
|
|
106
|
+
const $$fields = $item.querySelectorAll(".field--error");
|
|
107
|
+
for (const $field of $$fields) {
|
|
108
|
+
$field.classList.remove("field--error");
|
|
109
|
+
}
|
|
110
|
+
|
|
111
|
+
const $$errorMessages = $item.querySelectorAll(".error-message");
|
|
112
|
+
for (const $errorMessage of $$errorMessages) {
|
|
113
|
+
$errorMessage.remove();
|
|
114
|
+
}
|
|
115
|
+
|
|
116
|
+
const $$inputs = $item.querySelectorAll("input, select, textarea");
|
|
117
|
+
for (const $input of $$inputs) {
|
|
118
|
+
$input.id = $input.id.replace("-0", `-${uid}`);
|
|
119
|
+
$input.name = $input.name.replace("[0]", `[${uid}]`);
|
|
120
|
+
$input.value = "";
|
|
121
|
+
$input.classList.remove(
|
|
122
|
+
"input--error",
|
|
123
|
+
"select--error",
|
|
124
|
+
"textarea--error",
|
|
125
|
+
);
|
|
126
|
+
}
|
|
127
|
+
|
|
128
|
+
const $$labels = $item.querySelectorAll("label");
|
|
129
|
+
for (const $label of $$labels) {
|
|
130
|
+
const forAttribute = $label.getAttribute("for");
|
|
131
|
+
$label.setAttribute("for", forAttribute.replace("-0", `-${uid}`));
|
|
132
|
+
}
|
|
133
|
+
|
|
134
|
+
$item.id = `${this.id}-${uid}`;
|
|
135
|
+
|
|
136
|
+
return $item;
|
|
137
|
+
}
|
|
138
|
+
|
|
139
|
+
/**
|
|
140
|
+
* Update all items
|
|
141
|
+
* - Update ID’s to use for labelling remove button
|
|
142
|
+
* - Update ARIA label to reference item’s position in list
|
|
143
|
+
* - Add remove buttons (or remove if only one item remaining in list)
|
|
144
|
+
*/
|
|
145
|
+
updateItems() {
|
|
146
|
+
const $$items = this.querySelectorAll(".add-another__list-item");
|
|
147
|
+
|
|
148
|
+
for (const [index, $item] of $$items.entries()) {
|
|
149
|
+
$item.id = $item.id || `${this.id}-${index}`;
|
|
150
|
+
$item.setAttribute("aria-label", `Item ${index + 1}`);
|
|
151
|
+
|
|
152
|
+
// If no delete button, add one (if more than 1 item in list)
|
|
153
|
+
// Used when initializing
|
|
154
|
+
if (!this.getDeleteButton($item) && $$items.length > 1) {
|
|
155
|
+
this.createDeleteButton($item);
|
|
156
|
+
}
|
|
157
|
+
|
|
158
|
+
// If has delete button
|
|
159
|
+
if (this.getDeleteButton($item)) {
|
|
160
|
+
if ($$items.length === 1) {
|
|
161
|
+
// If only 1 item in list, remove button
|
|
162
|
+
this.getDeleteButton($item).remove();
|
|
163
|
+
} else {
|
|
164
|
+
// Else update button attributes
|
|
165
|
+
this.updateDeleteButton($item);
|
|
166
|
+
}
|
|
167
|
+
}
|
|
168
|
+
}
|
|
169
|
+
}
|
|
170
|
+
};
|
|
@@ -0,0 +1,63 @@
|
|
|
1
|
+
add-another {
|
|
2
|
+
--counter-size: 1.66667em;
|
|
3
|
+
display: block;
|
|
4
|
+
}
|
|
5
|
+
|
|
6
|
+
.add-another__list {
|
|
7
|
+
counter-reset: items;
|
|
8
|
+
}
|
|
9
|
+
|
|
10
|
+
.add-another__list-item {
|
|
11
|
+
--label-font: var(--font-fieldset-label);
|
|
12
|
+
margin-block-end: var(--space-m);
|
|
13
|
+
padding-block: var(--space-xs);
|
|
14
|
+
padding-inline-start: calc(var(--counter-size) + var(--space-s));
|
|
15
|
+
position: relative;
|
|
16
|
+
|
|
17
|
+
& .fieldset--group {
|
|
18
|
+
margin-block-start: 0;
|
|
19
|
+
}
|
|
20
|
+
|
|
21
|
+
&::before {
|
|
22
|
+
align-items: center;
|
|
23
|
+
background-color: var(--color-offset);
|
|
24
|
+
block-size: var(--counter-size);
|
|
25
|
+
border-radius: var(--border-radius-small);
|
|
26
|
+
color: var(--color-on-offset);
|
|
27
|
+
content: counter(items);
|
|
28
|
+
counter-increment: items;
|
|
29
|
+
display: flex;
|
|
30
|
+
font: var(--font-label);
|
|
31
|
+
inline-size: var(--counter-size);
|
|
32
|
+
inset: 0;
|
|
33
|
+
justify-content: center;
|
|
34
|
+
position: absolute;
|
|
35
|
+
}
|
|
36
|
+
|
|
37
|
+
&:not([hidden]) {
|
|
38
|
+
display: flex;
|
|
39
|
+
}
|
|
40
|
+
|
|
41
|
+
& > :first-child {
|
|
42
|
+
flex: 1;
|
|
43
|
+
}
|
|
44
|
+
}
|
|
45
|
+
|
|
46
|
+
.add-another__add.button {
|
|
47
|
+
display: flex;
|
|
48
|
+
inline-size: calc(100% - var(--counter-size) - var(--space-s));
|
|
49
|
+
margin-block-start: 0;
|
|
50
|
+
margin-inline-start: calc(var(--counter-size) + var(--space-s));
|
|
51
|
+
}
|
|
52
|
+
|
|
53
|
+
.add-another__delete.button {
|
|
54
|
+
--button-padding: 0;
|
|
55
|
+
--icon-size: 0.875em;
|
|
56
|
+
|
|
57
|
+
block-size: var(--counter-size);
|
|
58
|
+
display: flex;
|
|
59
|
+
inline-size: var(--counter-size);
|
|
60
|
+
inset-block-start: var(--counter-size);
|
|
61
|
+
inset-inline-start: 0;
|
|
62
|
+
position: absolute;
|
|
63
|
+
}
|
|
@@ -0,0 +1,39 @@
|
|
|
1
|
+
{% from "../button/macro.njk" import button with context %}
|
|
2
|
+
{% from "../field/macro.njk" import field with context %}
|
|
3
|
+
{% from "../fieldset/macro.njk" import fieldset with context %}
|
|
4
|
+
{% set id = opts.id or opts.name | slugify({ decamelize: true }) %}
|
|
5
|
+
{# `fieldset` is false by default #}
|
|
6
|
+
{%- set hasFieldset = true if opts.fieldset else false %}
|
|
7
|
+
{# Capture the HTML so we can optionally nest it within a fieldset #}
|
|
8
|
+
{%- set innerHtml %}{{ caller() if caller }}{% endset %}
|
|
9
|
+
{% call field({
|
|
10
|
+
element: "add-another",
|
|
11
|
+
classes: opts.field.classes,
|
|
12
|
+
attributes: {
|
|
13
|
+
id: id
|
|
14
|
+
}
|
|
15
|
+
}) %}
|
|
16
|
+
{% if opts.fieldset %}
|
|
17
|
+
{% call fieldset({
|
|
18
|
+
describedBy: describedBy,
|
|
19
|
+
classes: opts.fieldset.classes,
|
|
20
|
+
attributes: opts.fieldset.attributes,
|
|
21
|
+
legend: opts.fieldset.legend
|
|
22
|
+
}) %}{{ innerHtml | trim | safe }}{% endcall %}
|
|
23
|
+
{% else %}
|
|
24
|
+
{{ innerHtml | trim | safe }}
|
|
25
|
+
{% endif %}
|
|
26
|
+
<template id="add-button">
|
|
27
|
+
{{ button({
|
|
28
|
+
classes: "add-another__add button--secondary",
|
|
29
|
+
text: __("addAnother.add", opts.name)
|
|
30
|
+
}) | indent(4) }}
|
|
31
|
+
</template>
|
|
32
|
+
<template id="delete-button">
|
|
33
|
+
{{ button({
|
|
34
|
+
classes: "add-another__delete button--warning",
|
|
35
|
+
icon: "delete",
|
|
36
|
+
iconText: __("addAnother.delete")
|
|
37
|
+
}) | indent(4) }}
|
|
38
|
+
</template>
|
|
39
|
+
{% endcall %}
|
|
@@ -0,0 +1,45 @@
|
|
|
1
|
+
.app {
|
|
2
|
+
background-color: var(--color-offset);
|
|
3
|
+
display: flex;
|
|
4
|
+
flex-direction: column;
|
|
5
|
+
font-family: var(--font-family-sans);
|
|
6
|
+
justify-content: space-between;
|
|
7
|
+
}
|
|
8
|
+
|
|
9
|
+
.app--minimalui {
|
|
10
|
+
--container-max-inline-size: 36rem;
|
|
11
|
+
|
|
12
|
+
& .header,
|
|
13
|
+
& .footer {
|
|
14
|
+
border: 0;
|
|
15
|
+
}
|
|
16
|
+
|
|
17
|
+
& .header__container,
|
|
18
|
+
& .footer__container {
|
|
19
|
+
align-items: center;
|
|
20
|
+
inline-size: auto;
|
|
21
|
+
}
|
|
22
|
+
|
|
23
|
+
& .main {
|
|
24
|
+
@media (width > 36rem) {
|
|
25
|
+
border-radius: var(--border-radius-large);
|
|
26
|
+
flex: 0;
|
|
27
|
+
margin: auto;
|
|
28
|
+
overflow: hidden;
|
|
29
|
+
}
|
|
30
|
+
}
|
|
31
|
+
|
|
32
|
+
& .main__container {
|
|
33
|
+
padding-block: var(--space-l);
|
|
34
|
+
}
|
|
35
|
+
|
|
36
|
+
& .notification {
|
|
37
|
+
border-start-end-radius: var(--border-radius-large);
|
|
38
|
+
border-start-start-radius: var(--border-radius-large);
|
|
39
|
+
}
|
|
40
|
+
|
|
41
|
+
& .notification + .main__container {
|
|
42
|
+
border-start-end-radius: 0;
|
|
43
|
+
border-start-start-radius: 0;
|
|
44
|
+
}
|
|
45
|
+
}
|
|
@@ -0,0 +1,23 @@
|
|
|
1
|
+
.authorize {
|
|
2
|
+
--authorize-client-icon-size: 4rem;
|
|
3
|
+
line-height: var(--line-height-tight);
|
|
4
|
+
|
|
5
|
+
&:has(.authorize__client-icon) {
|
|
6
|
+
min-block-size: var(--authorize-client-icon-size);
|
|
7
|
+
}
|
|
8
|
+
|
|
9
|
+
& a {
|
|
10
|
+
font-weight: 600;
|
|
11
|
+
}
|
|
12
|
+
}
|
|
13
|
+
|
|
14
|
+
.authorize__client-icon {
|
|
15
|
+
background-color: var(--color-neutral90); /* Ignore color-scheme */
|
|
16
|
+
block-size: var(--authorize-client-icon-size);
|
|
17
|
+
border-radius: var(--border-radius-small);
|
|
18
|
+
box-shadow: inset 0 0 0 1px var(--color-shadow);
|
|
19
|
+
float: inline-start;
|
|
20
|
+
inline-size: var(--authorize-client-icon-size);
|
|
21
|
+
margin-inline-end: var(--space-s);
|
|
22
|
+
padding: var(--space-2xs);
|
|
23
|
+
}
|
|
@@ -0,0 +1,14 @@
|
|
|
1
|
+
{% set clientLink = opts.client.name | friendlyUrl | linkTo(opts.client.url) %}
|
|
2
|
+
{% set meLink = opts.me | friendlyUrl | replace("/", "/<wbr>") | linkTo(opts.me) %}
|
|
3
|
+
<p class="{{ classes("authorize", opts) }} s-flow"
|
|
4
|
+
{{- attributes(opts.attributes) }}>
|
|
5
|
+
{% if opts.client.logo %}
|
|
6
|
+
<a class="authorize__client" href="{{ opts.client.url }}">
|
|
7
|
+
<img class="authorize__client-icon" src="{{ opts.client.logo }}" alt="" height="64" width="64">
|
|
8
|
+
</a>
|
|
9
|
+
{% endif %}
|
|
10
|
+
{{ __(opts.key, {
|
|
11
|
+
client: "__client__",
|
|
12
|
+
me: "__me__"
|
|
13
|
+
}) | replace("__client__", clientLink) | replace("__me__", meLink) | markdown("inline") | safe }}
|
|
14
|
+
</p>
|
|
@@ -0,0 +1,23 @@
|
|
|
1
|
+
.avatar {
|
|
2
|
+
background:
|
|
3
|
+
radial-gradient(
|
|
4
|
+
circle,
|
|
5
|
+
var(--color-offset-variant-darker) 50%,
|
|
6
|
+
transparent 50%
|
|
7
|
+
)
|
|
8
|
+
50% 20%/75% 75% no-repeat,
|
|
9
|
+
radial-gradient(
|
|
10
|
+
circle,
|
|
11
|
+
var(--color-offset-variant-darker) 50%,
|
|
12
|
+
transparent 50%
|
|
13
|
+
)
|
|
14
|
+
50% -50%/100% 160% no-repeat,
|
|
15
|
+
var(--color-offset);
|
|
16
|
+
block-size: var(--avatar-size, 3rem);
|
|
17
|
+
border-radius: var(--border-radius-small);
|
|
18
|
+
inline-size: var(--avatar-size, 3rem);
|
|
19
|
+
max-inline-size: none;
|
|
20
|
+
object-fit: cover;
|
|
21
|
+
outline: var(--border-width-thin) solid var(--color-shadow);
|
|
22
|
+
outline-offset: calc(var(--border-width-thin) * -1);
|
|
23
|
+
}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
<img class="{{ classes("avatar", opts) }}" src="{{ opts.src }}" alt="{{ opts.alt }}">
|
|
@@ -0,0 +1,46 @@
|
|
|
1
|
+
.back-link {
|
|
2
|
+
--anchor-decoration-color: transparent;
|
|
3
|
+
--back-link-padding: var(--space-s);
|
|
4
|
+
--back-link-chevron-rotation: -45deg;
|
|
5
|
+
--back-link-chevron-size: 0.5em;
|
|
6
|
+
--back-link-chevron-thickness: var(--text-thickness);
|
|
7
|
+
|
|
8
|
+
display: inline-block;
|
|
9
|
+
font: var(--font-caption);
|
|
10
|
+
margin-inline: calc(var(--back-link-padding) * -1);
|
|
11
|
+
padding: var(--back-link-padding);
|
|
12
|
+
padding-block-start: var(--back-link-padding);
|
|
13
|
+
padding-inline-start: calc(var(--back-link-padding) * 2);
|
|
14
|
+
position: relative;
|
|
15
|
+
|
|
16
|
+
&::before {
|
|
17
|
+
block-size: var(--back-link-chevron-size);
|
|
18
|
+
border: 0 solid currentcolor;
|
|
19
|
+
border-block-start-width: var(--back-link-chevron-thickness);
|
|
20
|
+
border-inline-start-width: var(--back-link-chevron-thickness);
|
|
21
|
+
content: "";
|
|
22
|
+
display: block;
|
|
23
|
+
inline-size: var(--back-link-chevron-size);
|
|
24
|
+
inset-block-start: calc(
|
|
25
|
+
var(--back-link-padding) + var(--back-link-chevron-size)
|
|
26
|
+
);
|
|
27
|
+
inset-inline-start: var(--back-link-padding);
|
|
28
|
+
position: absolute;
|
|
29
|
+
transform: rotate(var(--back-link-chevron-rotation));
|
|
30
|
+
}
|
|
31
|
+
|
|
32
|
+
&:focus-visible::before,
|
|
33
|
+
&:hover::before {
|
|
34
|
+
--back-link-chevron-thickness: calc(var(--text-thickness) * 2);
|
|
35
|
+
}
|
|
36
|
+
|
|
37
|
+
&::after {
|
|
38
|
+
content: "";
|
|
39
|
+
inset: 0;
|
|
40
|
+
position: absolute;
|
|
41
|
+
}
|
|
42
|
+
}
|
|
43
|
+
|
|
44
|
+
:root[dir="rtl"] .back-link {
|
|
45
|
+
--back-link-chevron-rotation: 45deg;
|
|
46
|
+
}
|
|
@@ -0,0 +1,85 @@
|
|
|
1
|
+
.badge {
|
|
2
|
+
/*
|
|
3
|
+
* 1. When a user customises their colours, often the background is removed.
|
|
4
|
+
* Adding an outline ensures that badge still keeps it’s meaning.
|
|
5
|
+
*
|
|
6
|
+
* @link https://accessibility.blog.gov.uk/2017/03/27/how-users-change-colours-on-websites/
|
|
7
|
+
*
|
|
8
|
+
* 2. Adjust baseline to visually center text within pill shape.
|
|
9
|
+
*/
|
|
10
|
+
--icon-margin: var(--space-xs);
|
|
11
|
+
align-items: center;
|
|
12
|
+
background-color: var(--color-primary);
|
|
13
|
+
border-radius: var(--space-l);
|
|
14
|
+
color: var(--color-on-primary);
|
|
15
|
+
display: inline flow-root;
|
|
16
|
+
font: var(--font-caption);
|
|
17
|
+
font-weight: 500;
|
|
18
|
+
outline: var(--border-width-thick) solid transparent; /* 1 */
|
|
19
|
+
outline-offset: calc(var(--border-width-thick) * -1); /* 1 */
|
|
20
|
+
padding-block-end: calc(var(--space-2xs) - 0.0625rem); /* 2 */
|
|
21
|
+
padding-block-start: calc(var(--space-2xs) + 0.0625rem); /* 2 */
|
|
22
|
+
padding-inline: var(--space-m);
|
|
23
|
+
white-space: nowrap;
|
|
24
|
+
|
|
25
|
+
& + .badge {
|
|
26
|
+
margin-inline-start: var(--space-2xs);
|
|
27
|
+
}
|
|
28
|
+
|
|
29
|
+
& .icon {
|
|
30
|
+
inset-block-start: -0.125em;
|
|
31
|
+
}
|
|
32
|
+
}
|
|
33
|
+
|
|
34
|
+
.badge--small {
|
|
35
|
+
font-size: 0.75rem;
|
|
36
|
+
padding-block-end: calc(var(--space-2xs) / 2 - 0.0625rem);
|
|
37
|
+
padding-block-start: calc(var(--space-2xs) / 2 + 0.0625rem);
|
|
38
|
+
padding-inline: var(--space-s);
|
|
39
|
+
}
|
|
40
|
+
|
|
41
|
+
.badge--green {
|
|
42
|
+
background: var(--color-green50);
|
|
43
|
+
color: var(--color-green10);
|
|
44
|
+
}
|
|
45
|
+
|
|
46
|
+
.badge--purple {
|
|
47
|
+
background: var(--color-purple45);
|
|
48
|
+
color: var(--color-neutral99);
|
|
49
|
+
}
|
|
50
|
+
|
|
51
|
+
.badge--red {
|
|
52
|
+
background: var(--color-red45);
|
|
53
|
+
color: var(--color-neutral99);
|
|
54
|
+
}
|
|
55
|
+
|
|
56
|
+
.badge--yellow {
|
|
57
|
+
background: var(--color-yellow50);
|
|
58
|
+
color: var(--color-neutral10);
|
|
59
|
+
}
|
|
60
|
+
|
|
61
|
+
.badge--offset {
|
|
62
|
+
background: var(--color-offset);
|
|
63
|
+
box-shadow: inset 0 0 0 1px var(--color-shadow);
|
|
64
|
+
color: var(--color-on-offset);
|
|
65
|
+
}
|
|
66
|
+
|
|
67
|
+
.badge--offset-green {
|
|
68
|
+
background: var(--color-green90);
|
|
69
|
+
color: var(--color-green10);
|
|
70
|
+
}
|
|
71
|
+
|
|
72
|
+
.badge--offset-purple {
|
|
73
|
+
background: var(--color-purple90);
|
|
74
|
+
color: var(--color-purple10);
|
|
75
|
+
}
|
|
76
|
+
|
|
77
|
+
.badge--offset-red {
|
|
78
|
+
background: var(--color-red90);
|
|
79
|
+
color: var(--color-red10);
|
|
80
|
+
}
|
|
81
|
+
|
|
82
|
+
.badge--offset-yellow {
|
|
83
|
+
background: var(--color-yellow90);
|
|
84
|
+
color: var(--color-yellow10);
|
|
85
|
+
}
|