Skip to content

Commit

Permalink
Merge remote-tracking branch 'origin/cc/reader-rev-msg-front' into cc…
Browse files Browse the repository at this point in the history
…/reader-rev-msg-front
  • Loading branch information
charleycampbell committed Nov 22, 2024
2 parents 03f47a3 + 05a8408 commit 53bd44a
Show file tree
Hide file tree
Showing 6 changed files with 193 additions and 71 deletions.
30 changes: 30 additions & 0 deletions dotcom-rendering/src/components/ContainerOverrides.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -1077,6 +1077,28 @@ const carouselChevronBorderDisabledDark: ContainerFunction = (
containerPalette,
) => transparentColour(cardHeadlineDark(containerPalette), 0.4);

const slideshowPaginationDotLight: ContainerFunction = (containerPalette) => {
switch (containerPalette) {
case 'BreakingPalette':
case 'InvestigationPalette':
case 'SombrePalette':
case 'SombreAltPalette':
return transparentColour(cardHeadlineLight(containerPalette), 0.4);
default:
return transparentColour(cardHeadlineLight(containerPalette), 0.2);
}
};

const slideshowPaginationDotDark: ContainerFunction = (containerPalette) =>
transparentColour(cardHeadlineDark(containerPalette), 0.4);

const slideshowPaginationDotActiveLight: ContainerFunction = (
containerPalette,
) => cardHeadlineLight(containerPalette);
const slideshowPaginationDotActiveDark: ContainerFunction = (
containerPalette,
) => cardHeadlineDark(containerPalette);

type ColourName = Parameters<typeof palette>[0];

type ContainerFunction = (containerPalette: DCRContainerPalette) => string;
Expand Down Expand Up @@ -1210,6 +1232,14 @@ const containerColours = {
light: carouselChevronHoverLight,
dark: carouselChevronHoverDark,
},
'--slideshow-pagination-dot': {
light: slideshowPaginationDotLight,
dark: slideshowPaginationDotDark,
},
'--slideshow-pagination-dot-active': {
light: slideshowPaginationDotActiveLight,
dark: slideshowPaginationDotActiveDark,
},
'--section-border': {
light: sectionBorderLight,
dark: sectionBorderDark,
Expand Down
28 changes: 19 additions & 9 deletions dotcom-rendering/src/components/SlideshowCarousel.importable.tsx
Original file line number Diff line number Diff line change
@@ -1,5 +1,10 @@
import { css } from '@emotion/react';
import { space, textSansBold12, width } from '@guardian/source/foundations';
import {
from,
space,
textSansBold12,
width,
} from '@guardian/source/foundations';
import type { ThemeButton } from '@guardian/source/react-components';
import {
Button,
Expand Down Expand Up @@ -49,18 +54,18 @@ const carouselItemStyles = css`
`;

const captionStyles = css`
${textSansBold12}
position: absolute;
bottom: 0;
left: 0;
right: 0;
${textSansBold12}
color: ${palette('--slideshow-caption')};
background: linear-gradient(
to bottom,
rgba(0, 0, 0, 0) 0%,
rgba(0, 0, 0, 0.8) 100%
);
color: ${palette('--slideshow-caption')};
padding: 60px ${space[2]}px ${space[2]}px;
padding: ${space[10]}px ${space[2]}px ${space[2]}px;
`;

const navigationStyles = css`
Expand All @@ -70,20 +75,25 @@ const navigationStyles = css`
`;

const buttonStyles = css`
display: flex;
gap: ${space[2]}px;
display: none;
${from.tablet} {
display: flex;
gap: ${space[2]}px;
}
`;

/**
* Padding is added to the left of the scrolling navigation dots to match the
* width of the navigation buttons on the right. This allows them to be centred
* below the slideshow image.
* width of the navigation buttons on the right at tablet and above. This allows
* them to be centred below the slideshow image.
*/
const scrollingDotStyles = css`
display: flex;
justify-content: center;
flex: 1 0 0;
padding-left: ${width.ctaSmall * 2 + space[2]}px;
${from.tablet} {
padding-left: ${width.ctaSmall * 2 + space[2]}px;
}
`;

export const SlideshowCarousel = ({
Expand Down
131 changes: 94 additions & 37 deletions dotcom-rendering/src/components/SlideshowCarousel.stories.tsx
Original file line number Diff line number Diff line change
@@ -1,41 +1,12 @@
import { css } from '@emotion/react';
import { breakpoints, space } from '@guardian/source/foundations';
import { breakpoints, space, textSans17 } from '@guardian/source/foundations';
import type { Meta, StoryObj } from '@storybook/react';
import type { ReactNode } from 'react';
import type { DCRSlideshowImage } from '../types/front';
import { palette } from '../palette';
import type { DCRContainerPalette, DCRSlideshowImage } from '../types/front';
import { ContainerOverrides } from './ContainerOverrides';
import { SlideshowCarousel } from './SlideshowCarousel.importable';

const Wrapper = ({ children }: { children: ReactNode }) => {
const styles = css`
margin: ${space[2]}px;
max-width: 460px;
`;
return <div css={styles}>{children}</div>;
};

const meta = {
component: SlideshowCarousel,
title: 'Components/SlideshowCarousel',
render: (args) => (
<Wrapper>
<SlideshowCarousel {...args} />
</Wrapper>
),
parameters: {
chromatic: {
viewports: [
breakpoints.mobile,
breakpoints.tablet,
breakpoints.leftCol,
],
},
},
} satisfies Meta<typeof SlideshowCarousel>;

export default meta;

type Story = StoryObj<typeof meta>;

const images = [
{
imageSrc:
Expand Down Expand Up @@ -75,23 +46,109 @@ const images = [
},
] as const satisfies readonly DCRSlideshowImage[];

export const WithMultipleImages = {
const Wrapper = ({
children,
heading,
}: {
children: ReactNode;
heading?: string;
}) => {
const sectionStyles = css`
padding: ${space[4]}px;
background: ${palette('--card-background')};
`;
const containerStyles = css`
max-width: 460px;
`;
const headingStyles = css`
${textSans17};
color: ${palette('--card-headline')};
margin-bottom: ${space[2]}px;
`;
return (
<section css={sectionStyles}>
<div css={containerStyles}>
{!!heading && <h2 css={headingStyles}>{heading}</h2>}
{children}
</div>
</section>
);
};

const meta = {
component: SlideshowCarousel,
title: 'Components/SlideshowCarousel',
parameters: {
chromatic: {
viewports: [
breakpoints.mobile,
breakpoints.tablet,
breakpoints.leftCol,
],
},
},
args: {
images,
imageSize: 'medium',
},
} satisfies Story;
render: (args) => (
<Wrapper>
<SlideshowCarousel {...args} />
</Wrapper>
),
} satisfies Meta<typeof SlideshowCarousel>;

export default meta;

type Story = StoryObj<typeof meta>;

export const WithMultipleImages = {} satisfies Story;

export const WithThreeImages = {
args: {
images: images.slice(0, 3),
imageSize: 'medium',
},
} satisfies Story;

export const WithOneImage = {
args: {
images: images.slice(0, 1),
imageSize: 'medium',
},
} satisfies Story;

const containerPalettes = [
'InvestigationPalette',
'LongRunningPalette',
'SombrePalette',
'BreakingPalette',
'EventPalette',
'EventAltPalette',
'LongRunningAltPalette',
'SombreAltPalette',
'SpecialReportAltPalette',
'Branded',
] as const satisfies readonly Omit<
DCRContainerPalette,
'MediaPalette' | 'PodcastPalette'
>[];

export const WithSpecialPaletteVariations = {
parameters: {
/** We only want one breakpoint snapshotted for special palette variations */
chromatic: { viewports: [breakpoints.desktop] },
},
render: (args) => (
<>
{containerPalettes.map((containerPalette) => (
<ContainerOverrides
containerPalette={containerPalette}
key={containerPalette}
>
<Wrapper heading={containerPalette}>
<SlideshowCarousel {...args} />
</Wrapper>
</ContainerOverrides>
))}
</>
),
} satisfies Story;
23 changes: 22 additions & 1 deletion dotcom-rendering/src/components/TableOfContents.importable.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,7 @@ import {
} from '@guardian/source/react-components';
import { useState } from 'react';
import { ArticleDisplay, type ArticleFormat } from '../lib/articleFormat';
import { getZIndex } from '../lib/getZIndex';
import type { TableOfContentsItem } from '../model/enhanceTableOfContents';
import { palette } from '../palette';

Expand Down Expand Up @@ -72,6 +73,20 @@ const detailsStyles = css`
display: none;
}
`;
const stickyStyles = css`
position: sticky;
top: 0;
background: ${palette('--article-background')};
${getZIndex('tableOfContents')}
max-height: 100vh;
overflow: scroll;
summary {
position: sticky;
top: 0;
z-index: 1;
background: ${palette('--article-background')};
}
`;

const summaryStyles = css`
display: flex;
Expand Down Expand Up @@ -126,7 +141,10 @@ export const TableOfContents = ({ tableOfContents, format }: Props) => {
return (
<details
open={open}
css={detailsStyles}
css={[
detailsStyles,
tableOfContents.length > 5 ? stickyStyles : undefined,
]}
data-component="table-of-contents"
>
<summary
Expand Down Expand Up @@ -173,6 +191,9 @@ export const TableOfContents = ({ tableOfContents, format }: Props) => {
<a
href={`#${item.id}`}
css={[anchorStyles, paddingStyles]}
onClick={(): void => {
setOpen((state) => !state);
}}
>
{item.title}
</a>
Expand Down
49 changes: 25 additions & 24 deletions dotcom-rendering/src/lib/getZIndex.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -2,34 +2,35 @@ import { getZIndex } from './getZIndex';

describe('getZIndex', () => {
it('gets the correct zindex for group and sibling', () => {
expect(getZIndex('sticky-video-button')).toBe('z-index: 31;');
expect(getZIndex('sticky-video')).toBe('z-index: 30;');
expect(getZIndex('banner')).toBe('z-index: 29;');
expect(getZIndex('dropdown')).toBe('z-index: 28;');
expect(getZIndex('burger')).toBe('z-index: 27;');
expect(getZIndex('sticky-video-button')).toBe('z-index: 32;');
expect(getZIndex('sticky-video')).toBe('z-index: 31;');
expect(getZIndex('banner')).toBe('z-index: 30;');
expect(getZIndex('dropdown')).toBe('z-index: 29;');
expect(getZIndex('burger')).toBe('z-index: 28;');
expect(getZIndex('mastheadVeggieBurgerExpandedMobile')).toBe(
'z-index: 26;',
'z-index: 27;',
);
expect(getZIndex('expanded-veggie-menu-wrapper')).toBe('z-index: 25;');
expect(getZIndex('expanded-veggie-menu')).toBe('z-index: 24;');
expect(getZIndex('expanded-veggie-menu-wrapper')).toBe('z-index: 26;');
expect(getZIndex('expanded-veggie-menu')).toBe('z-index: 25;');
expect(getZIndex('fullPageInteractiveHeaderWrapper')).toBe(
'z-index: 23;',
'z-index: 24;',
);
expect(getZIndex('mobileSticky')).toBe('z-index: 22;');
expect(getZIndex('stickyAdWrapperLabsHeader')).toBe('z-index: 21;');
expect(getZIndex('stickyAdWrapper')).toBe('z-index: 20;');
expect(getZIndex('stickyAdWrapperNav')).toBe('z-index: 19;');
expect(getZIndex('mastheadMyAccountDropdown')).toBe('z-index: 18;');
expect(getZIndex('mastheadEditionDropdown')).toBe('z-index: 17;');
expect(getZIndex('editionDropdown')).toBe('z-index: 16;');
expect(getZIndex('summaryDetails')).toBe('z-index: 15;');
expect(getZIndex('toast')).toBe('z-index: 14;');
expect(getZIndex('onwardsCarousel')).toBe('z-index: 13;');
expect(getZIndex('myAccountDropdown')).toBe('z-index: 12;');
expect(getZIndex('searchHeaderLink')).toBe('z-index: 11;');
expect(getZIndex('TheGuardian')).toBe('z-index: 10;');
expect(getZIndex('editionSwitcherBanner')).toBe('z-index: 9;');
expect(getZIndex('expandableMarketingCardOverlay')).toBe('z-index: 8;');
expect(getZIndex('mobileSticky')).toBe('z-index: 23;');
expect(getZIndex('stickyAdWrapperLabsHeader')).toBe('z-index: 22;');
expect(getZIndex('stickyAdWrapper')).toBe('z-index: 21;');
expect(getZIndex('stickyAdWrapperNav')).toBe('z-index: 20;');
expect(getZIndex('mastheadMyAccountDropdown')).toBe('z-index: 19;');
expect(getZIndex('mastheadEditionDropdown')).toBe('z-index: 18;');
expect(getZIndex('editionDropdown')).toBe('z-index: 17;');
expect(getZIndex('summaryDetails')).toBe('z-index: 16;');
expect(getZIndex('toast')).toBe('z-index: 15;');
expect(getZIndex('onwardsCarousel')).toBe('z-index: 14;');
expect(getZIndex('myAccountDropdown')).toBe('z-index: 13;');
expect(getZIndex('searchHeaderLink')).toBe('z-index: 12;');
expect(getZIndex('TheGuardian')).toBe('z-index: 11;');
expect(getZIndex('editionSwitcherBanner')).toBe('z-index: 10;');
expect(getZIndex('expandableMarketingCardOverlay')).toBe('z-index: 9;');
expect(getZIndex('tableOfContents')).toBe('z-index: 8;');
expect(getZIndex('articleHeadline')).toBe('z-index: 7;');
expect(getZIndex('immersiveBlackBox')).toBe('z-index: 6;');
expect(getZIndex('bodyArea')).toBe('z-index: 5;');
Expand Down
3 changes: 3 additions & 0 deletions dotcom-rendering/src/lib/getZIndex.ts
Original file line number Diff line number Diff line change
Expand Up @@ -77,6 +77,9 @@ const indices = [
// Overlay for expandable marketing card (currently US only)
'expandableMarketingCardOverlay',

// Sticky table of contents element
'tableOfContents',

// Article headline (should be above main media)
'articleHeadline',
'immersiveBlackBox',
Expand Down

0 comments on commit 53bd44a

Please sign in to comment.