Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Aksel v7 #3139

Merged
merged 14 commits into from
Sep 13, 2024
Merged
Show file tree
Hide file tree
Changes from 9 commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
5 changes: 5 additions & 0 deletions .changeset/great-crews-hang.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
---
"@navikt/ds-react": major
---

ErrorSummary: Added fallback text for `heading`.
5 changes: 5 additions & 0 deletions .changeset/little-files-cough.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
---
"@navikt/ds-react": major
---

Tooltip: :boom: Updated labeling of items inside Tooltip. [See migrations for how to update](https://aksel.nav.no/grunnleggende/kode/migrering#3b5cf05fd100).
KenAJoh marked this conversation as resolved.
Show resolved Hide resolved
5 changes: 5 additions & 0 deletions .changeset/small-apples-pretend.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
---
"@navikt/aksel-icons": major
---

Icons: Removed renamed icons. [See migration for changes](https://aksel.nav.no/grunnleggende/kode/migrering#194b60833d9e).
5 changes: 5 additions & 0 deletions .changeset/stupid-pianos-end.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
---
"@navikt/ds-tailwind": major
---

Tailwind: Extended 'screens'-config in theme to match Aksel breakpoints. Tailwind and Primitives can now be used side by side with matching dynamic breakpoints. [See migration for potential issues when adopting](https://aksel.nav.no/grunnleggende/kode/migrering#3a2340f6f69b).
6 changes: 6 additions & 0 deletions .changeset/thick-roses-sneeze.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
---
"@navikt/ds-react": patch
"@navikt/ds-css": patch
---

ErrorSummary: Focus heading instead of container for improved experience with screen reader.
3 changes: 0 additions & 3 deletions @navikt/aksel-icons/icons/BeaconSignals.svg

This file was deleted.

19 changes: 0 additions & 19 deletions @navikt/aksel-icons/icons/BeaconSignals.yml

This file was deleted.

3 changes: 0 additions & 3 deletions @navikt/aksel-icons/icons/BeaconSignalsFill.svg

This file was deleted.

19 changes: 0 additions & 19 deletions @navikt/aksel-icons/icons/BeaconSignalsFill.yml

This file was deleted.

3 changes: 0 additions & 3 deletions @navikt/aksel-icons/icons/Buldings2.svg

This file was deleted.

8 changes: 0 additions & 8 deletions @navikt/aksel-icons/icons/Buldings2.yml

This file was deleted.

3 changes: 0 additions & 3 deletions @navikt/aksel-icons/icons/Buldings2Fill.svg

This file was deleted.

8 changes: 0 additions & 8 deletions @navikt/aksel-icons/icons/Buldings2Fill.yml

This file was deleted.

3 changes: 0 additions & 3 deletions @navikt/aksel-icons/icons/Buldings3.svg

This file was deleted.

8 changes: 0 additions & 8 deletions @navikt/aksel-icons/icons/Buldings3.yml

This file was deleted.

3 changes: 0 additions & 3 deletions @navikt/aksel-icons/icons/Buldings3Fill.svg

This file was deleted.

8 changes: 0 additions & 8 deletions @navikt/aksel-icons/icons/Buldings3Fill.yml

This file was deleted.

8 changes: 8 additions & 0 deletions @navikt/core/css/form/error-summary.css
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,14 @@
padding: var(--a-spacing-3);
}

.navds-error-summary__heading {
scroll-margin-top: var(--a-spacing-6);
}

.navds-error-summary--small .navds-error-summary__heading {
scroll-margin-top: var(--a-spacing-4);
}

.navds-error-summary__heading:focus {
outline: none;
}
Expand Down
32 changes: 20 additions & 12 deletions @navikt/core/react/src/form/error-summary/ErrorSummary.tsx
HalvorHaugan marked this conversation as resolved.
Show resolved Hide resolved
Original file line number Diff line number Diff line change
@@ -1,8 +1,8 @@
import cl from "clsx";
import React, { HTMLAttributes, forwardRef, isValidElement } from "react";
import React, { HTMLAttributes, forwardRef, useRef } from "react";
import { BodyShort, Heading } from "../../typography";
import { useId } from "../../util/hooks";
import ErrorSummaryItem, { ErrorSummaryItemType } from "./ErrorSummaryItem";
import { useId, useMergeRefs } from "../../util/hooks";
import ErrorSummaryItem from "./ErrorSummaryItem";

export interface ErrorSummaryProps extends HTMLAttributes<HTMLDivElement> {
/**
Expand All @@ -16,6 +16,7 @@ export interface ErrorSummaryProps extends HTMLAttributes<HTMLDivElement> {
size?: "medium" | "small";
/**
* Heading above links.
* @default "Du må rette disse feilene før du kan fortsette:"
*/
heading?: React.ReactNode;
/**
Expand All @@ -41,7 +42,7 @@ interface ErrorSummaryComponent
* </ErrorSummary.Item>
* ```
*/
Item: ErrorSummaryItemType;
Item: typeof ErrorSummaryItem;
}

/**
Expand Down Expand Up @@ -69,16 +70,21 @@ export const ErrorSummary = forwardRef<HTMLDivElement, ErrorSummaryProps>(
className,
size = "medium",
headingTag = "h2",
heading,
heading = "Du må rette disse feilene før du kan fortsette:",
...rest
},
ref,
) => {
const headingId = useId();

const sectionRef = useRef<HTMLDivElement>(null);
const headingRef = useRef<HTMLHeadingElement>(null);

const mergedRef = useMergeRefs(ref, sectionRef);

return (
<section
ref={ref}
ref={mergedRef}
{...rest}
className={cl(
className,
Expand All @@ -89,22 +95,24 @@ export const ErrorSummary = forwardRef<HTMLDivElement, ErrorSummaryProps>(
aria-live="polite"
aria-relevant="all"
aria-labelledby={headingId}
onFocus={(event) => {
if (event.target === sectionRef.current) {
headingRef?.current?.focus();
}
}}
>
<Heading
className="navds-error-summary__heading"
as={headingTag}
size="small"
id={headingId}
ref={headingRef}
tabIndex={-1}
>
{heading}
</Heading>
<BodyShort as="ul" size={size} className="navds-error-summary__list">
{React.Children.map(children, (child) => {
if (!isValidElement(child)) {
return null;
}
return <li key={child.toString()}>{child}</li>;
})}
{children}
</BodyShort>
</section>
);
Expand Down
18 changes: 10 additions & 8 deletions @navikt/core/react/src/form/error-summary/ErrorSummaryItem.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -14,21 +14,23 @@ export interface ErrorSummaryItemProps
href?: string;
}

export type ErrorSummaryItemType = OverridableComponent<
type ErrorSummaryItemType = OverridableComponent<
ErrorSummaryItemProps,
HTMLAnchorElement
>;

export const ErrorSummaryItem: ErrorSummaryItemType = forwardRef(
({ children, as: Component = "a", className, ...rest }, ref) => {
return (
<Component
{...rest}
ref={ref}
className={cl(className, "navds-error-summary__item", "navds-link")}
>
{children}
</Component>
<li>
<Component
{...rest}
ref={ref}
className={cl(className, "navds-error-summary__item", "navds-link")}
>
{children}
</Component>
</li>
);
},
);
Expand Down
97 changes: 76 additions & 21 deletions @navikt/core/react/src/form/error-summary/error-summary.stories.tsx
Original file line number Diff line number Diff line change
@@ -1,24 +1,12 @@
import { Meta, StoryObj } from "@storybook/react";
import React from "react";
import { expect, userEvent, within } from "@storybook/test";
import React, { useRef } from "react";
import { VStack } from "../../layout/stack";
import { ErrorSummary } from "./ErrorSummary";

export default {
title: "ds-react/Errorsummary",
title: "ds-react/ErrorSummary",
component: ErrorSummary,
argTypes: {
headingTag: {
control: {
type: "text",
},
},
size: {
control: {
type: "radio",
},
options: ["medium", "small"],
},
},
parameters: {
chromatic: { disable: true },
},
Expand All @@ -27,18 +15,32 @@ export default {
type Story = StoryObj<typeof ErrorSummary>;

export const Default: Story = {
render: (props) => (
<ErrorSummary
heading="Feiloppsummering komponent"
headingTag={props.headingTag || "h2"}
size={props.size ?? undefined}
>
render: ({ headingTag, ...rest }) => (
<ErrorSummary headingTag={headingTag || undefined} {...rest}>
<ErrorSummary.Item href="#1">Checkbox må fylles ut</ErrorSummary.Item>
<ErrorSummary.Item href="#2">
Tekstfeltet må ha en godkjent e-mail
</ErrorSummary.Item>
</ErrorSummary>
),
argTypes: {
heading: {
control: {
type: "text",
},
},
headingTag: {
control: {
type: "text",
},
},
size: {
control: {
type: "radio",
},
options: ["medium", "small"],
},
},
};

export const Small: Story = {
Expand All @@ -52,6 +54,59 @@ export const Small: Story = {
),
};

export const A11yDemo: Story = {
name: "A11y Demo",
render: () => {
const ref = useRef<HTMLHeadingElement>(null);
return (
<div>
<button
onClick={() => {
ref.current?.focus();
}}
>
Fokuser ErrorSummary
</button>
<ErrorSummary heading="Feiloppsummering tittel" ref={ref}>
<ErrorSummary.Item href="#1">Checkbox må fylles ut</ErrorSummary.Item>
<ErrorSummary.Item href="#2">
Tekstfeltet må ha en godkjent e-mail
</ErrorSummary.Item>
</ErrorSummary>
</div>
);
},
};

export const FocusDemo: Story = {
render: () => {
const ref = useRef<HTMLHeadingElement>(null);
return (
<div>
<button onClick={() => ref.current?.focus()}>Focus summary</button>
<ErrorSummary heading="Feiloppsummering tittel" ref={ref}>
<ErrorSummary.Item href="#1">Checkbox må fylles ut</ErrorSummary.Item>
<ErrorSummary.Item href="#2">
Tekstfeltet må ha en godkjent e-mail
</ErrorSummary.Item>
</ErrorSummary>
</div>
);
},
play: async ({ canvasElement, step }) => {
const canvas = within(canvasElement);

const button = canvas.getByText("Focus summary");
const heading = canvas.getByText("Feiloppsummering tittel");

await step("click button", async () => {
await userEvent.click(button);
});

expect(heading).toHaveFocus();
},
};

export const Chromatic: Story = {
render: () => (
<VStack gap="4">
Expand Down
Loading
Loading