@undrr/undrr-mangrove 2.0.0 → 2.1.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.
- package/README.md +9 -5
- package/components/BookCard.js +2 -2
- package/components/Breadcrumbs.js +2 -2
- package/components/Checkbox.js +2 -2
- package/components/Chips.js +2 -2
- package/components/CopyButton.js +2 -2
- package/components/CtaButton.js +2 -2
- package/components/Drawer.js +3 -3
- package/components/Drawer.js.LICENSE.txt +3 -1
- package/components/EmbedContainer.js +2 -2
- package/components/Footer.js +2 -2
- package/components/FormAction.js +2 -2
- package/components/FormErrorSummary.js +2 -2
- package/components/FormGroup.js +2 -2
- package/components/FullWidth.js +2 -2
- package/components/Gallery.js +3 -3
- package/components/Hero.js +3 -3
- package/components/HighlightBox.js +2 -2
- package/components/HorizontalBookCard.js +3 -3
- package/components/HorizontalBookCard.js.LICENSE.txt +3 -1
- package/components/HorizontalCard.js +3 -3
- package/components/HorizontalCard.js.LICENSE.txt +3 -1
- package/components/IconCard.js +3 -3
- package/components/IconCard.js.LICENSE.txt +3 -1
- package/components/Legend.js +2 -2
- package/components/Loader.js +3 -3
- package/components/MegaMenu.js +3 -3
- package/components/Notice.js +2 -2
- package/components/PageHeader.js +2 -2
- package/components/Pager.js +2 -2
- package/components/ProgressBar.js +9 -0
- package/components/ProgressBar.js.LICENSE.txt +9 -0
- package/components/QuoteHighlight.js +3 -3
- package/components/QuoteHighlight.js.LICENSE.txt +3 -1
- package/components/Radio.js +2 -2
- package/components/Range.js +2 -2
- package/components/ScrollContainer.js +2 -2
- package/components/SegmentedControl.js +2 -2
- package/components/Select.js +2 -2
- package/components/ServiceNotice.js +2 -2
- package/components/ShareButtons.js +3 -3
- package/components/ShowMore.js +3 -3
- package/components/SkipLink.js +2 -2
- package/components/StatsCard.js +3 -3
- package/components/StatsCard.js.LICENSE.txt +3 -1
- package/components/SyndicationSearchWidget.js +3 -3
- package/components/Tab.js +2 -2
- package/components/TextCta.js +3 -3
- package/components/TextCta.js.LICENSE.txt +3 -1
- package/components/TextInput.js +2 -2
- package/components/Textarea.js +2 -2
- package/components/Tree.js +2 -2
- package/components/UserFeedback.js +2 -2
- package/components/VerticalCard.js +3 -3
- package/components/VerticalCard.js.LICENSE.txt +3 -1
- package/components/hydrate.js +3 -3
- package/css/style-all.css +147 -128
- package/css/style-all.css.map +1 -1
- package/css/style-delta.css +147 -128
- package/css/style-delta.css.map +1 -1
- package/css/style-gutenberg.css +12 -12
- package/css/style-gutenberg.css.map +1 -1
- package/css/style-irp.css +147 -128
- package/css/style-irp.css.map +1 -1
- package/css/style-mcr.css +147 -128
- package/css/style-mcr.css.map +1 -1
- package/css/style-preventionweb.css +147 -128
- package/css/style-preventionweb.css.map +1 -1
- package/css/style.css +147 -128
- package/css/style.css.map +1 -1
- package/docs/EDITORIAL-MANUAL.md +193 -0
- package/docs/llms-editorial-manual.txt +200 -0
- package/docs/llms-motion.txt +125 -0
- package/docs/llms-page-building.txt +1140 -0
- package/docs/llms-search-widget.txt +765 -0
- package/error-pages/401.html +1 -1
- package/error-pages/403.html +1 -1
- package/error-pages/404.html +1 -1
- package/error-pages/429.html +1 -1
- package/error-pages/500.html +1 -1
- package/error-pages/502.html +1 -1
- package/error-pages/503.html +1 -1
- package/error-pages/504.html +1 -1
- package/error-pages/5xx.html +1 -1
- package/error-pages/challenge.html +1 -1
- package/error-pages/managed-challenge.html +1 -1
- package/js/cite-this.js +994 -0
- package/js/on-this-page-nav.js +80 -1
- package/js/show-more.js +149 -21
- package/package.json +6 -1
- package/scss/Atom/BaseTypography/Abbr/abbr.scss +1 -1
- package/scss/Atom/BaseTypography/Blockquote/blockquote.scss +1 -1
- package/scss/Atom/BaseTypography/Cite/cite.scss +1 -1
- package/scss/Atom/BaseTypography/Code/code.scss +1 -1
- package/scss/Atom/BaseTypography/Mark/mark.scss +1 -1
- package/scss/Atom/BaseTypography/Quotation/quotation.scss +1 -1
- package/scss/Atom/BaseTypography/Small/small.scss +1 -1
- package/scss/Atom/Colors/color.scss +1 -1
- package/scss/Atom/EmptyState/empty-state.scss +1 -1
- package/scss/Atom/Icons/_icon-definitions.scss +35 -3
- package/scss/Atom/Icons/icons.scss +1 -1
- package/scss/Atom/Images/AuthorImage/author-image.scss +10 -3
- package/scss/Atom/Images/Image/image.scss +1 -1
- package/scss/Atom/Images/ImageCaptionCredit/image-caption-credit.scss +7 -2
- package/scss/Atom/Images/ImageCredit/image-credit.scss +1 -1
- package/scss/Atom/Layout/Container/container.scss +1 -1
- package/scss/Atom/Layout/Grid/grid.scss +1 -1
- package/scss/Atom/Layout/Spacing/spacing.scss +1 -1
- package/scss/Atom/Logo/logo.scss +1 -1
- package/scss/Atom/Navigation/Breadcrumb/breadcrumb.scss +1 -1
- package/scss/Atom/Navigation/MenuItems/menu-items.scss +1 -1
- package/scss/Atom/ReachElement/Details/details.scss +5 -3
- package/scss/Atom/ReachElement/Figcaption/figcaption.scss +1 -1
- package/scss/Atom/StatusLabel/status-label.scss +1 -1
- package/scss/Atom/Table/table.scss +1 -1
- package/scss/Atom/Tag/tag.scss +1 -1
- package/scss/Atom/Video/video.scss +1 -1
- package/scss/Components/Boilerplate/boilerplate.scss +1 -1
- package/scss/Components/Breadcrumbs/breadcrumbs.scss +1 -1
- package/scss/Components/Buttons/Chips/chips.scss +1 -1
- package/scss/Components/Buttons/CopyButton/copy-button.scss +1 -1
- package/scss/Components/Buttons/CtaButton/buttons.scss +1 -1
- package/scss/Components/Buttons/CtaButton/cta-button.scss +1 -1
- package/scss/Components/Buttons/ShareButtons/share-buttons.scss +90 -1
- package/scss/Components/Cards/Card/card.scss +9 -3
- package/scss/Components/Cards/StatsCard/stats-card.scss +9 -2
- package/scss/Components/CiteThis/cite-this.scss +339 -0
- package/scss/Components/CookieConsentBanner/cookie-consent-banner.scss +1 -1
- package/scss/Components/DataViz/Legend/legend.scss +1 -1
- package/scss/Components/ErrorPages/error-pages.scss +1 -1
- package/scss/Components/Footer/footer.scss +1 -1
- package/scss/Components/Forms/Checkbox/checkbox.scss +1 -1
- package/scss/Components/Forms/FormAction/form-action.scss +1 -1
- package/scss/Components/Forms/FormGroup/form-group.scss +1 -1
- package/scss/Components/Forms/InputFields/input-fields.scss +1 -1
- package/scss/Components/Forms/Radio/radio.scss +1 -1
- package/scss/Components/Forms/Range/range.scss +1 -1
- package/scss/Components/Forms/SegmentedControl/segmented-control.scss +1 -1
- package/scss/Components/Forms/Select/select.scss +1 -1
- package/scss/Components/Forms/TextInput/text-input.scss +1 -1
- package/scss/Components/Forms/Textarea/textarea.scss +1 -1
- package/scss/Components/Forms/_form-base.scss +1 -1
- package/scss/Components/Gallery/gallery.scss +41 -16
- package/scss/Components/Hero/hero.scss +166 -1
- package/scss/Components/HighlightBox/highlight-box.scss +1 -1
- package/scss/Components/MegaMenu/mega-menu.scss +43 -122
- package/scss/Components/MegaMenu/megamenu.scss +1 -1
- package/scss/Components/Navigation/Drawer/drawer.scss +11 -1
- package/scss/Components/Navigation/Tree/tree.scss +1 -1
- package/scss/Components/Notice/notice.scss +1 -1
- package/scss/Components/OnThisPageNav/on-this-page-nav.scss +109 -4
- package/scss/Components/PageHeader/page-header.scss +1 -1
- package/scss/Components/Pager/pager.scss +1 -1
- package/scss/Components/PreviewAccess/preview-access.scss +1 -1
- package/scss/Components/ProgressBar/progress-bar.scss +215 -0
- package/scss/Components/QuoteHighlight/quote-highlight.scss +1 -1
- package/scss/Components/ScrollContainer/scroll-container.scss +1 -1
- package/scss/Components/Snackbar/snackbar.scss +1 -1
- package/scss/Components/SyndicationSearchWidget/_deprecated-teaser-hide.scss +1 -1
- package/scss/Components/SyndicationSearchWidget/syndication-search-widget.scss +253 -128
- package/scss/Components/Tab/tab.scss +3 -2
- package/scss/Components/TableOfContents/table-of-contents.scss +1 -1
- package/scss/Components/TextCta/text-cta.scss +1 -1
- package/scss/Components/TextCta/textcta.scss +1 -1
- package/scss/Components/UserFeedback/user-feedback.scss +1 -1
- package/scss/Molecules/ImageCaption/image-caption.scss +17 -3
- package/scss/Molecules/SectionHeader/section-header.scss +1 -1
- package/scss/Molecules/SectionHeader/sectionheader.scss +1 -1
- package/scss/Patterns/HubHeader/hub-header.scss +1 -1
- package/scss/Patterns/RichContent/rich-content.scss +177 -0
- package/scss/Patterns/_shared/pattern-demo.scss +6 -1
- package/scss/Utilities/EmbedContainer/embed-container.scss +1 -1
- package/scss/Utilities/FullWidth/full-width.scss +1 -1
- package/scss/Utilities/Loader/loader.scss +133 -12
- package/scss/Utilities/Normalize/normalize.scss +1 -1
- package/scss/Utilities/PagePatterns/page-patterns.scss +1 -1
- package/scss/Utilities/ShowMore/show-more.scss +7 -1
- package/scss/Utilities/SkipLink/skip-link.scss +1 -1
- package/scss/assets/scss/_components.scss +5 -0
- package/scss/assets/scss/_foundational.scss +23 -8
- package/scss/assets/scss/_mixins.scss +5 -0
- package/scss/assets/scss/_variables.scss +2 -2
package/js/on-this-page-nav.js
CHANGED
|
@@ -107,6 +107,7 @@ export function mgOnThisPageNav(scope) {
|
|
|
107
107
|
container._mgOnThisPageNavAbort = ac;
|
|
108
108
|
|
|
109
109
|
setupClickHandlers(container, ac.signal);
|
|
110
|
+
setupBlockSize(container, ac.signal);
|
|
110
111
|
setupScrollSpy(container);
|
|
111
112
|
setupFocusScrolling(container, ac.signal);
|
|
112
113
|
setupScrollButtons(container, ac.signal);
|
|
@@ -132,13 +133,53 @@ export function mgOnThisPageNavDestroy(container) {
|
|
|
132
133
|
container._mgOnThisPageNavResizeObserver.disconnect();
|
|
133
134
|
delete container._mgOnThisPageNavResizeObserver;
|
|
134
135
|
}
|
|
136
|
+
if (container._mgOnThisPageNavSizeObserver) {
|
|
137
|
+
container._mgOnThisPageNavSizeObserver.disconnect();
|
|
138
|
+
delete container._mgOnThisPageNavSizeObserver;
|
|
139
|
+
document.documentElement.style.removeProperty(BLOCK_SIZE);
|
|
140
|
+
}
|
|
135
141
|
container
|
|
136
142
|
.querySelectorAll('.mg-on-this-page-nav__scroll-btn')
|
|
137
143
|
.forEach(btn => btn.remove());
|
|
138
|
-
container.classList.remove(
|
|
144
|
+
container.classList.remove(
|
|
145
|
+
'mg-on-this-page-nav--has-left-overflow',
|
|
146
|
+
'mg-on-this-page-nav--has-right-overflow'
|
|
147
|
+
);
|
|
139
148
|
delete container.dataset.mgOnThisPageNavInitialized;
|
|
140
149
|
}
|
|
141
150
|
|
|
151
|
+
const BLOCK_SIZE = '--mg-on-this-page-nav-block-size';
|
|
152
|
+
|
|
153
|
+
/**
|
|
154
|
+
* Publishes the bar's height on the root element while it is sticky, and 0px
|
|
155
|
+
* when it is not (it un-sticks on short viewports). The stylesheet adds it to
|
|
156
|
+
* `scroll-padding-top`, so anything the browser scrolls into view (focus,
|
|
157
|
+
* anchors, scrollIntoView from other components) lands below the bar rather
|
|
158
|
+
* than under it.
|
|
159
|
+
*
|
|
160
|
+
* @param {HTMLElement} container - The nav element
|
|
161
|
+
* @param {AbortSignal} signal - Removes the resize listener on destroy
|
|
162
|
+
*/
|
|
163
|
+
function setupBlockSize(container, signal) {
|
|
164
|
+
const root = document.documentElement;
|
|
165
|
+
const publish = () => {
|
|
166
|
+
const sticky = getComputedStyle(container).position === 'sticky';
|
|
167
|
+
root.style.setProperty(
|
|
168
|
+
BLOCK_SIZE,
|
|
169
|
+
`${sticky ? container.offsetHeight || 0 : 0}px`
|
|
170
|
+
);
|
|
171
|
+
};
|
|
172
|
+
publish();
|
|
173
|
+
window.addEventListener('resize', publish, { passive: true, signal });
|
|
174
|
+
if (typeof ResizeObserver === 'function') {
|
|
175
|
+
const observer = new ResizeObserver(publish);
|
|
176
|
+
observer.observe(container);
|
|
177
|
+
container._mgOnThisPageNavSizeObserver = observer;
|
|
178
|
+
} else {
|
|
179
|
+
container._mgOnThisPageNavSizeObserver = { disconnect() {} };
|
|
180
|
+
}
|
|
181
|
+
}
|
|
182
|
+
|
|
142
183
|
/**
|
|
143
184
|
* Auto-detect mode: scan headings from the page and generate nav links.
|
|
144
185
|
* Preserves any existing CTA element in the container.
|
|
@@ -399,6 +440,13 @@ function updateScrollButtons(container, list, prevBtn, nextBtn) {
|
|
|
399
440
|
'mg-on-this-page-nav--has-left-overflow',
|
|
400
441
|
rtl ? canScrollFurther : scrolledFromStart
|
|
401
442
|
);
|
|
443
|
+
// has-right-overflow is its mirror. Only the RTL fades read it: in RTL the
|
|
444
|
+
// hidden content can sit on either physical side, and a fade belongs only
|
|
445
|
+
// on a side with something hidden behind it.
|
|
446
|
+
container.classList.toggle(
|
|
447
|
+
'mg-on-this-page-nav--has-right-overflow',
|
|
448
|
+
rtl ? scrolledFromStart : canScrollFurther
|
|
449
|
+
);
|
|
402
450
|
}
|
|
403
451
|
|
|
404
452
|
/**
|
|
@@ -543,6 +591,15 @@ function setupScrollSpy(container) {
|
|
|
543
591
|
if (targets.length === 0) return;
|
|
544
592
|
|
|
545
593
|
let activeId = null;
|
|
594
|
+
|
|
595
|
+
// At the foot of a page that scrolls a real distance. On a page that barely
|
|
596
|
+
// scrolls, the bottom is also the top, and the first section is right.
|
|
597
|
+
const atFoot = () => {
|
|
598
|
+
const doc = document.documentElement;
|
|
599
|
+
const scrollable = doc.scrollHeight - window.innerHeight;
|
|
600
|
+
const minimum = Math.max(120, window.innerHeight * 0.25);
|
|
601
|
+
return scrollable >= minimum && window.scrollY >= scrollable - 2;
|
|
602
|
+
};
|
|
546
603
|
// Track which targets are currently intersecting (avoids DOM expando properties)
|
|
547
604
|
const intersecting = new Set();
|
|
548
605
|
|
|
@@ -584,6 +641,13 @@ function setupScrollSpy(container) {
|
|
|
584
641
|
}
|
|
585
642
|
});
|
|
586
643
|
|
|
644
|
+
// At the foot of the page the last section wins (see onScroll). The
|
|
645
|
+
// observer reports after the scroll event, so without this check it
|
|
646
|
+
// would take the mark straight back.
|
|
647
|
+
if (atFoot()) {
|
|
648
|
+
setActive(targets[targets.length - 1].id);
|
|
649
|
+
return;
|
|
650
|
+
}
|
|
587
651
|
// Pick the first intersecting target in DOM order
|
|
588
652
|
const firstVisible = targets.find(t => intersecting.has(t));
|
|
589
653
|
if (firstVisible) {
|
|
@@ -599,12 +663,27 @@ function setupScrollSpy(container) {
|
|
|
599
663
|
targets.forEach(target => observer.observe(target));
|
|
600
664
|
container._mgOnThisPageNavObserver = observer;
|
|
601
665
|
|
|
666
|
+
// A short last section can never scroll up into the observed band, so at
|
|
667
|
+
// the foot of the page the previous section stayed marked, even straight
|
|
668
|
+
// after following the last link. At the bottom, mark the last target. Only
|
|
669
|
+
// on pages that scroll a real distance: on one that barely scrolls, the
|
|
670
|
+
// bottom is also the top, and the first section is the right answer.
|
|
671
|
+
const onScroll = () => {
|
|
672
|
+
if (atFoot()) setActive(targets[targets.length - 1].id);
|
|
673
|
+
};
|
|
674
|
+
window.addEventListener('scroll', onScroll, {
|
|
675
|
+
passive: true,
|
|
676
|
+
signal: container._mgOnThisPageNavAbort?.signal,
|
|
677
|
+
});
|
|
678
|
+
|
|
602
679
|
const hashId = window.location.hash ? window.location.hash.slice(1) : null;
|
|
603
680
|
if (hashId && linkMap.has(hashId)) {
|
|
604
681
|
setActive(hashId);
|
|
605
682
|
} else if (targets.length > 0) {
|
|
606
683
|
setActive(targets[0].id);
|
|
607
684
|
}
|
|
685
|
+
// A page restored at its foot (reload, back button) is checked straight away.
|
|
686
|
+
onScroll();
|
|
608
687
|
}
|
|
609
688
|
|
|
610
689
|
// Auto-wrap so the browser Event object is not passed as scope
|
package/js/show-more.js
CHANGED
|
@@ -61,6 +61,58 @@ function resolveTarget(toggle, selector) {
|
|
|
61
61
|
return document.querySelector(selector);
|
|
62
62
|
}
|
|
63
63
|
|
|
64
|
+
/**
|
|
65
|
+
* The height the content collapses to, read from CSS: the computed
|
|
66
|
+
* max-height of the collapsed state, so `--mg-show-more-height` may be set in
|
|
67
|
+
* any unit, including `lh`. Applying and removing the class in one task
|
|
68
|
+
* forces a style recalculation but never paints.
|
|
69
|
+
*
|
|
70
|
+
* @param {HTMLElement} target - The collapsible content.
|
|
71
|
+
* @returns {number} Pixels, or NaN when CSS gives no length.
|
|
72
|
+
*/
|
|
73
|
+
function collapsedHeight(target) {
|
|
74
|
+
const collapsed = target.classList.contains('mg-show-more--collapsed');
|
|
75
|
+
if (!collapsed) target.classList.add('mg-show-more--collapsed');
|
|
76
|
+
const height = parseFloat(getComputedStyle(target).maxHeight);
|
|
77
|
+
if (!collapsed) target.classList.remove('mg-show-more--collapsed');
|
|
78
|
+
return height;
|
|
79
|
+
}
|
|
80
|
+
|
|
81
|
+
/**
|
|
82
|
+
* @param {HTMLElement} target - The collapsible content.
|
|
83
|
+
* @returns {number} Its line height in pixels.
|
|
84
|
+
*/
|
|
85
|
+
function lineHeight(target) {
|
|
86
|
+
const style = getComputedStyle(target);
|
|
87
|
+
const line = parseFloat(style.lineHeight);
|
|
88
|
+
return Number.isFinite(line) ? line : parseFloat(style.fontSize) * 1.2;
|
|
89
|
+
}
|
|
90
|
+
|
|
91
|
+
/**
|
|
92
|
+
* After a reader collapses content, bring the start of it back into view if
|
|
93
|
+
* the toggle has left the viewport. Scrolls the heading just before the
|
|
94
|
+
* content when there is one, honours scroll-padding (so a sticky bar such as
|
|
95
|
+
* On this page is allowed for) and reduced motion.
|
|
96
|
+
*
|
|
97
|
+
* @param {HTMLElement} toggle - The toggle that was used.
|
|
98
|
+
* @param {HTMLElement} target - The content it collapsed.
|
|
99
|
+
*/
|
|
100
|
+
function returnToContent(toggle, target) {
|
|
101
|
+
const box = toggle.getBoundingClientRect();
|
|
102
|
+
if (box.bottom > 0 && box.top < window.innerHeight) return;
|
|
103
|
+
const previous = target.previousElementSibling;
|
|
104
|
+
const anchor = previous?.matches('h1, h2, h3, h4, h5, h6')
|
|
105
|
+
? previous
|
|
106
|
+
: target;
|
|
107
|
+
const reduce =
|
|
108
|
+
typeof window.matchMedia === 'function' &&
|
|
109
|
+
window.matchMedia('(prefers-reduced-motion: reduce)').matches;
|
|
110
|
+
anchor.scrollIntoView?.({
|
|
111
|
+
block: 'start',
|
|
112
|
+
behavior: reduce ? 'auto' : 'smooth',
|
|
113
|
+
});
|
|
114
|
+
}
|
|
115
|
+
|
|
64
116
|
/**
|
|
65
117
|
* Initializes "show more" toggle buttons.
|
|
66
118
|
*
|
|
@@ -102,7 +154,6 @@ export function mgShowMore(scope) {
|
|
|
102
154
|
'mg-show-more--collapsed'
|
|
103
155
|
);
|
|
104
156
|
const wasOpen = item.classList.contains('mg-show-more--button--open');
|
|
105
|
-
const initialText = item.textContent;
|
|
106
157
|
const initialControls = item.getAttribute('aria-controls');
|
|
107
158
|
const initialRole = item.getAttribute('role');
|
|
108
159
|
const onKeydown = event => {
|
|
@@ -112,8 +163,27 @@ export function mgShowMore(scope) {
|
|
|
112
163
|
}
|
|
113
164
|
};
|
|
114
165
|
|
|
115
|
-
|
|
116
|
-
|
|
166
|
+
// The click tracker reads data-vf-analytics-label. Report the action the
|
|
167
|
+
// toggle is about to perform, in fixed English so reports do not split by
|
|
168
|
+
// language. A label the author set by hand is kept as it is, unless
|
|
169
|
+
// per-state labels are given.
|
|
170
|
+
const COLLAPSED = 'mg-show-more--collapsed';
|
|
171
|
+
const authorLabel = item.getAttribute('data-vf-analytics-label');
|
|
172
|
+
const { mgShowMoreAnalyticsCollapsed, mgShowMoreAnalyticsOpen } =
|
|
173
|
+
item.dataset;
|
|
174
|
+
const stateLabels =
|
|
175
|
+
mgShowMoreAnalyticsCollapsed || mgShowMoreAnalyticsOpen || !authorLabel
|
|
176
|
+
? {
|
|
177
|
+
collapsed: mgShowMoreAnalyticsCollapsed || 'Show more',
|
|
178
|
+
open: mgShowMoreAnalyticsOpen || 'Show less',
|
|
179
|
+
}
|
|
180
|
+
: null;
|
|
181
|
+
|
|
182
|
+
// Visible text lives in a [data-mg-show-more-label] child when there is
|
|
183
|
+
// one, so visually hidden context beside it survives each toggle.
|
|
184
|
+
const labelNode = item.querySelector('[data-mg-show-more-label]') || item;
|
|
185
|
+
const initialText = labelNode.textContent;
|
|
186
|
+
const initialHidden = item.hidden;
|
|
117
187
|
|
|
118
188
|
// Relate the toggle to the content it acts on. A <button> already
|
|
119
189
|
// announces as a button; an anchor copied from an earlier version of the
|
|
@@ -131,24 +201,35 @@ export function mgShowMore(scope) {
|
|
|
131
201
|
item.addEventListener('keydown', onKeydown);
|
|
132
202
|
}
|
|
133
203
|
|
|
134
|
-
|
|
135
|
-
|
|
136
|
-
|
|
137
|
-
|
|
138
|
-
|
|
139
|
-
|
|
140
|
-
|
|
141
|
-
'mg-show-more--collapsed'
|
|
142
|
-
)
|
|
204
|
+
// Initialisation and re-measures change state here rather than through
|
|
205
|
+
// item.click(), so they reach no click listener (analytics reporting, the
|
|
206
|
+
// Drupal wrapper). Focus entering, or a click on, collapsed content still
|
|
207
|
+
// clicks the toggle below: those stand for a reader's action.
|
|
208
|
+
const setCollapsed = collapsed => {
|
|
209
|
+
mgShowMoreTarget.classList.toggle(COLLAPSED, collapsed);
|
|
210
|
+
labelNode.textContent = collapsed
|
|
143
211
|
? item.dataset.mgShowMoreLabelCollapsed || 'Show more'
|
|
144
212
|
: item.dataset.mgShowMoreLabelOpen || 'Show less';
|
|
145
|
-
|
|
146
|
-
if (
|
|
147
|
-
item.
|
|
148
|
-
|
|
149
|
-
|
|
213
|
+
item.classList.toggle('mg-show-more--button--open', !collapsed);
|
|
214
|
+
if (stateLabels) {
|
|
215
|
+
item.setAttribute(
|
|
216
|
+
'data-vf-analytics-label',
|
|
217
|
+
collapsed ? stateLabels.collapsed : stateLabels.open
|
|
218
|
+
);
|
|
150
219
|
}
|
|
151
220
|
};
|
|
221
|
+
|
|
222
|
+
let readerToggled = false;
|
|
223
|
+
const onClick = event => {
|
|
224
|
+
// Also neutralises the dead `href="#"` on a legacy anchor toggle.
|
|
225
|
+
event.preventDefault();
|
|
226
|
+
readerToggled = true;
|
|
227
|
+
const collapsing = !mgShowMoreTarget.classList.contains(COLLAPSED);
|
|
228
|
+
setCollapsed(collapsing);
|
|
229
|
+
// Collapsing a long block pulls the toggle up the page, often out of
|
|
230
|
+
// view. Bring the reader back to the start of what they collapsed.
|
|
231
|
+
if (collapsing) returnToContent(item, mgShowMoreTarget);
|
|
232
|
+
};
|
|
152
233
|
item.addEventListener('click', onClick);
|
|
153
234
|
|
|
154
235
|
// The collapse is `max-height` + `overflow: hidden`, which clips content
|
|
@@ -158,7 +239,7 @@ export function mgShowMore(scope) {
|
|
|
158
239
|
// entry keeps the focused control visible.
|
|
159
240
|
const onFocusin = event => {
|
|
160
241
|
if (item === event.target || item.contains(event.target)) return;
|
|
161
|
-
if (mgShowMoreTarget.classList.contains(
|
|
242
|
+
if (mgShowMoreTarget.classList.contains(COLLAPSED)) {
|
|
162
243
|
item.click();
|
|
163
244
|
}
|
|
164
245
|
};
|
|
@@ -167,14 +248,61 @@ export function mgShowMore(scope) {
|
|
|
167
248
|
// Allow items to be shown by clicking anywhere on the collapsed item
|
|
168
249
|
// https://gitlab.com/undrr/web-backlog/-/issues/1612
|
|
169
250
|
const onTargetClick = () => {
|
|
170
|
-
if (mgShowMoreTarget.classList.contains(
|
|
251
|
+
if (mgShowMoreTarget.classList.contains(COLLAPSED)) {
|
|
171
252
|
item.click();
|
|
172
253
|
}
|
|
173
254
|
};
|
|
174
255
|
mgShowMoreTarget.addEventListener('click', onTargetClick);
|
|
175
256
|
|
|
176
|
-
|
|
257
|
+
// A template may ship the toggle `hidden` so it never shows without
|
|
258
|
+
// JavaScript; the content is then simply open.
|
|
259
|
+
item.hidden = false;
|
|
260
|
+
setCollapsed(!wasCollapsed);
|
|
261
|
+
|
|
262
|
+
// Opt-in: collapse only when enough would be hidden. Short content stays
|
|
263
|
+
// open and the toggle is hidden, so a template can wrap every body field
|
|
264
|
+
// in ShowMore. The value is a number of lines (empty means 1): collapse
|
|
265
|
+
// when the content runs at least that many lines past the collapsed
|
|
266
|
+
// height. The collapsed height is read from CSS (--mg-show-more-height),
|
|
267
|
+
// so the decision does not depend on the current state and cannot flip
|
|
268
|
+
// back and forth. Measured again when the content resizes, until the
|
|
269
|
+
// reader uses the toggle. Content with no layout yet (inside a closed
|
|
270
|
+
// tab, say) waits until it has one.
|
|
271
|
+
let observer = null;
|
|
272
|
+
let frame = 0;
|
|
273
|
+
if (item.hasAttribute('data-mg-show-more-min-hidden-lines')) {
|
|
274
|
+
const lines =
|
|
275
|
+
parseFloat(item.dataset.mgShowMoreMinHiddenLines) > 0
|
|
276
|
+
? parseFloat(item.dataset.mgShowMoreMinHiddenLines)
|
|
277
|
+
: 1;
|
|
278
|
+
const measure = () => {
|
|
279
|
+
frame = 0;
|
|
280
|
+
if (readerToggled || mgShowMoreTarget.scrollHeight === 0) return;
|
|
281
|
+
const limit = collapsedHeight(mgShowMoreTarget);
|
|
282
|
+
const line = lineHeight(mgShowMoreTarget);
|
|
283
|
+
if (!Number.isFinite(limit) || !Number.isFinite(line)) return;
|
|
284
|
+
const collapse = mgShowMoreTarget.scrollHeight - limit >= lines * line;
|
|
285
|
+
setCollapsed(collapse);
|
|
286
|
+
item.hidden = !collapse;
|
|
287
|
+
};
|
|
288
|
+
measure();
|
|
289
|
+
if (typeof ResizeObserver === 'function') {
|
|
290
|
+
// Deferred to the next frame: changing the observed box inside the
|
|
291
|
+
// callback is what raises "ResizeObserver loop" errors.
|
|
292
|
+
observer = new ResizeObserver(() => {
|
|
293
|
+
if (frame) cancelAnimationFrame(frame);
|
|
294
|
+
frame = requestAnimationFrame(measure);
|
|
295
|
+
});
|
|
296
|
+
observer.observe(mgShowMoreTarget);
|
|
297
|
+
}
|
|
298
|
+
}
|
|
299
|
+
|
|
177
300
|
cleanups.push(() => {
|
|
301
|
+
observer?.disconnect();
|
|
302
|
+
if (frame) cancelAnimationFrame(frame);
|
|
303
|
+
item.hidden = initialHidden;
|
|
304
|
+
if (authorLabel === null) item.removeAttribute('data-vf-analytics-label');
|
|
305
|
+
else item.setAttribute('data-vf-analytics-label', authorLabel);
|
|
178
306
|
item.removeEventListener('click', onClick);
|
|
179
307
|
item.removeEventListener('keydown', onKeydown);
|
|
180
308
|
mgShowMoreTarget.removeEventListener('focusin', onFocusin);
|
|
@@ -184,7 +312,7 @@ export function mgShowMore(scope) {
|
|
|
184
312
|
wasCollapsed
|
|
185
313
|
);
|
|
186
314
|
item.classList.toggle('mg-show-more--button--open', wasOpen);
|
|
187
|
-
|
|
315
|
+
labelNode.textContent = initialText;
|
|
188
316
|
for (const [attribute, value] of [
|
|
189
317
|
['aria-controls', initialControls],
|
|
190
318
|
['role', initialRole],
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@undrr/undrr-mangrove",
|
|
3
|
-
"version": "2.
|
|
3
|
+
"version": "2.1.0",
|
|
4
4
|
"description": "Mangrove design System for UNDRR",
|
|
5
5
|
"files": [
|
|
6
6
|
"components/**/*",
|
|
@@ -9,6 +9,7 @@
|
|
|
9
9
|
"scss/**/*.scss",
|
|
10
10
|
"error-pages/**/*",
|
|
11
11
|
"fonts/**/*",
|
|
12
|
+
"docs/**/*",
|
|
12
13
|
"!**/__tests__/**",
|
|
13
14
|
"!**/__snapshots__/**",
|
|
14
15
|
"!**/__mocks__/**",
|
|
@@ -20,6 +21,10 @@
|
|
|
20
21
|
"type": "git",
|
|
21
22
|
"url": "https://github.com/unisdr/undrr-mangrove.git"
|
|
22
23
|
},
|
|
24
|
+
"homepage": "https://mangrove.undrr.org/",
|
|
25
|
+
"bugs": {
|
|
26
|
+
"url": "https://github.com/PreventionWeb/undrr-mangrove/issues"
|
|
27
|
+
},
|
|
23
28
|
"keywords": [],
|
|
24
29
|
"author": "",
|
|
25
30
|
"license": "Apache-2.0"
|
|
@@ -4,7 +4,7 @@
|
|
|
4
4
|
* Styles for HTML <abbr> elements with subtle dotted underlines and accessible expansion styling.
|
|
5
5
|
*
|
|
6
6
|
* Full documentation:
|
|
7
|
-
* https://github.com/
|
|
7
|
+
* https://github.com/PreventionWeb/undrr-mangrove/blob/main/stories/Atom/BaseTypography/BaseTypography.mdx
|
|
8
8
|
*/
|
|
9
9
|
abbr[title] {
|
|
10
10
|
border-bottom: 2px dashed rgb(var(--mg-color-red-900));
|
|
@@ -4,7 +4,7 @@
|
|
|
4
4
|
* Typography and border accent styles for standard HTML <blockquote> elements.
|
|
5
5
|
*
|
|
6
6
|
* Full documentation:
|
|
7
|
-
* https://github.com/
|
|
7
|
+
* https://github.com/PreventionWeb/undrr-mangrove/blob/main/stories/Atom/BaseTypography/BaseTypography.mdx
|
|
8
8
|
*/
|
|
9
9
|
.mg-body blockquote,
|
|
10
10
|
.mg-content blockquote {
|
|
@@ -4,7 +4,7 @@
|
|
|
4
4
|
* Typographic styles for HTML <cite> citation references.
|
|
5
5
|
*
|
|
6
6
|
* Full documentation:
|
|
7
|
-
* https://github.com/
|
|
7
|
+
* https://github.com/PreventionWeb/undrr-mangrove/blob/main/stories/Atom/BaseTypography/BaseTypography.mdx
|
|
8
8
|
*/
|
|
9
9
|
.mg-body cite,
|
|
10
10
|
.mg-content cite {
|
|
@@ -4,7 +4,7 @@
|
|
|
4
4
|
* Monospace typographic styling for inline <code> elements.
|
|
5
5
|
*
|
|
6
6
|
* Full documentation:
|
|
7
|
-
* https://github.com/
|
|
7
|
+
* https://github.com/PreventionWeb/undrr-mangrove/blob/main/stories/Atom/BaseTypography/BaseTypography.mdx
|
|
8
8
|
*/
|
|
9
9
|
.mg-code,
|
|
10
10
|
code {
|
|
@@ -4,7 +4,7 @@
|
|
|
4
4
|
* Highlight styling for HTML <mark> elements using theme-aware highlight colors.
|
|
5
5
|
*
|
|
6
6
|
* Full documentation:
|
|
7
|
-
* https://github.com/
|
|
7
|
+
* https://github.com/PreventionWeb/undrr-mangrove/blob/main/stories/Atom/BaseTypography/BaseTypography.mdx
|
|
8
8
|
*/
|
|
9
9
|
mark {
|
|
10
10
|
background: var(--mg-color-yellow-light);
|
|
@@ -4,7 +4,7 @@
|
|
|
4
4
|
* Inline quotation typography and glyph styles for <q> elements.
|
|
5
5
|
*
|
|
6
6
|
* Full documentation:
|
|
7
|
-
* https://github.com/
|
|
7
|
+
* https://github.com/PreventionWeb/undrr-mangrove/blob/main/stories/Atom/BaseTypography/BaseTypography.mdx
|
|
8
8
|
*/
|
|
9
9
|
q {
|
|
10
10
|
font-style: italic;
|
|
@@ -4,7 +4,7 @@
|
|
|
4
4
|
* Reduced scale typography styles for fine print and secondary metadata (<small>).
|
|
5
5
|
*
|
|
6
6
|
* Full documentation:
|
|
7
|
-
* https://github.com/
|
|
7
|
+
* https://github.com/PreventionWeb/undrr-mangrove/blob/main/stories/Atom/BaseTypography/BaseTypography.mdx
|
|
8
8
|
*/
|
|
9
9
|
small {
|
|
10
10
|
@extend %paragraph-font-100;
|
|
@@ -4,6 +4,6 @@
|
|
|
4
4
|
* Color swatch and background/text utility helper classes across brand palettes.
|
|
5
5
|
*
|
|
6
6
|
* Full documentation:
|
|
7
|
-
* https://github.com/
|
|
7
|
+
* https://github.com/PreventionWeb/undrr-mangrove/blob/main/stories/Atom/Colors/color.mdx
|
|
8
8
|
*/
|
|
9
9
|
// empty
|
|
@@ -4,7 +4,7 @@
|
|
|
4
4
|
* Placeholder presentation for empty search results, missing data, or filtered-out views.
|
|
5
5
|
*
|
|
6
6
|
* Full documentation:
|
|
7
|
-
* https://github.com/
|
|
7
|
+
* https://github.com/PreventionWeb/undrr-mangrove/blob/main/stories/Atom/EmptyState/EmptyState.mdx
|
|
8
8
|
*/
|
|
9
9
|
// Empty state — what a list, table, chart or dashboard tile shows when it has
|
|
10
10
|
// no content to show.
|
|
@@ -5,10 +5,10 @@
|
|
|
5
5
|
* Generated by scripts/icon-build.cjs — do not edit by hand.
|
|
6
6
|
*
|
|
7
7
|
* Full documentation:
|
|
8
|
-
* https://github.com/
|
|
8
|
+
* https://github.com/PreventionWeb/undrr-mangrove/blob/main/stories/Atom/Icons/Icons.mdx
|
|
9
9
|
*/
|
|
10
10
|
// To regenerate: yarn build:icons
|
|
11
|
-
//
|
|
11
|
+
// 106 icons from Lucide, OCHA, and custom SVG sources.
|
|
12
12
|
|
|
13
13
|
.mg-icon-globe::before {
|
|
14
14
|
--mg-icon-svg: url("data:image/svg+xml,<svg xmlns='http://www.w3.org/2000/svg' fill='none' stroke='currentColor' stroke-linecap='round' stroke-linejoin='round' stroke-width='2' viewBox='0 0 24 24'><circle cx='12' cy='12' r='10'/><path d='M12 2a14.5 14.5 0 0 0 0 20 14.5 14.5 0 0 0 0-20M2 12h20'/></svg>");
|
|
@@ -55,7 +55,7 @@
|
|
|
55
55
|
}
|
|
56
56
|
|
|
57
57
|
.mg-icon-pen-nib::before {
|
|
58
|
-
--mg-icon-svg: url("data:image/svg+xml,<svg xmlns='http://www.w3.org/2000/svg' fill='none' stroke='currentColor' stroke-linecap='round' stroke-linejoin='round' stroke-width='2' viewBox='0 0 24 24'><path d='
|
|
58
|
+
--mg-icon-svg: url("data:image/svg+xml,<svg xmlns='http://www.w3.org/2000/svg' fill='none' stroke='currentColor' stroke-linecap='round' stroke-linejoin='round' stroke-width='2' viewBox='0 0 24 24'><path d='m18 13-.654-4.736a4 4 0 0 0-2.756-3.266l-9.163-2.9a2 2 0 0 0-2.017.493l-.82.819a2 2 0 0 0-.492 2.017l2.9 9.163a4 4 0 0 0 3.266 2.756L13 18'/><path d='M18.648 12.352a1.205 1.205 0 0 1 1.704 0l1.296 1.296a1.205 1.205 0 0 1 0 1.704l-6.296 6.296a1.205 1.205 0 0 1-1.704 0l-1.296-1.296a1.205 1.205 0 0 1 0-1.704zM3 3l6.586 6.586'/><circle cx='11' cy='11' r='2'/></svg>");
|
|
59
59
|
}
|
|
60
60
|
|
|
61
61
|
.mg-icon-code-branch::before {
|
|
@@ -126,6 +126,38 @@
|
|
|
126
126
|
--mg-icon-svg: url("data:image/svg+xml,<svg xmlns='http://www.w3.org/2000/svg' fill='none' stroke='currentColor' stroke-linecap='round' stroke-linejoin='round' stroke-width='2' viewBox='0 0 24 24'><path d='M3 12a9 9 0 0 1 9-9 9.75 9.75 0 0 1 6.74 2.74L21 8'/><path d='M21 3v5h-5M21 12a9 9 0 0 1-9 9 9.75 9.75 0 0 1-6.74-2.74L3 16'/><path d='M8 16H3v5'/></svg>");
|
|
127
127
|
}
|
|
128
128
|
|
|
129
|
+
.mg-icon-plus::before {
|
|
130
|
+
--mg-icon-svg: url("data:image/svg+xml,<svg xmlns='http://www.w3.org/2000/svg' fill='none' stroke='currentColor' stroke-linecap='round' stroke-linejoin='round' stroke-width='2' viewBox='0 0 24 24'><path d='M5 12h14M12 5v14'/></svg>");
|
|
131
|
+
}
|
|
132
|
+
|
|
133
|
+
.mg-icon-minus::before {
|
|
134
|
+
--mg-icon-svg: url("data:image/svg+xml,<svg xmlns='http://www.w3.org/2000/svg' fill='none' stroke='currentColor' stroke-linecap='round' stroke-linejoin='round' stroke-width='2' viewBox='0 0 24 24'><path d='M5 12h14'/></svg>");
|
|
135
|
+
}
|
|
136
|
+
|
|
137
|
+
.mg-icon-pause::before {
|
|
138
|
+
--mg-icon-svg: url("data:image/svg+xml,<svg xmlns='http://www.w3.org/2000/svg' fill='none' stroke='currentColor' stroke-linecap='round' stroke-linejoin='round' stroke-width='2' viewBox='0 0 24 24'><rect width='5' height='18' x='14' y='3' rx='1'/><rect width='5' height='18' x='5' y='3' rx='1'/></svg>");
|
|
139
|
+
}
|
|
140
|
+
|
|
141
|
+
.mg-icon-play::before {
|
|
142
|
+
--mg-icon-svg: url("data:image/svg+xml,<svg xmlns='http://www.w3.org/2000/svg' fill='none' stroke='currentColor' stroke-linecap='round' stroke-linejoin='round' stroke-width='2' viewBox='0 0 24 24'><path d='M5 5a2 2 0 0 1 3.008-1.728l11.997 6.998a2 2 0 0 1 .003 3.458l-12 7A2 2 0 0 1 5 19z'/></svg>");
|
|
143
|
+
}
|
|
144
|
+
|
|
145
|
+
.mg-icon-circle-minus::before {
|
|
146
|
+
--mg-icon-svg: url("data:image/svg+xml,<svg xmlns='http://www.w3.org/2000/svg' fill='none' stroke='currentColor' stroke-linecap='round' stroke-linejoin='round' stroke-width='2' viewBox='0 0 24 24'><circle cx='12' cy='12' r='10'/><path d='M8 12h8'/></svg>");
|
|
147
|
+
}
|
|
148
|
+
|
|
149
|
+
.mg-icon-expand::before {
|
|
150
|
+
--mg-icon-svg: url("data:image/svg+xml,<svg xmlns='http://www.w3.org/2000/svg' fill='none' stroke='currentColor' stroke-linecap='round' stroke-linejoin='round' stroke-width='2' viewBox='0 0 24 24'><path d='m15 15 6 6M15 9l6-6M21 16v5h-5M21 8V3h-5M3 16v5h5M3 21l6-6M3 8V3h5M9 9 3 3'/></svg>");
|
|
151
|
+
}
|
|
152
|
+
|
|
153
|
+
.mg-icon-shrink::before {
|
|
154
|
+
--mg-icon-svg: url("data:image/svg+xml,<svg xmlns='http://www.w3.org/2000/svg' fill='none' stroke='currentColor' stroke-linecap='round' stroke-linejoin='round' stroke-width='2' viewBox='0 0 24 24'><path d='m15 15 6 6m-6-6v4.8m0-4.8h4.8M9 19.8V15m0 0H4.2M9 15l-6 6M15 4.2V9m0 0h4.8M15 9l6-6M9 4.2V9m0 0H4.2M9 9 3 3'/></svg>");
|
|
155
|
+
}
|
|
156
|
+
|
|
157
|
+
.mg-icon-layers::before {
|
|
158
|
+
--mg-icon-svg: url("data:image/svg+xml,<svg xmlns='http://www.w3.org/2000/svg' fill='none' stroke='currentColor' stroke-linecap='round' stroke-linejoin='round' stroke-width='2' viewBox='0 0 24 24'><path d='M12.83 2.18a2 2 0 0 0-1.66 0L2.6 6.08a1 1 0 0 0 0 1.83l8.58 3.91a2 2 0 0 0 1.66 0l8.58-3.9a1 1 0 0 0 0-1.83z'/><path d='M2 12a1 1 0 0 0 .58.91l8.6 3.91a2 2 0 0 0 1.65 0l8.58-3.9A1 1 0 0 0 22 12'/><path d='M2 17a1 1 0 0 0 .58.91l8.6 3.91a2 2 0 0 0 1.65 0l8.58-3.9A1 1 0 0 0 22 17'/></svg>");
|
|
159
|
+
}
|
|
160
|
+
|
|
129
161
|
.mg-icon-clone::before {
|
|
130
162
|
--mg-icon-svg: url("data:image/svg+xml,<svg xmlns='http://www.w3.org/2000/svg' fill='none' stroke='currentColor' stroke-linecap='round' stroke-linejoin='round' stroke-width='2' viewBox='0 0 24 24'><rect width='14' height='14' x='8' y='8' rx='2' ry='2'/><path d='M4 16c-1.1 0-2-.9-2-2V4c0-1.1.9-2 2-2h10c1.1 0 2 .9 2 2'/></svg>");
|
|
131
163
|
}
|
|
@@ -4,7 +4,7 @@
|
|
|
4
4
|
* Base styles, icon sizing, font-family setup, and alignment classes for Mangrove icons.
|
|
5
5
|
*
|
|
6
6
|
* Full documentation:
|
|
7
|
-
* https://github.com/
|
|
7
|
+
* https://github.com/PreventionWeb/undrr-mangrove/blob/main/stories/Atom/Icons/Icons.mdx
|
|
8
8
|
*/
|
|
9
9
|
// Mangrove Icon System
|
|
10
10
|
// Icons render via CSS mask-image backed by SVG data URIs (Lucide, OCHA, custom sources).
|
|
@@ -4,7 +4,7 @@
|
|
|
4
4
|
* Circular avatar and author profile photo styling with standardized sizing and object-fit.
|
|
5
5
|
*
|
|
6
6
|
* Full documentation:
|
|
7
|
-
* https://github.com/
|
|
7
|
+
* https://github.com/PreventionWeb/undrr-mangrove/blob/main/stories/Atom/Images/AuthorImage/AuthorImages.mdx
|
|
8
8
|
*/
|
|
9
9
|
/* author image */
|
|
10
10
|
|
|
@@ -49,8 +49,8 @@
|
|
|
49
49
|
position: absolute;
|
|
50
50
|
z-index: 1;
|
|
51
51
|
transition:
|
|
52
|
-
opacity
|
|
53
|
-
transform
|
|
52
|
+
opacity var(--mg-motion-duration-fast) var(--mg-motion-easing-standard),
|
|
53
|
+
transform var(--mg-motion-duration-fast) var(--mg-motion-easing-standard);
|
|
54
54
|
transform: translateY(2px);
|
|
55
55
|
}
|
|
56
56
|
|
|
@@ -224,3 +224,10 @@
|
|
|
224
224
|
justify-items: center;
|
|
225
225
|
text-align: center;
|
|
226
226
|
}
|
|
227
|
+
|
|
228
|
+
@media (prefers-reduced-motion: reduce) {
|
|
229
|
+
.mg-author-image__avatar::before {
|
|
230
|
+
transition: none;
|
|
231
|
+
transform: none;
|
|
232
|
+
}
|
|
233
|
+
}
|
|
@@ -4,7 +4,7 @@
|
|
|
4
4
|
* Fluid responsive image wrapper and image sizing utilities.
|
|
5
5
|
*
|
|
6
6
|
* Full documentation:
|
|
7
|
-
* https://github.com/
|
|
7
|
+
* https://github.com/PreventionWeb/undrr-mangrove/blob/main/stories/Atom/Images/ImageCaptionCredit/ImageCaptionCredit.mdx
|
|
8
8
|
*/
|
|
9
9
|
/* img start */
|
|
10
10
|
img,
|
|
@@ -4,7 +4,7 @@
|
|
|
4
4
|
* Figure, figcaption, caption text, and photo credit metadata presentation styles.
|
|
5
5
|
*
|
|
6
6
|
* Full documentation:
|
|
7
|
-
* https://github.com/
|
|
7
|
+
* https://github.com/PreventionWeb/undrr-mangrove/blob/main/stories/Atom/Images/ImageCaptionCredit/ImageCaptionCredit.mdx
|
|
8
8
|
*/
|
|
9
9
|
// @import '../../../assets/scss/base';
|
|
10
10
|
|
|
@@ -49,7 +49,8 @@
|
|
|
49
49
|
padding-bottom: 0;
|
|
50
50
|
width: 25%;
|
|
51
51
|
|
|
52
|
-
p
|
|
52
|
+
p,
|
|
53
|
+
:where(.mg-image-caption__text) {
|
|
53
54
|
font-size: var(--mg-font-size-200);
|
|
54
55
|
line-height: 1.4;
|
|
55
56
|
margin-bottom: var(--mg-spacing-50);
|
|
@@ -61,6 +62,10 @@
|
|
|
61
62
|
padding: var(--mg-spacing-50) 0 0 0;
|
|
62
63
|
}
|
|
63
64
|
}
|
|
65
|
+
|
|
66
|
+
.mg-image-caption__text p:last-child {
|
|
67
|
+
margin-bottom: 0;
|
|
68
|
+
}
|
|
64
69
|
}
|
|
65
70
|
}
|
|
66
71
|
|
|
@@ -4,7 +4,7 @@
|
|
|
4
4
|
* Subtle attribution and copyright credit line styling for imagery.
|
|
5
5
|
*
|
|
6
6
|
* Full documentation:
|
|
7
|
-
* https://github.com/
|
|
7
|
+
* https://github.com/PreventionWeb/undrr-mangrove/blob/main/stories/Atom/Images/ImageCaptionCredit/ImageCaptionCredit.mdx
|
|
8
8
|
*/
|
|
9
9
|
.mg-credits {
|
|
10
10
|
font-size: var(--mg-font-size-200);
|
|
@@ -4,7 +4,7 @@
|
|
|
4
4
|
* Responsive layout containers with breakpoint-driven max widths (480/900/1164/1440px) and gutter padding.
|
|
5
5
|
*
|
|
6
6
|
* Full documentation:
|
|
7
|
-
* https://github.com/
|
|
7
|
+
* https://github.com/PreventionWeb/undrr-mangrove/blob/main/stories/Atom/Layout/Container/Container.mdx
|
|
8
8
|
*/
|
|
9
9
|
// Define your breakpoints if not already defined
|
|
10
10
|
// $mg-breakpoint-mobile: 480px;
|