mirror of
https://github.com/navikt/aksel.git
synced 2026-10-13 01:02:02 +00:00
Compare commits
46
Commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
9a1a48d319 | ||
|
|
ce4afb17a8 | ||
|
|
146111e859 | ||
|
|
40a8965cec | ||
|
|
8f4e6a5e89 | ||
|
|
e73c9d2f3e | ||
|
|
0849fffe40 | ||
|
|
7a261e86a3 | ||
|
|
a2c48a9246 | ||
|
|
7c845ac464 | ||
|
|
6edd03a9c1 | ||
|
|
724a90eb28 | ||
|
|
43b686e769 | ||
|
|
c485e1bfc7 | ||
|
|
9533504b16 | ||
|
|
bca56d1c48 | ||
|
|
a656a19df5 | ||
|
|
a2ac8fedb1 | ||
|
|
bf0a71f1d4 | ||
|
|
e4b51f49fb | ||
|
|
ea49e12e23 | ||
|
|
4a29f5b449 | ||
|
|
7b7950dab1 | ||
|
|
bcb8d46c72 | ||
|
|
60dbbaedd9 | ||
|
|
8991704a09 | ||
|
|
4a22f10763 | ||
|
|
7335fb6c8d | ||
|
|
9b95eff894 | ||
|
|
08ce808f21 | ||
|
|
64b2f2bfb5 | ||
|
|
df38a410a5 | ||
|
|
0e426ee905 | ||
|
|
7f0278429b | ||
|
|
041c662737 | ||
|
|
f8c59d7bc1 | ||
|
|
f0dccb0a83 | ||
|
|
11f23ef579 | ||
|
|
ebb7be678f | ||
|
|
588d485841 | ||
|
|
f4ec864c5d | ||
|
|
c91131c29c | ||
|
|
d8e18812ff | ||
|
|
d40f624edb | ||
|
|
1cfd79fdb8 | ||
|
|
9dabc6386d |
No files matched your search
@@ -50,7 +50,7 @@ jobs:
|
||||
publish-npm:
|
||||
needs: test-build
|
||||
runs-on: ubuntu-latest
|
||||
if: github.event_name == 'push'
|
||||
if: github.event_name == 'push' && contains(github.event.head_commit.message, '[fix]') || contains(github.event.head_commit.message, '[feature]') || contains(github.event.head_commit.message, '[breaking]')
|
||||
steps:
|
||||
- uses: actions/checkout@v2
|
||||
with:
|
||||
@@ -71,25 +71,48 @@ jobs:
|
||||
run: yarn install --frozen-lockfile
|
||||
- name: Boot
|
||||
run: yarn boot
|
||||
- run: git config --global user.email "github-actions[bot]@users.noreply.github.com"
|
||||
- run: git config --global user.name "github-actions[bot]"
|
||||
- run: git remote set-url origin https://github-actions[bot]:$NAV_DS_TOKEN@github.com/$GITHUB_REPOSITORY.git
|
||||
- name: Setup github connection for auth
|
||||
run: |
|
||||
git config --global user.email "github-actions[bot]@users.noreply.github.com"
|
||||
git config --global user.name "github-actions[bot]"
|
||||
git remote set-url origin https://github-actions[bot]:$NAV_DS_TOKEN@github.com/$GITHUB_REPOSITORY.git
|
||||
env:
|
||||
NAV_DS_TOKEN: ${{secrets.GIT_REPO}}
|
||||
- run: yarn lerna version patch --include-merged-tags --yes
|
||||
- run: yarn lerna publish from-package --yes
|
||||
|
||||
- name: Update changed packages with PATCH
|
||||
if: "contains(github.event.head_commit.message, '[fix]')"
|
||||
run: yarn lerna version patch --include-merged-tags --yes
|
||||
- name: Update changed packages with MINOR
|
||||
if: "contains(github.event.head_commit.message, '[feature]')"
|
||||
run: yarn lerna version minor --include-merged-tags --yes
|
||||
- name: Update changed packages with MAJOR
|
||||
if: "contains(github.event.head_commit.message, '[breaking]')"
|
||||
run: yarn lerna version major --include-merged-tags --yes
|
||||
|
||||
- name: Create a .npmrc file for NPM
|
||||
run: |
|
||||
echo "//registry.npmjs.org/:_authToken=$NPM_TOKEN" >> .npmrc
|
||||
npm whoami
|
||||
env:
|
||||
NPM_TOKEN: ${{secrets.NPM_AUTOMATION}}
|
||||
- name: Publish to NPM registry
|
||||
run: |
|
||||
yarn lerna publish from-package --yes
|
||||
rm .npmrc
|
||||
- name: Create a .npmrc file for the github package repository
|
||||
uses: FerLuisxd/create-npmrc@3
|
||||
with:
|
||||
org_name: navikt
|
||||
env:
|
||||
AUTH_TOKEN: ${{secrets.GIT_REPO}}
|
||||
- run: rm lerna.json && cp utilities/lerna.json lerna.json
|
||||
- run: git add . && git commit -m "tmp"
|
||||
- run: yarn lerna publish --registry https://npm.pkg.github.com from-package --yes
|
||||
- name: Publish to Github registry
|
||||
run: |
|
||||
rm lerna.json && cp utilities/lerna.json lerna.json
|
||||
git add . && git commit -m "tmp"
|
||||
yarn lerna publish --registry https://npm.pkg.github.com from-package --yes
|
||||
|
||||
publish-pages:
|
||||
needs: publish-npm
|
||||
needs: test-build
|
||||
runs-on: ubuntu-latest
|
||||
if: github.event_name == 'push'
|
||||
steps:
|
||||
|
||||
+21
-32
@@ -1,54 +1,43 @@
|
||||
{
|
||||
"repository": "@nav/designsystem",
|
||||
"head": "updated-specify-tokens",
|
||||
"base": "master",
|
||||
"head": "specify-sync",
|
||||
"base": "specify-token-parsing",
|
||||
"rules": [
|
||||
{
|
||||
"name": "Specify / Icons",
|
||||
"path": "@navikt/ds-icons/svg",
|
||||
"name": "Color sync",
|
||||
"path": "@navikt/ds-tokens/src/colors.js",
|
||||
"filter": {
|
||||
"types": ["vector"]
|
||||
"types": ["color"]
|
||||
},
|
||||
"parsers": [
|
||||
{
|
||||
"name": "pascalcasify",
|
||||
"name": "to-theme-ui",
|
||||
"options": {
|
||||
"keys": ["name"]
|
||||
}
|
||||
},
|
||||
{
|
||||
"name": "name-assets-files-by-pattern",
|
||||
"options": {
|
||||
"pattern": "{{name}}.{{format}}"
|
||||
"formatConfig": {
|
||||
"module": "commonjs"
|
||||
},
|
||||
"formatTokens": {
|
||||
"colorFormat": {
|
||||
"format": "rgb"
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
]
|
||||
},
|
||||
{
|
||||
"name": "Specify / Icons - metadata",
|
||||
"path": "@navikt/ds-icons/figma-api/metadata-specify.json",
|
||||
"name": "Spacing sync",
|
||||
"path": "@navikt/ds-tokens/src/spacing.js",
|
||||
"filter": {
|
||||
"types": ["vector"]
|
||||
"types": ["measurement"]
|
||||
},
|
||||
"parsers": [
|
||||
{
|
||||
"name": "pascalcasify",
|
||||
"name": "to-theme-ui",
|
||||
"options": {
|
||||
"keys": ["name"]
|
||||
}
|
||||
},
|
||||
{
|
||||
"name": "pick",
|
||||
"options": {
|
||||
"keys": [
|
||||
"name",
|
||||
"createdAt",
|
||||
"updatedAt",
|
||||
"meta.description",
|
||||
"meta.parentFrame",
|
||||
"meta.frame",
|
||||
"page"
|
||||
]
|
||||
"formatConfig": {
|
||||
"module": "commonjs"
|
||||
}
|
||||
}
|
||||
}
|
||||
]
|
||||
|
||||
@@ -0,0 +1,229 @@
|
||||
import { Meta } from "@storybook/addon-docs";
|
||||
|
||||
<Meta title="ds-react/Migration" />
|
||||
|
||||
# Migrering til ds-react, ds-css v0.8.0
|
||||
|
||||
Denne guiden vil være til hjelp for de som allerede har begynt å ta i bruk de nye pakkene våre tidligere enn v0.8.0.
|
||||
For de som ikke har begynt å ta i bruk pakkene kan man se bort fra denne.
|
||||
|
||||
Fra versjon v0.7 til v0.8 er det komment flere store endringer både i ds-react og ds-css. For å lettere
|
||||
oppdatere til v0.8 har vi da laget en liten guide som forklarer de største endringene.
|
||||
|
||||
## Styling
|
||||
|
||||
De fleste komponenter har fått diverse justering på styling. Anbefales da å ta en rask sjekk om alt fortsatt stemmer
|
||||
etter oppdateringen.
|
||||
|
||||
## Sizing
|
||||
|
||||
Alle komponenter som tidligere var implementert med `size`-prop har fått oppdatert
|
||||
props fra "xs", "s", "m", "l", "xl", "2xl" -> "xsmall", "small", "medium", "large", "xlarge", "2xlarge".
|
||||
|
||||
Dette betyr også at css-stylingen er eks endret fra `.navds-body-short--s` -> `.navds-body-short--small`
|
||||
|
||||
## Overridable component
|
||||
|
||||
Komponenter som tidligere implementerte ovveridable component med bruk av `component`-prop bruker nå `as`.
|
||||
Implementasjonen av OverridableComponent er WIP så kan hende typene ender opp med å krangle i enkelte tilfeller. Om så ta gjerne kontakt med oss
|
||||
slik at vi får sett på det tilfellet!
|
||||
|
||||
```jsx
|
||||
/* Før */
|
||||
<BodyShort component="span" />
|
||||
|
||||
/* Etter */
|
||||
<BodyShort as="span" />
|
||||
```
|
||||
|
||||
## Navneendringer
|
||||
|
||||
### Buttons
|
||||
|
||||
- `Primary` -> `Secondary` (Normal)
|
||||
- `Action` -> `Primary` (Hoved)
|
||||
- `Secondary` -> `Tertiary` (Flat)
|
||||
|
||||
For alle som har brukt `<Button />` så må man fikse slik at riktige knapper blir brukt der de skal!
|
||||
|
||||
## Nytt
|
||||
|
||||
- GuidePanel (veilederpanel)
|
||||
- HelpText (Hjeleptext)
|
||||
|
||||
### Typography
|
||||
|
||||
Vi har valgt å endre fra `<Title/>` -> `<Heading/>` i typografien vår da dette ga mer mening i bruk.
|
||||
APIet til komponenten er ikke endret borsett fra "Sizing" endringene nevt lengre opp, så skal bare være en rask search/replace.
|
||||
|
||||
For de som har brukt css-en direkte, eks `navds-title` så må man endre til `navds-heading`
|
||||
|
||||
Endret `Header` -> `PageHeader`, samme som er nevnt ang endringen over gjelder her også: sjekk css hvis brukt direkte.
|
||||
|
||||
## Fjernet komponenter
|
||||
|
||||
Fjernet da den var utdaterte/må ses mer på
|
||||
|
||||
- ProductPageLayout
|
||||
|
||||
## Typography
|
||||
|
||||
Linjehøyder for alle typo-komponentene er oppdatert til å matche figma.
|
||||
|
||||
Lagt til en Heading lvl 6 og size="xsmall"
|
||||
|
||||
## AccordionMenu
|
||||
|
||||
Implementert med dot-notation
|
||||
|
||||
- Trenger bare importere AccordionMenu
|
||||
- AccordionMenuCollapsable -> AccordionMenu.Collapsable
|
||||
- AccordionMenuItem -> AccordionMenu.Item
|
||||
|
||||
## Accordion
|
||||
|
||||
Implementert med dot-notation
|
||||
|
||||
- Trenger bare importere Accordion nå
|
||||
|
||||
Fragmenterte komponenten:
|
||||
|
||||
- Accordion -> Accordion.Item
|
||||
- Header -> Accordion.Header
|
||||
- children -> Accordion.Content
|
||||
|
||||
La til prop: `defaultOpen` på `Accordion.Item`
|
||||
|
||||
```jsx
|
||||
/* Før */
|
||||
<Accordion heading="tittel" open={open} onClick={(open) => setOpen(!open)}>
|
||||
Eu magna fugiat officia
|
||||
</Accordion>
|
||||
<Accordion heading="tittel2" open={open2} onClick={(open2) => setOpen(!open2)}>
|
||||
Eu magna fugiat officia
|
||||
</Accordion>
|
||||
|
||||
/* Etter */
|
||||
<Accordion>
|
||||
<Accordion.Item open={open}>
|
||||
<Accordion.Header onClick={(open) => setOpen(!open)}>
|
||||
Accordion header text
|
||||
</Accordion.Header>
|
||||
<Accordion.Content>
|
||||
Magna aliquip aliquip fugiat nostrud nostrud velit pariatur veniam officia
|
||||
laboris voluptate officia pariatur.Lorem est ex anim velit
|
||||
</Accordion.Content>
|
||||
</Accordion.Item>
|
||||
<Accordion.Item open={open2}>
|
||||
<Accordion.Header onClick={(open2) => setOpen(!open2)}>
|
||||
Accordion header text
|
||||
</Accordion.Header>
|
||||
<Accordion.Content>
|
||||
Magna aliquip aliquip fugiat nostrud nostrud velit pariatur veniam officia
|
||||
laboris voluptate officia pariatur.Lorem est ex anim velit
|
||||
</Accordion.Content>
|
||||
</Accordion.Item>
|
||||
</Accordion>
|
||||
```
|
||||
|
||||
## Alert
|
||||
|
||||
- La til `fullWidth`-prop for alert uten border-radius og width 100%
|
||||
- La til `inline`-prop for alert med transparent border/background og 0 padding.
|
||||
|
||||
## Button
|
||||
|
||||
Oppdatert med Overridablecomponent.
|
||||
|
||||
Håndtering av sentrering, margins er oppdatert. Trenger ikke wrappe tekst med `span` når man skal bruke ikoner lengre.
|
||||
|
||||
Hvis man skal manuelt justere på alignment av innhold, eks bruke `flex-direction: column` må man sette
|
||||
det på css-klassen `.navds-button__inner` da children er wrappet i den.
|
||||
|
||||
## CopyToClipboard
|
||||
|
||||
Ekstender nå ButtonProps, slik at man eks kan ta i bruk `size`-proppen
|
||||
|
||||
`text`-prop -> `copyText`
|
||||
`label`-prop -> `popoverText`
|
||||
|
||||
Fjernet `icon`-prop, la til `popoverPlacement`
|
||||
|
||||
## Modal
|
||||
|
||||
Implementert med dot-notasjon
|
||||
|
||||
Innholds-padding er flyttet fra Modal -> Modal.Content
|
||||
|
||||
```
|
||||
/* Før */
|
||||
<Modal>Modal innhold</Modal>
|
||||
|
||||
/* Etter */
|
||||
<Modal><Modal.Content>Modal innhold</Modal.Content></Modal>
|
||||
```
|
||||
|
||||
## LinkPanel
|
||||
|
||||
Implementert med dot-notasjon
|
||||
|
||||
```jsx
|
||||
/* Før */
|
||||
<LinkPanel href="#">Consectetur eu duis aliqua eu irure fugiat fugiat eu.</LinkPanel>
|
||||
|
||||
/* Etter */
|
||||
<LinkPanel href="#">
|
||||
<LinkPanel.Title>
|
||||
Consectetur eu duis aliqua eu irure fugiat fugiat eu.
|
||||
</LinkPanel.Title>
|
||||
</LinkPanel>
|
||||
```
|
||||
|
||||
Kan nå legge til en beskrivelse med `Linkpanel.Description`
|
||||
|
||||
```jsx
|
||||
<LinkPanel href="#">
|
||||
<LinkPanel.Title>
|
||||
Consectetur eu duis aliqua eu irure fugiat fugiat eu.
|
||||
</LinkPanel.Title>
|
||||
<LinkPanel.Description>Aliqua id aliquip Lorem esse</LinkPanel.Description>
|
||||
</LinkPanel>
|
||||
```
|
||||
|
||||
## Popover
|
||||
|
||||
Implementert med dot-notasjon
|
||||
|
||||
Får nå padding rundt innhold med Popover.Content
|
||||
|
||||
```jsx
|
||||
|
||||
/* Før */
|
||||
|
||||
<Popover>Popover innhold</Popover>
|
||||
|
||||
/* Etter */
|
||||
|
||||
<Popover>
|
||||
<Popover.Content>Modal innhold</Popover.Content>
|
||||
</Popover>
|
||||
```
|
||||
|
||||
## Header -> PageHeader
|
||||
|
||||
Props må fikses for de som har brukt denne komponenten, i tilleg til å endre navn.
|
||||
|
||||
- `variant`-prop -> `align`
|
||||
- `theme`-prop -> `variant`
|
||||
|
||||
## MicroCard
|
||||
|
||||
- Oppdatert med OverridableComponent
|
||||
|
||||
## SpeechBubble
|
||||
|
||||
Implementert med Dot-notasjon
|
||||
|
||||
- `<Bubble/>` -> `<SpeechBubble.Bubble/>`
|
||||
|
||||
Bubble er fortsatt eksportert så vil ikke brekke noe for de som har begynt å ta denne i bruk.
|
||||
@@ -20,7 +20,7 @@ Dette vil gjøre styling og overriding av komponenter enklere da man kan bruke c
|
||||
## Intern / Ekstern sizing
|
||||
|
||||
Komponenter tilpasses og standariseres bedre for skillet mellom interne/eksterne flater.
|
||||
Løsning er ikke fast bestemt, men eksempel på dette er `size="s" -> 32px, size="m"-> 48px`.
|
||||
Løsning er ikke fast bestemt, men eksempel på dette er `size="small" -> 32px, size="medium"-> 48px`.
|
||||
Dette vil da eksempelvis kunne være en standard som er gjennomgående for de fleste komponentene.
|
||||
|
||||
## Ny dokumentasjon-side
|
||||
@@ -44,12 +44,6 @@ eks darkmode.
|
||||
Dette er noe vi ikke har på planene for tiden, men etterhvert som ting faller på plass så vil dette være
|
||||
noe vi kunne ta en titt på hvis vi ser at det trengs.
|
||||
|
||||
## Feature-flagging
|
||||
|
||||
Ideen om å ta i bruk feature-flagging er noe som virker veldig interessant og vil da se på muligheten for å kunne levere
|
||||
større endringe i feature-flags for testing, og da publisere under eks major-bump i faste intervaller. Dette vil da kunne
|
||||
gjøre det enklere for deg som consumer av pakkene å ha oversikt over endringer og hva som må migreres.
|
||||
|
||||
## Versjonering
|
||||
|
||||
To av de nye pakkene under `@navikt`, da `ds-css` og `ds-react` er nå versjonert under to store pakker med alle komponentene. I fremtiden vil vi se på å
|
||||
|
||||
+1
-1
@@ -1,3 +1,3 @@
|
||||
# Designsystem v2
|
||||
# Designsystem v2
|
||||
|
||||
Storybook: https://navikt.github.io/Designsystemet/
|
||||
@@ -1,3 +1,11 @@
|
||||
:root {
|
||||
--navds-accordion-menu-color-text: var(--navds-color-text-link);
|
||||
--navds-accordion-menu-color-text-focus: var(--navds-color-darkgray);
|
||||
--navds-accordion-menu-color-background-hover: var(--navds-color-blue-10);
|
||||
--navds-accordion-menu-color-text-active: var(--navds-color-text);
|
||||
--navds-accordion-menu-outline-focus: var(--navds-text-focus);
|
||||
}
|
||||
|
||||
.navds-accordion-menu__list {
|
||||
list-style: none;
|
||||
margin: 0;
|
||||
@@ -18,7 +26,7 @@
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
font-weight: var(--navds-font-weight-bold);
|
||||
color: var(--navds-color-text-link);
|
||||
color: var(--navds-accordion-menu-color-text);
|
||||
text-decoration: underline;
|
||||
}
|
||||
|
||||
@@ -31,7 +39,7 @@
|
||||
|
||||
.navds-accordion-menu-collapsable__expand-icon {
|
||||
font-size: 1.5rem;
|
||||
color: var(--navds-color-text-link);
|
||||
color: var(--navds-accordion-menu-color);
|
||||
flex-shrink: 0;
|
||||
margin-left: var(--navds-spacing-2);
|
||||
}
|
||||
@@ -73,18 +81,23 @@
|
||||
|
||||
.navds-accordion-menu-item:focus,
|
||||
.navds-accordion-menu-collapsable__button:focus {
|
||||
outline: 3px solid var(--navds-text-focus);
|
||||
outline: 3px solid var(--navds-accordion-menu-outline-focus);
|
||||
outline-offset: -3px;
|
||||
color: var(--navds-color-darkgray);
|
||||
color: var(--navds-accordion-menu-color-text-focus);
|
||||
}
|
||||
|
||||
.navds-accordion-menu-collapsable__button:focus
|
||||
> .navds-accordion-menu-collapsable__expand-icon {
|
||||
color: var(--navds-accordion-menu-color-focus);
|
||||
}
|
||||
|
||||
.navds-accordion-menu-item:hover,
|
||||
.navds-accordion-menu-collapsable__button:hover {
|
||||
background-color: var(--navds-color-blue-10);
|
||||
background-color: var(--navds-accordion-menu-color-background-hover);
|
||||
}
|
||||
|
||||
.navds-accordion-menu-item--active {
|
||||
box-shadow: inset 0.5rem 0 var(--navds-color-text-link);
|
||||
color: var(--navds-color-text);
|
||||
color: var(--navds-accordion-menu-color-text-active);
|
||||
text-decoration: none;
|
||||
}
|
||||
@@ -1,82 +1,70 @@
|
||||
.ReactCollapse--collapse {
|
||||
transition: height 300ms cubic-bezier(0.4, 0, 0.2, 1);
|
||||
:root {
|
||||
--navds-accordion-color-text: var(--navds-color-darkgray);
|
||||
--navds-accordion-color-background: var(--navds-color-background);
|
||||
--navds-accordion-color-text-hover: var(--navds-color-blue-50);
|
||||
--navds-accordion-color-border-hover: var(--navds-color-blue-50);
|
||||
--navds-accordion-color-border-focus: var(--navds-color-background);
|
||||
}
|
||||
|
||||
.navds-accordion .ReactCollapse--collapse {
|
||||
transition: height 250ms cubic-bezier(0.4, 0, 0.2, 1);
|
||||
}
|
||||
|
||||
.navds-accordion {
|
||||
position: relative;
|
||||
background: var(--navds-color-background);
|
||||
border-bottom: 2px solid #c9c9c9;
|
||||
background: var(--navds-accordion-color-background);
|
||||
}
|
||||
|
||||
.navds-accordion:hover {
|
||||
/* color: black; */
|
||||
border-bottom: 2px solid var(--navds-color-blue-50);
|
||||
}
|
||||
|
||||
.navds-accordion:focus,
|
||||
.navds-accordion__button:focus {
|
||||
box-shadow: var(--navds-shadow-focus);
|
||||
.navds-accordion__header:focus {
|
||||
outline: none;
|
||||
box-shadow: var(--navds-shadow-focus);
|
||||
border-color: var(--navds-accordion-color-border-focus);
|
||||
}
|
||||
|
||||
.navds-accordion__chevron {
|
||||
width: 1.25em;
|
||||
height: 1.25em;
|
||||
transform: rotateZ(0deg);
|
||||
.navds-accordion__header:hover {
|
||||
color: var(--navds-accordion-color-text-hover);
|
||||
border-color: var(--navds-accordion-color-border-hover);
|
||||
text-decoration: underline;
|
||||
}
|
||||
|
||||
.navds-accordion__expand-icon {
|
||||
width: 1.5rem;
|
||||
height: 1.5rem;
|
||||
flex-shrink: 0;
|
||||
margin-left: var(--navds-spacing-4);
|
||||
}
|
||||
|
||||
.navds-accordion__chevron--up {
|
||||
transform: rotateZ(-180deg);
|
||||
.navds-accordion__expand-icon--flip {
|
||||
transform: rotateZ(180deg);
|
||||
}
|
||||
|
||||
.navds-accordion__chevron--down {
|
||||
transform: rotateZ(0deg);
|
||||
}
|
||||
|
||||
.navds-accordion__button {
|
||||
padding: var(--navds-spacing-4);
|
||||
.navds-accordion__header {
|
||||
padding: var(--navds-spacing-4) var(--navds-spacing-3);
|
||||
background: transparent;
|
||||
text-align: left;
|
||||
border: none;
|
||||
width: 100%;
|
||||
margin-bottom: 0;
|
||||
margin: 0;
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
color: var(--navds-color-text-link);
|
||||
}
|
||||
|
||||
.navds-accordion__button:hover .navds-accordion__heading {
|
||||
text-decoration: underline;
|
||||
color: var(--navds-color-text-link);
|
||||
border-bottom: 2px solid #a0a0a0;
|
||||
gap: var(--navds-spacing-4);
|
||||
}
|
||||
|
||||
.navds-accordion__content {
|
||||
padding: var(--navds-spacing-2) var(--navds-spacing-4) var(--navds-spacing-4);
|
||||
color: var(--navds-accordion-color-text);
|
||||
padding: var(--navds-spacing-5) var(--navds-spacing-3) var(--navds-spacing-10);
|
||||
}
|
||||
|
||||
.navds-accordion--open .navds-accordion__content {
|
||||
border-top-left-radius: 0;
|
||||
border-top-right-radius: 0;
|
||||
}
|
||||
|
||||
.navds-accordion--open > .navds-accordion__button {
|
||||
border-bottom-left-radius: 0;
|
||||
border-bottom-right-radius: 0;
|
||||
}
|
||||
|
||||
.navds-accordion__chevron--filled {
|
||||
.navds-accordion__expand-icon--filled {
|
||||
display: none;
|
||||
}
|
||||
|
||||
.navds-accordion__button:hover
|
||||
> .navds-accordion__chevron.navds-accordion__chevron--filled {
|
||||
.navds-accordion__header:hover
|
||||
> .navds-accordion__expand-icon.navds-accordion__expand-icon--filled {
|
||||
display: inherit;
|
||||
}
|
||||
|
||||
.navds-accordion__button:hover > .navds-accordion__chevron {
|
||||
.navds-accordion__header:hover > .navds-accordion__expand-icon {
|
||||
display: none;
|
||||
}
|
||||
+86
-51
@@ -1,84 +1,119 @@
|
||||
:root {
|
||||
--navds-alert-color-border: var(--navds-color-gray-40);
|
||||
--navds-alert-color-error-border: var(--navds-color-error-border);
|
||||
--navds-alert-color-error-background: var(--navds-color-error-background);
|
||||
--navds-alert-color-warning-border: var(--navds-color-warning-border);
|
||||
--navds-alert-color-warning-background: var(--navds-color-warning-background);
|
||||
--navds-alert-color-info-border: var(--navds-color-info-border);
|
||||
--navds-alert-color-info-background: var(--navds-color-info-background);
|
||||
--navds-alert-color-success-border: var(--navds-color-success-border);
|
||||
--navds-alert-color-success-background: var(--navds-color-success-background);
|
||||
--navds-alert-color-error-icon: var(--navds-color-red-60);
|
||||
--navds-alert-color-error-icon-background: var(--navds-color-white);
|
||||
--navds-alert-color-warning-icon: var(--navds-color-orange-40);
|
||||
--navds-alert-color-warning-icon-background: var(--navds-color-darkgray);
|
||||
--navds-alert-color-info-icon: var(--navds-color-lightblue-70);
|
||||
--navds-alert-color-info-icon-background: var(--navds-color-white);
|
||||
--navds-alert-color-success-icon: var(--navds-color-green-70);
|
||||
--navds-alert-color-success-icon-background: var(--navds-color-white);
|
||||
}
|
||||
|
||||
.navds-alert {
|
||||
border-radius: 4px;
|
||||
border: var(--navds-border-default);
|
||||
|
||||
/* Padding calculated based on 18px font for 64px tall alert */
|
||||
padding: var(--navds-spacing-4) var(--navds-spacing-4);
|
||||
display: grid;
|
||||
grid-auto-flow: column;
|
||||
justify-content: start;
|
||||
min-height: 64px;
|
||||
box-sizing: border-box;
|
||||
border: 1px solid;
|
||||
border-color: var(--navds-alert-color-border);
|
||||
padding: calc(var(--navds-spacing-4) + 1px) calc(var(--navds-spacing-4) + 1px);
|
||||
display: flex;
|
||||
gap: var(--navds-spacing-3);
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.navds-alert--s {
|
||||
padding: var(--navds-spacing-1) var(--navds-spacing-4);
|
||||
min-height: 32px;
|
||||
.navds-alert__wrapper {
|
||||
max-width: 43.5rem;
|
||||
}
|
||||
|
||||
.navds-alert > span > svg {
|
||||
margin-right: var(--navds-spacing-3);
|
||||
font-size: 1.5rem;
|
||||
.navds-alert--small {
|
||||
padding: calc(var(--navds-spacing-1) - 1px) var(--navds-spacing-4);
|
||||
}
|
||||
|
||||
.navds-alert--full-width {
|
||||
border-radius: 0;
|
||||
}
|
||||
|
||||
.navds-alert > .navds-alert__icon {
|
||||
flex-shrink: 0;
|
||||
font-size: 1.5rem;
|
||||
align-self: flex-start;
|
||||
height: var(--navds-font-line-height-xl);
|
||||
}
|
||||
|
||||
.navds-alert--small > .navds-alert__icon {
|
||||
font-size: 1.25rem;
|
||||
height: var(--navds-font-line-height-l);
|
||||
}
|
||||
|
||||
.navds-alert--error {
|
||||
border-color: var(--navds-alert-color-error-border);
|
||||
background-color: var(--navds-alert-color-error-background);
|
||||
}
|
||||
|
||||
.navds-alert--error > .navds-alert__icon {
|
||||
color: var(--navds-alert-color-error-icon);
|
||||
background: radial-gradient(
|
||||
circle,
|
||||
var(--navds-color-background) 50%,
|
||||
var(--navds-alert-color-error-icon-background) 50%,
|
||||
0,
|
||||
transparent
|
||||
);
|
||||
}
|
||||
|
||||
.navds-alert > div {
|
||||
display: block;
|
||||
margin: auto 0;
|
||||
max-width: 43.5rem;
|
||||
flex: 1;
|
||||
}
|
||||
|
||||
.navds-alert > span {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
max-height: calc(var(--navds-spacing-8) - 2px);
|
||||
}
|
||||
|
||||
.navds-alert--error {
|
||||
border-color: var(--navds-color-error-border);
|
||||
background-color: var(--navds-color-error-background);
|
||||
}
|
||||
|
||||
.navds-alert--error > span > svg {
|
||||
color: var(--navds-color-red-60);
|
||||
}
|
||||
|
||||
.navds-alert--warning {
|
||||
border-color: var(--navds-color-warning-border);
|
||||
background-color: var(--navds-color-warning-background);
|
||||
border-color: var(--navds-alert-color-warning-border);
|
||||
background-color: var(--navds-alert-color-warning-background);
|
||||
}
|
||||
|
||||
.navds-alert--warning > span > svg {
|
||||
color: var(--navds-color-orange-40);
|
||||
.navds-alert--warning > .navds-alert__icon {
|
||||
color: var(--navds-alert-color-warning-icon);
|
||||
background: radial-gradient(
|
||||
circle,
|
||||
var(--navds-color-darkgray) 50%,
|
||||
var(--navds-alert-color-warning-icon-background) 50%,
|
||||
0,
|
||||
transparent
|
||||
);
|
||||
}
|
||||
|
||||
.navds-alert--info {
|
||||
border-color: var(--navds-color-info-border);
|
||||
background-color: var(--navds-color-info-background);
|
||||
border-color: var(--navds-alert-color-info-border);
|
||||
background-color: var(--navds-alert-color-info-background);
|
||||
}
|
||||
|
||||
.navds-alert--info > span > svg {
|
||||
color: var(--navds-color-lightblue-70);
|
||||
.navds-alert--info > .navds-alert__icon {
|
||||
color: var(--navds-alert-color-info-icon);
|
||||
background: radial-gradient(
|
||||
circle,
|
||||
var(--navds-alert-color-info-icon-background) 50%,
|
||||
0,
|
||||
transparent
|
||||
);
|
||||
}
|
||||
|
||||
.navds-alert--success {
|
||||
border-color: var(--navds-color-success-border);
|
||||
background-color: var(--navds-color-success-background);
|
||||
border-color: var(--navds-alert-color-success-border);
|
||||
background-color: var(--navds-alert-color-success-background);
|
||||
}
|
||||
|
||||
.navds-alert--success > span > svg {
|
||||
color: var(--navds-color-green-70);
|
||||
.navds-alert--success > .navds-alert__icon {
|
||||
color: var(--navds-alert-color-success-icon);
|
||||
background: radial-gradient(
|
||||
circle,
|
||||
var(--navds-alert-color-success-icon-background) 50%,
|
||||
0,
|
||||
transparent
|
||||
);
|
||||
}
|
||||
|
||||
.navds-alert--inline {
|
||||
background-color: transparent;
|
||||
border-color: transparent;
|
||||
padding: 0;
|
||||
}
|
||||
@@ -9,7 +9,8 @@
|
||||
* https://medium.com/@jessebeach/beware-smushed-off-screen-accessible-text-5952a4c2cbfe
|
||||
*/
|
||||
|
||||
.sr-only {
|
||||
.sr-only,
|
||||
.navds-sr-only {
|
||||
border: 0;
|
||||
clip: rect(0, 0, 0, 0);
|
||||
height: 1px;
|
||||
@@ -32,7 +33,9 @@
|
||||
*/
|
||||
|
||||
.sr-only.focusable:active,
|
||||
.sr-only.focusable:focus {
|
||||
.sr-only.focusable:focus,
|
||||
.navds-sr-only.focusable:active,
|
||||
.navds-sr-only.focusable:focus {
|
||||
clip: auto;
|
||||
height: auto;
|
||||
margin: 0;
|
||||
|
||||
+154
-87
@@ -1,47 +1,73 @@
|
||||
:root {
|
||||
/* Primary */
|
||||
--navds-button-color-primary-text: var(--navds-color-white);
|
||||
--navds-button-color-primary-border-focus: var(--navds-color-white);
|
||||
--navds-button-color-primary-background: var(--navds-color-action-default);
|
||||
--navds-button-color-primary-background-hover: var(
|
||||
--navds-color-action-hover
|
||||
);
|
||||
--navds-button-color-primary-background-active: var(
|
||||
--navds-color-action-active
|
||||
);
|
||||
|
||||
/* Secondary */
|
||||
--navds-button-color-secondary-text: var(--navds-color-action-default);
|
||||
--navds-button-color-secondary-text-hover: var(--navds-color-text-inverse);
|
||||
--navds-button-color-secondary-text-active: var(--navds-color-text-inverse);
|
||||
--navds-button-color-secondary-border: var(--navds-color-action-default);
|
||||
--navds-button-color-secondary-border-focus-active-hover: var(
|
||||
--navds-color-white
|
||||
);
|
||||
--navds-button-color-secondary-background: var(--navds-color-background);
|
||||
--navds-button-color-secondary-background-hover: var(
|
||||
--navds-color-action-hover
|
||||
);
|
||||
--navds-button-color-secondary-background-active: var(
|
||||
--navds-color-action-active
|
||||
);
|
||||
|
||||
/* Tertiary */
|
||||
--navds-button-color-tertiary-text: var(--navds-color-action-default);
|
||||
--navds-button-color-tertiary-text-active: var(--navds-color-text-inverse);
|
||||
--navds-button-color-tertiary-border-hover: var(--navds-color-action-default);
|
||||
--navds-button-color-tertiary-border-focus: var(--navds-color-action-default);
|
||||
--navds-button-color-tertiary-border-active: var(--navds-color-white);
|
||||
--navds-button-color-tertiary-background-active: var(
|
||||
--navds-color-action-active
|
||||
);
|
||||
|
||||
/* Danger */
|
||||
--navds-button-color-danger-text: var(--navds-color-white);
|
||||
--navds-button-color-danger-background: var(--navds-color-danger-default);
|
||||
--navds-button-color-danger-background-hover: var(--navds-color-danger-hover);
|
||||
--navds-button-color-danger-background-active: var(
|
||||
--navds-color-danger-active
|
||||
);
|
||||
--navds-button-color-danger-border-focus: var(--navds-color-white);
|
||||
|
||||
/* Disabled */
|
||||
--navds-button-color-text-disabled: var(--navds-color-text-inverse);
|
||||
--navds-button-color-background-disabled: var(--navds-color-disabled);
|
||||
}
|
||||
|
||||
.navds-button {
|
||||
display: inline-flex;
|
||||
cursor: pointer;
|
||||
background-color: var(--navds-color-background);
|
||||
color: var(--navds-color-action-default);
|
||||
margin: 0;
|
||||
text-align: center;
|
||||
text-decoration: none;
|
||||
border-color: var(--navds-color-action-default);
|
||||
border: none;
|
||||
background: none;
|
||||
border-radius: 2px;
|
||||
border-style: solid;
|
||||
border-width: 2px;
|
||||
min-height: 48px;
|
||||
align-items: center;
|
||||
|
||||
/* Padding calculated based on 18px font for 44px tall button */
|
||||
padding: calc(var(--navds-spacing-3) - 2px) var(--navds-spacing-3);
|
||||
min-width: 48px;
|
||||
padding: var(--navds-spacing-3);
|
||||
flex-shrink: 0;
|
||||
}
|
||||
|
||||
.navds-button > svg {
|
||||
font-size: 1.5rem;
|
||||
width: 1.5rem;
|
||||
height: 1.5rem;
|
||||
}
|
||||
|
||||
.navds-button--s > svg {
|
||||
font-size: 1.25rem;
|
||||
width: 1.25rem;
|
||||
height: 1.25rem;
|
||||
}
|
||||
|
||||
.navds-button > svg + *:not(.sr-only),
|
||||
.navds-button > *:not(.sr-only) + svg {
|
||||
margin-left: 0.5rem;
|
||||
}
|
||||
|
||||
/* .navds-button:last-child {
|
||||
margin-left: 0.5rem;
|
||||
} */
|
||||
|
||||
.navds-button--s {
|
||||
/* Padding calculated based on 16px font for 32px tall button */
|
||||
padding: 0.25rem calc(var(--navds-spacing-4) - 2px);
|
||||
min-height: 32px;
|
||||
.navds-button--small {
|
||||
padding-top: 0.375rem;
|
||||
padding-bottom: 0.375rem;
|
||||
min-width: 32px;
|
||||
}
|
||||
|
||||
.navds-button:focus {
|
||||
@@ -49,94 +75,135 @@
|
||||
box-shadow: var(--navds-shadow-focus);
|
||||
}
|
||||
|
||||
/**************************
|
||||
* .navds-button--primary *
|
||||
**************************/
|
||||
|
||||
.navds-button--primary:hover,
|
||||
.navds-button--primary:active {
|
||||
color: var(--navds-color-text-inverse);
|
||||
background-color: var(--navds-color-action-hover);
|
||||
border-color: transparent;
|
||||
.navds-button__inner {
|
||||
margin: auto;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
gap: var(--navds-spacing-2);
|
||||
}
|
||||
|
||||
.navds-button--primary:active {
|
||||
background-color: var(--navds-color-action-active);
|
||||
.navds-button svg {
|
||||
font-size: 1.5rem;
|
||||
}
|
||||
|
||||
/****************************
|
||||
.navds-button--small svg {
|
||||
font-size: 1.25rem;
|
||||
}
|
||||
|
||||
/*************************
|
||||
* .navds-button--primary *
|
||||
*************************/
|
||||
|
||||
.navds-button--primary {
|
||||
background-color: var(--navds-button-color-primary-background);
|
||||
color: var(--navds-button-color-primary-text);
|
||||
}
|
||||
|
||||
.navds-button--primary:hover {
|
||||
background-color: var(--navds-button-color-primary-background-hover);
|
||||
}
|
||||
|
||||
.navds-button--primary:active {
|
||||
background-color: var(--navds-button-color-primary-background-active);
|
||||
}
|
||||
|
||||
.navds-button--primary:focus {
|
||||
box-shadow: inset 0 0 0 1px var(--navds-button-color-primary-border-focus),
|
||||
var(--navds-shadow-focus);
|
||||
}
|
||||
|
||||
/**************************
|
||||
* .navds-button--secondary *
|
||||
****************************/
|
||||
**************************/
|
||||
|
||||
.navds-button--secondary {
|
||||
border-color: transparent;
|
||||
background-color: transparent;
|
||||
color: var(--navds-button-color-secondary-text);
|
||||
background-color: var(--navds-button-color-secondary-background);
|
||||
box-shadow: inset 0 0 0 2px var(--navds-button-color-secondary-border);
|
||||
}
|
||||
|
||||
.navds-button--secondary:hover {
|
||||
color: var(--navds-button-color-secondary-text-hover);
|
||||
background-color: var(--navds-button-color-secondary-background-hover);
|
||||
box-shadow: none;
|
||||
}
|
||||
|
||||
.navds-button--secondary:hover,
|
||||
.navds-button--secondary:focus {
|
||||
border-color: var(--navds-color-action-default);
|
||||
box-shadow: inset 0 0 0 2px var(--navds-button-color-secondary-border),
|
||||
var(--navds-shadow-focus);
|
||||
}
|
||||
|
||||
.navds-button--secondary:active {
|
||||
color: var(--navds-color-text-inverse);
|
||||
border-color: var(--navds-color-action-active);
|
||||
background-color: var(--navds-color-action-active);
|
||||
color: var(--navds-button-color-secondary-text-active);
|
||||
background-color: var(--navds-button-color-secondary-background-active);
|
||||
box-shadow: none;
|
||||
}
|
||||
|
||||
.navds-button--secondary:focus:hover,
|
||||
.navds-button--secondary:focus:active {
|
||||
box-shadow: inset 0 0 0 1px
|
||||
var(--navds-button-color-secondary-border-focus-active-hover),
|
||||
var(--navds-shadow-focus);
|
||||
}
|
||||
|
||||
/****************************
|
||||
* .navds-button--tertiary *
|
||||
****************************/
|
||||
|
||||
.navds-button--tertiary {
|
||||
color: var(--navds-button-color-tertiary-text);
|
||||
}
|
||||
|
||||
.navds-button--tertiary:hover {
|
||||
box-shadow: inset 0 0 0 2px var(--navds-button-color-tertiary-border-hover);
|
||||
}
|
||||
|
||||
.navds-button--tertiary:focus {
|
||||
box-shadow: inset 0 0 0 2px var(--navds-button-color-tertiary-border-focus),
|
||||
var(--navds-shadow-focus);
|
||||
}
|
||||
|
||||
.navds-button--tertiary:active {
|
||||
color: var(--navds-button-color-tertiary-text-active);
|
||||
background-color: var(--navds-button-color-tertiary-background-active);
|
||||
box-shadow: inset 0 0 0 1px var(--navds-button-color-tertiary-border-active);
|
||||
}
|
||||
|
||||
.navds-button--tertiary:active:focus {
|
||||
box-shadow: inset 0 0 0 1px var(--navds-button-color-tertiary-border-active),
|
||||
var(--navds-shadow-focus);
|
||||
}
|
||||
|
||||
/*************************
|
||||
* .navds-button--action *
|
||||
* .navds-button--danger *
|
||||
*************************/
|
||||
|
||||
.navds-button--action {
|
||||
background-color: var(--navds-color-action-default);
|
||||
border-color: var(--navds-color-action-default);
|
||||
}
|
||||
|
||||
.navds-button--danger {
|
||||
background-color: var(--navds-color-danger-default);
|
||||
border-color: var(--navds-color-danger-default);
|
||||
}
|
||||
|
||||
.navds-button--action,
|
||||
.navds-button--danger {
|
||||
color: white;
|
||||
border-width: 1px;
|
||||
}
|
||||
|
||||
.navds-button--action:hover {
|
||||
background-color: var(--navds-color-action-hover);
|
||||
border-color: var(--navds-color-action-hover);
|
||||
background-color: var(--navds-button-color-danger-background);
|
||||
color: var(--navds-button-color-danger-text);
|
||||
}
|
||||
|
||||
.navds-button--danger:hover {
|
||||
background-color: var(--navds-color-danger-hover);
|
||||
border-color: var(--navds-color-danger-hover);
|
||||
}
|
||||
|
||||
.navds-button--action:active {
|
||||
background-color: var(--navds-color-action-active);
|
||||
background-color: var(--navds-button-color-danger-background-hover);
|
||||
}
|
||||
|
||||
.navds-button--danger:active {
|
||||
background-color: var(--navds-color-danger-active);
|
||||
background-color: var(--navds-button-color-danger-background-active);
|
||||
}
|
||||
|
||||
.navds-button--action:focus,
|
||||
.navds-button--danger:focus {
|
||||
border-color: white;
|
||||
box-shadow: inset 0 0 0 1px var(--navds-button-color-danger-border-focus),
|
||||
var(--navds-shadow-focus);
|
||||
}
|
||||
|
||||
/**************************
|
||||
* .navds-button:disabled *
|
||||
**************************/
|
||||
|
||||
.navds-button:disabled:disabled {
|
||||
background-color: var(--navds-color-disabled);
|
||||
color: var(--navds-color-text-inverse);
|
||||
.navds-button:disabled {
|
||||
color: var(--navds-button-color-text-disabled);
|
||||
background-color: var(--navds-button-color-background-disabled);
|
||||
cursor: not-allowed;
|
||||
border-width: 0;
|
||||
box-shadow: none;
|
||||
transform: none;
|
||||
}
|
||||
+25
-11
@@ -1,31 +1,45 @@
|
||||
:root {
|
||||
--navds-card-micro-color-text: var(--navds-color-text-primary);
|
||||
--navds-card-micro-color-background: var(--navds-color-orange-20);
|
||||
--navds-card-micro-color-border: transparent;
|
||||
--navds-card-micro-color-text-hover: var(--navds-color-blue-50);
|
||||
--navds-card-micro-color-background-hover: var(--navds-color-white);
|
||||
--navds-card-micro-color-border-hover: var(--navds-color-blue-50);
|
||||
--navds-card-micro-color-text-focus: var(--navds-color-blue-50);
|
||||
--navds-card-micro-color-background-focus: var(--navds-color-white);
|
||||
--navds-card-micro-color-shadow-focus: var(--navds-color-blue-80);
|
||||
--navds-card-micro-color-background-active: var(--navds-color-blue-70);
|
||||
--navds-card-micro-color-text-active: var(--navds-color-white);
|
||||
}
|
||||
|
||||
/*
|
||||
MicroCard
|
||||
*/
|
||||
|
||||
.navds-card__micro {
|
||||
border-radius: 1rem;
|
||||
color: var(--navds-color-text-primary);
|
||||
color: var(--navds-card-micro-color-text);
|
||||
display: inline-flex;
|
||||
padding: var(--navds-spacing-1) var(--navds-spacing-2);
|
||||
text-decoration: none;
|
||||
background-color: var(--navds-color-orange-20);
|
||||
border: 1px solid transparent;
|
||||
background-color: var(--navds-card-micro-color-background);
|
||||
border: 1px solid var(--navds-card-micro-color-border);
|
||||
}
|
||||
|
||||
.navds-card__micro:hover {
|
||||
background-color: var(--navds-color-white);
|
||||
border-color: var(--navds-color-blue-50);
|
||||
color: var(--navds-color-blue-50);
|
||||
background-color: var(--navds-card-micro-color-background-hover);
|
||||
border-color: var(--navds-card-micro-color-border-hover);
|
||||
color: var(--navds-card-micro-color-text-hover);
|
||||
}
|
||||
|
||||
.navds-card__micro:focus {
|
||||
background-color: var(--navds-color-white);
|
||||
color: var(--navds-color-blue-50);
|
||||
background-color: var(--navds-card-micro-color-background-focus);
|
||||
color: var(--navds-card-micro-color-text-focus);
|
||||
outline: none;
|
||||
box-shadow: var(--navds-shadow-focus);
|
||||
box-shadow: 0 0 0 3px var(--navds-card-micro-color-shadow-focus);
|
||||
}
|
||||
|
||||
.navds-card__micro:active {
|
||||
background-color: var(--navds-color-blue-70);
|
||||
color: var(--navds-color-white);
|
||||
background-color: var(--navds-card-micro-color-background-active);
|
||||
color: var(--navds-card-micro-color-text-active);
|
||||
}
|
||||
@@ -1,11 +1,3 @@
|
||||
.navds-copy-to-clipboard {
|
||||
display: inline-flex;
|
||||
align-items: center;
|
||||
column-gap: 0.5em;
|
||||
padding: var(--navds-spacing-1);
|
||||
min-height: 32px;
|
||||
}
|
||||
|
||||
.navds-copy-to-clipboard__popover {
|
||||
padding: var(--navds-spacing-1);
|
||||
}
|
||||
@@ -1,13 +1,13 @@
|
||||
.navds-checkbox-group--s > .navds-checkboxes {
|
||||
.navds-checkbox-group--small > .navds-checkboxes {
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
gap: 4px;
|
||||
}
|
||||
|
||||
.navds-fieldset.navds-checkbox-group--m > .navds-checkboxes {
|
||||
.navds-fieldset.navds-checkbox-group--medium > .navds-checkboxes {
|
||||
margin-top: 0;
|
||||
}
|
||||
|
||||
.navds-fieldset.navds-checkbox-group--m > .navds-fieldset__error {
|
||||
.navds-fieldset.navds-checkbox-group--medium > .navds-fieldset__error {
|
||||
margin-top: 0;
|
||||
}
|
||||
@@ -1,3 +1,25 @@
|
||||
:root {
|
||||
--navds-checkbox-color-background: var(--navds-color-white);
|
||||
--navds-checkbox-color-border: var(--navds-color-gray-60);
|
||||
--navds-checkbox-color-label-hover: var(--navds-color-blue-50);
|
||||
--navds-checkbox-color-border-hover: var(--navds-color-blue-50);
|
||||
--navds-checkbox-color-background-hover: var(--navds-color-blue-10);
|
||||
--navds-checkbox-color-description: var(--navds-color-gray-80);
|
||||
--navds-checkbox-color-border-checked: var(--navds-color-blue-50);
|
||||
--navds-checkbox-color-background-checked: var(--navds-color-blue-50);
|
||||
--navds-checkbox-color-shadow-error: var(--navds-color-red-50);
|
||||
--navds-checkbox-color-border-error: var(--navds-color-red-50);
|
||||
|
||||
/* Disabled */
|
||||
--navds-checkbox-color-label-disabled: var(--navds-color-gray-40);
|
||||
--navds-checkbox-color-border-disabled: var(--navds-color-gray-60);
|
||||
--navds-checkbox-color-background-disabled: var(--navds-color-gray-10);
|
||||
--navds-checkbox-color-border-checked-disabled: var(--navds-color-gray-40);
|
||||
--navds-checkbox-color-background-checked-disabled: var(
|
||||
--navds-color-gray-40
|
||||
);
|
||||
}
|
||||
|
||||
.navds-checkbox {
|
||||
position: relative;
|
||||
padding: var(--navds-spacing-3) 0;
|
||||
@@ -24,7 +46,7 @@
|
||||
|
||||
.navds-checkbox__description {
|
||||
padding-left: calc(48px - 12px);
|
||||
color: var(--navds-color-gray-80);
|
||||
color: var(--navds-checkbox-color-description);
|
||||
}
|
||||
|
||||
.navds-checkbox--with-description {
|
||||
@@ -45,37 +67,37 @@
|
||||
|
||||
.navds-checkbox__label::before {
|
||||
content: "";
|
||||
background-color: white;
|
||||
border: 1px solid var(--navds-color-border);
|
||||
background-color: var(--navds-checkbox-color-background);
|
||||
border: 1px solid var(--navds-checkbox-color-border);
|
||||
width: 1.5rem;
|
||||
height: 1.5rem;
|
||||
border-radius: 4px;
|
||||
flex-shrink: 0;
|
||||
}
|
||||
|
||||
.navds-checkbox--s {
|
||||
.navds-checkbox--small {
|
||||
padding: var(--navds-spacing-1) 0;
|
||||
}
|
||||
|
||||
.navds-checkbox--s > .navds-checkbox__input {
|
||||
.navds-checkbox--small > .navds-checkbox__input {
|
||||
width: 24px;
|
||||
height: 24px;
|
||||
top: 2px;
|
||||
left: 0;
|
||||
}
|
||||
|
||||
.navds-checkbox--s > .navds-checkbox__label::before {
|
||||
.navds-checkbox--small > .navds-checkbox__label::before {
|
||||
margin-top: -2px;
|
||||
margin-bottom: -2px;
|
||||
}
|
||||
|
||||
.navds-checkbox__input:hover + .navds-checkbox__label {
|
||||
color: var(--navds-color-blue-50);
|
||||
color: var(--navds-checkbox-color-label-hover);
|
||||
}
|
||||
|
||||
.navds-checkbox__input:hover + .navds-checkbox__label::before {
|
||||
border-color: var(--navds-color-blue-50);
|
||||
background-color: var(--navds-color-blue-10);
|
||||
border-color: var(--navds-checkbox-color-border-hover);
|
||||
background-color: var(--navds-checkbox-color-background-hover);
|
||||
}
|
||||
|
||||
.navds-checkbox__input:focus + .navds-checkbox__label::before {
|
||||
@@ -87,8 +109,8 @@
|
||||
background-position: center center;
|
||||
background-repeat: no-repeat;
|
||||
background-size: 75%;
|
||||
border: 2px solid var(--navds-color-blue-50);
|
||||
background-color: var(--navds-color-blue-50);
|
||||
border: 2px solid var(--navds-checkbox-color-border-checked);
|
||||
background-color: var(--navds-checkbox-color-background-checked);
|
||||
}
|
||||
|
||||
.navds-checkbox__input:checked:focus + .navds-checkbox__label::before {
|
||||
@@ -99,26 +121,26 @@
|
||||
.navds-checkbox--error
|
||||
> .navds-checkbox__input:not(:hover):not(:focus):not(:disabled):not(:checked)
|
||||
+ .navds-checkbox__label::before {
|
||||
box-shadow: 0 0 0 1px var(--navds-color-red-50);
|
||||
border-color: var(--navds-color-red-50);
|
||||
box-shadow: 0 0 0 1px var(--navds-checkbox-color-shadow-error);
|
||||
border-color: var(--navds-checkbox-color-border-error);
|
||||
}
|
||||
|
||||
.navds-checkbox--s .navds-error-message {
|
||||
.navds-checkbox--small .navds-error-message {
|
||||
margin-top: 4px;
|
||||
}
|
||||
|
||||
.navds-checkbox__input:disabled,
|
||||
.navds-checkbox__input:disabled + .navds-checkbox__label {
|
||||
color: var(--navds-color-gray-40);
|
||||
color: var(--navds-checkbox-color-label-disabled);
|
||||
cursor: not-allowed;
|
||||
}
|
||||
|
||||
.navds-checkbox__input:disabled + .navds-checkbox__label::before {
|
||||
background-color: var(--navds-color-gray-10);
|
||||
border-color: var(--navds-color-gray-60);
|
||||
background-color: var(--navds-checkbox-color-background-disabled);
|
||||
border-color: var(--navds-checkbox-color-border-disabled);
|
||||
}
|
||||
|
||||
.navds-checkbox__input:disabled:checked + .navds-checkbox__label::before {
|
||||
background-color: var(--navds-color-gray-40);
|
||||
border-color: var(--navds-color-gray-40);
|
||||
background-color: var(--navds-checkbox-color-background-checked-disabled);
|
||||
border-color: var(--navds-checkbox-color-border-checked-disabled);
|
||||
}
|
||||
@@ -1,10 +1,40 @@
|
||||
:root {
|
||||
--navds-confirmation-panel-color-background: var(
|
||||
--navds-color-warning-background
|
||||
);
|
||||
--navds-confirmation-panel-color-background-checked: var(
|
||||
--navds-color-success-background
|
||||
);
|
||||
--navds-confirmation-panel-color-border-checked: var(
|
||||
--navds-color-success-background
|
||||
);
|
||||
--navds-confirmation-panel-color-background-error: var(
|
||||
--navds-color-error-background
|
||||
);
|
||||
--navds-confirmation-panel-color-checkbox-background-checked-hover: var(
|
||||
--navds-color-green-70
|
||||
);
|
||||
--navds-confirmation-panel-color-checkbox-border-checked-hover: var(
|
||||
--navds-color-green-70
|
||||
);
|
||||
--navds-confirmation-panel-color-checkbox-background-checked: var(
|
||||
--navds-color-green-50
|
||||
);
|
||||
--navds-confirmation-panel-color-checkbox-border-checked: var(
|
||||
--navds-color-green-50
|
||||
);
|
||||
--navds-confirmation-panel-color-checkbox-label-checked: var(
|
||||
--navds-color-darkgray
|
||||
);
|
||||
}
|
||||
|
||||
.navds-confirmation-panel {
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
gap: var(--navds-spacing-4);
|
||||
padding: var(--navds-spacing-4);
|
||||
border-radius: 4px;
|
||||
background-color: #ffeccc;
|
||||
background-color: var(--navds-confirmation-panel-color-background);
|
||||
transition: background-color linear 100ms;
|
||||
}
|
||||
|
||||
@@ -12,27 +42,21 @@
|
||||
max-width: 80ch;
|
||||
}
|
||||
|
||||
.navds-confirmation-panel--s {
|
||||
.navds-confirmation-panel--small {
|
||||
padding: var(--navds-spacing-3);
|
||||
gap: var(--navds-spacing-2);
|
||||
}
|
||||
|
||||
.navds-confirmation-panel--checked {
|
||||
background-color: #ccf1d6;
|
||||
border-color: #ccf1d6;
|
||||
background-color: var(--navds-confirmation-panel-color-background-checked);
|
||||
border-color: var(--navds-confirmation-panel-color-border-checked);
|
||||
}
|
||||
|
||||
.navds-confirmation-panel--error {
|
||||
background-color: #f3e3e3;
|
||||
background-color: var(--navds-confirmation-panel-color-background-error);
|
||||
border: 1px solid transparent;
|
||||
}
|
||||
|
||||
.navds-confirmation-panel--checked
|
||||
> .navds-confirmation-panel__content
|
||||
.navds-link:not(:focus) {
|
||||
color: var(--navds-color-darkgray);
|
||||
}
|
||||
|
||||
.navds-confirmation-panel
|
||||
.navds-checkbox__input:hover
|
||||
+ .navds-checkbox__label {
|
||||
@@ -42,23 +66,29 @@
|
||||
.navds-confirmation-panel--checked
|
||||
.navds-checkbox__input:hover
|
||||
+ .navds-checkbox__label {
|
||||
color: var(--navds-color-darkgray);
|
||||
color: var(--navds-confirmation-panel-color-checkbox-label-checked);
|
||||
}
|
||||
|
||||
.navds-confirmation-panel--checked
|
||||
.navds-checkbox__input
|
||||
+ .navds-checkbox__label::before {
|
||||
transition: none;
|
||||
background-color: var(--navds-color-green-50);
|
||||
border-color: var(--navds-color-green-50);
|
||||
background-color: var(
|
||||
--navds-confirmation-panel-color-checkbox-background-checked
|
||||
);
|
||||
border-color: var(--navds-confirmation-panel-color-checkbox-border-checked);
|
||||
background-image: var(--navds-checkmark-image-white);
|
||||
}
|
||||
|
||||
.navds-confirmation-panel--checked
|
||||
.navds-checkbox__input:hover
|
||||
+ .navds-checkbox__label::before {
|
||||
background-color: var(--navds-color-green-70);
|
||||
border-color: var(--navds-color-green-70);
|
||||
background-color: var(
|
||||
--navds-confirmation-panel-color-checkbox-background-checked-hover
|
||||
);
|
||||
border-color: var(
|
||||
--navds-confirmation-panel-color-checkbox-border-checked-hover
|
||||
);
|
||||
}
|
||||
|
||||
.navds-confirmation-panel--checked
|
||||
|
||||
@@ -1,4 +1,8 @@
|
||||
:root {
|
||||
--navds-error-message-color-text: var(--navds-color-text-error);
|
||||
}
|
||||
|
||||
.navds-error-message {
|
||||
display: block;
|
||||
color: var(--navds-color-red-50);
|
||||
color: var(--navds-error-message-color-text);
|
||||
}
|
||||
@@ -1,10 +1,15 @@
|
||||
.navds-error-summary {
|
||||
background-color: #fff;
|
||||
padding: var(--navds-spacing-4);
|
||||
border: 4px solid #ba3a26;
|
||||
:root {
|
||||
--navds-error-summary-color-background: var(--navds-color-white);
|
||||
--navds-error-summary-color-border: var(--navds-color-error-border);
|
||||
}
|
||||
|
||||
.navds-error-summary--s {
|
||||
.navds-error-summary {
|
||||
background-color: var(--navds-error-summary-color-background);
|
||||
padding: var(--navds-spacing-4);
|
||||
border: 4px solid var(--navds-error-summary-color-border);
|
||||
}
|
||||
|
||||
.navds-error-summary--small {
|
||||
padding: var(--navds-spacing-2);
|
||||
}
|
||||
|
||||
@@ -20,6 +25,6 @@
|
||||
gap: 0.25rem;
|
||||
}
|
||||
|
||||
.navds-error-summary--s > .navds-error-summary__list {
|
||||
.navds-error-summary--small > .navds-error-summary__list {
|
||||
margin: 0.5rem 0;
|
||||
}
|
||||
@@ -9,7 +9,7 @@
|
||||
margin-top: 8px;
|
||||
}
|
||||
|
||||
.navds-fieldset--s > :not(:first-child):not(:empty) {
|
||||
.navds-fieldset--small > :not(:first-child):not(:empty) {
|
||||
margin-top: 4px;
|
||||
}
|
||||
|
||||
|
||||
@@ -3,8 +3,8 @@
|
||||
margin-top: 8px;
|
||||
}
|
||||
|
||||
.navds-form-field--s > :not(:first-child):not(:empty),
|
||||
.navds-form-field--s > input:not(:first-child) {
|
||||
.navds-form-field--small > :not(:first-child):not(:empty),
|
||||
.navds-form-field--small > input:not(:first-child) {
|
||||
margin-top: 4px;
|
||||
}
|
||||
|
||||
|
||||
@@ -1,13 +1,13 @@
|
||||
.navds-radio-group--s > .navds-radio-buttons {
|
||||
.navds-radio-group--small > .navds-radio-buttons {
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
gap: 4px;
|
||||
}
|
||||
|
||||
.navds-fieldset.navds-radio-group--m > .navds-radio-buttons {
|
||||
.navds-fieldset.navds-radio-group--medium > .navds-radio-buttons {
|
||||
margin-top: 0;
|
||||
}
|
||||
|
||||
.navds-fieldset.navds-radio-group--m > .navds-fieldset__error {
|
||||
.navds-fieldset.navds-radio-group--medium > .navds-fieldset__error {
|
||||
margin-top: 0;
|
||||
}
|
||||
@@ -1,3 +1,27 @@
|
||||
:root {
|
||||
--navds-radio-color-description: var(--navds-color-gray-80);
|
||||
--navds-radio-color-background: var(--navds-color-white);
|
||||
--navds-radio-color-border: var(--navds-color-gray-60);
|
||||
--navds-radio-color-label-hover: var(--navds-color-blue-50);
|
||||
--navds-radio-color-border-hover: var(--navds-color-blue-50);
|
||||
--navds-radio-color-background-hover: var(--navds-color-blue-10);
|
||||
--navds-radio-color-border-checked: var(--navds-color-blue-50);
|
||||
--navds-radio-color-shadow-checked: var(--navds-color-blue-50);
|
||||
--navds-radio-color-shadow-checked-focus: var(--navds-color-blue-80);
|
||||
--navds-radio-color-shadow-background-checked-focus: var(--navds-color-white);
|
||||
--navds-radio-color-shadow-dot-checked-focus: var(--navds-color-blue-50);
|
||||
--navds-radio-color-shadow-error: var(--navds-color-red-50);
|
||||
--navds-radio-color-border-error: var(--navds-color-red-50);
|
||||
|
||||
/* Disabled */
|
||||
--navds-radio-color-background-disabled: var(--navds-color-gray-10);
|
||||
--navds-radio-color-border-disabled: var(--navds-color-gray-60);
|
||||
--navds-radio-color-label-disabled: var(--navds-color-gray-40);
|
||||
--navds-radio-color-background-disabled-checked: var(--navds-color-gray-40);
|
||||
--navds-radio-color-border-disabled-checked: var(--navds-color-gray-40);
|
||||
--navds-radio-color-shadow-disabled-checked: var(--navds-color-gray-40);
|
||||
}
|
||||
|
||||
.navds-radio {
|
||||
position: relative;
|
||||
padding: var(--navds-spacing-3) 0;
|
||||
@@ -33,7 +57,7 @@
|
||||
|
||||
.navds-radio__description {
|
||||
padding-left: calc(48px - 12px);
|
||||
color: var(--navds-color-gray-80);
|
||||
color: var(--navds-radio-color-description);
|
||||
}
|
||||
|
||||
.navds-radio--with-description {
|
||||
@@ -46,8 +70,8 @@
|
||||
|
||||
.navds-radio__label::before {
|
||||
content: "";
|
||||
background-color: white;
|
||||
border: 1px solid var(--navds-color-border);
|
||||
background-color: var(--navds-radio-color-background);
|
||||
border: 1px solid var(--navds-radio-color-border);
|
||||
width: 1.5rem;
|
||||
height: 1.5rem;
|
||||
border-radius: 4px;
|
||||
@@ -55,29 +79,29 @@
|
||||
border-radius: 50%;
|
||||
}
|
||||
|
||||
.navds-radio--s {
|
||||
.navds-radio--small {
|
||||
padding: var(--navds-spacing-1) 0;
|
||||
}
|
||||
|
||||
.navds-radio--s > .navds-radio__input {
|
||||
.navds-radio--small > .navds-radio__input {
|
||||
width: 24px;
|
||||
height: 24px;
|
||||
top: 2px;
|
||||
left: 0;
|
||||
}
|
||||
|
||||
.navds-radio--s > .navds-radio__label::before {
|
||||
.navds-radio--small > .navds-radio__label::before {
|
||||
margin-top: -2px;
|
||||
margin-bottom: -2px;
|
||||
}
|
||||
|
||||
.navds-radio__input:hover + .navds-radio__label {
|
||||
color: var(--navds-color-blue-50);
|
||||
color: var(--navds-radio-color-label-hover);
|
||||
}
|
||||
|
||||
.navds-radio__input:hover + .navds-radio__label::before {
|
||||
border-color: var(--navds-color-blue-50);
|
||||
background-color: var(--navds-color-blue-10);
|
||||
border-color: var(--navds-radio-color-border-hover);
|
||||
background-color: var(--navds-radio-color-background-hover);
|
||||
}
|
||||
|
||||
.navds-radio__input:focus + .navds-radio__label::before {
|
||||
@@ -85,40 +109,43 @@
|
||||
}
|
||||
|
||||
.navds-radio__input:checked + .navds-radio__label::before {
|
||||
border: 2px solid var(--navds-color-blue-50);
|
||||
box-shadow: 0 0 0 3px #fff inset, 0 0 0 2rem var(--navds-color-blue-50) inset;
|
||||
border: 2px solid var(--navds-radio-color-border-checked);
|
||||
box-shadow: 0 0 0 3px #fff inset,
|
||||
0 0 0 2rem var(--navds-radio-color-shadow-checked) inset;
|
||||
}
|
||||
|
||||
.navds-radio__input:checked:focus + .navds-radio__label::before {
|
||||
transition: box-shadow 200ms cubic-bezier(0.465, 0.183, 0.153, 0.946);
|
||||
box-shadow: 0 0 0 3px var(--navds-color-blue-80), 0 0 0 3px #fff inset,
|
||||
0 0 0 2rem var(--navds-color-blue-50) inset;
|
||||
box-shadow: 0 0 0 3px var(--navds-radio-color-shadow-checked-focus),
|
||||
0 0 0 3px var(--navds-radio-color-shadow-background-checked-focus) inset,
|
||||
0 0 0 2rem var(--navds-radio-color-shadow-dot-checked-focus) inset;
|
||||
}
|
||||
|
||||
.navds-radio--error
|
||||
> .navds-radio__input:not(:hover):not(:focus):not(:disabled):not(:checked)
|
||||
+ .navds-radio__label::before {
|
||||
box-shadow: 0 0 0 1px var(--navds-color-red-50);
|
||||
border-color: var(--navds-color-red-50);
|
||||
box-shadow: 0 0 0 1px var(--navds-radio-color-shadow-error);
|
||||
border-color: var(--navds-radio-color-border-error);
|
||||
}
|
||||
|
||||
.navds-radio--s .navds-error-message {
|
||||
.navds-radio--small .navds-error-message {
|
||||
margin-top: 4px;
|
||||
}
|
||||
|
||||
.navds-radio__input:disabled,
|
||||
.navds-radio__input:disabled + .navds-radio__label {
|
||||
color: var(--navds-color-gray-40);
|
||||
color: var(--navds-radio-color-label-disabled);
|
||||
cursor: not-allowed;
|
||||
}
|
||||
|
||||
.navds-radio__input:disabled + .navds-radio__label::before {
|
||||
background-color: var(--navds-color-gray-10);
|
||||
border-color: var(--navds-color-gray-60);
|
||||
background-color: var(--navds-radio-color-background-disabled);
|
||||
border-color: var(--navds-radio-color-border-disabled);
|
||||
}
|
||||
|
||||
.navds-radio__input:disabled:checked + .navds-radio__label::before {
|
||||
background-color: var(--navds-color-gray-40);
|
||||
border-color: var(--navds-color-gray-40);
|
||||
box-shadow: 0 0 0 3px #fff inset, 0 0 0 2rem var(--navds-color-gray-40) inset;
|
||||
background-color: var(--navds-radio-color-background-disabled-checked);
|
||||
border-color: var(--navds-radio-color-border-disabled-checked);
|
||||
box-shadow: 0 0 0 3px #fff inset,
|
||||
0 0 0 2rem var(--navds-radio-color-shadow-disabled-checked) inset;
|
||||
}
|
||||
@@ -1,9 +1,17 @@
|
||||
.navds-search-field__input-wrapper {
|
||||
display: flex;
|
||||
:root {
|
||||
--navds-search-field-color-shadow-error: var(--navds-color-red-50);
|
||||
--navds-search-field-color-border-error: var(--navds-color-red-50);
|
||||
--navds-search-field-color-clearbutton-border: var(--navds-color-gray-60);
|
||||
}
|
||||
|
||||
.navds-form-field--s .navds-search-field__input {
|
||||
padding: 0.25rem;
|
||||
.navds-search-field__input-wrapper {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
}
|
||||
|
||||
.navds-form-field--small .navds-search-field__input {
|
||||
padding: 0.15rem;
|
||||
min-height: 32px;
|
||||
}
|
||||
|
||||
@@ -22,11 +30,11 @@
|
||||
}
|
||||
|
||||
.navds-search-field__input-wrapper :focus {
|
||||
z-index: 1;
|
||||
z-index: var(--navds-z-index-focus);
|
||||
}
|
||||
|
||||
.navds-search-field--error
|
||||
.navds-search-field__input:not(:hover):not(:focus):not(:disabled) {
|
||||
box-shadow: 0 0 0 1px var(--navds-color-red-50) inset;
|
||||
border-color: var(--navds-color-red-50);
|
||||
box-shadow: 0 0 0 1px var(--navds-search-field-color-shadow-error) inset;
|
||||
border-color: var(--navds-search-field-color-border-error);
|
||||
}
|
||||
@@ -1,9 +1,20 @@
|
||||
:root {
|
||||
--navds-select-color-background: var(--navds-color-white);
|
||||
--navds-select-color-border: var(--navds-color-gray-60);
|
||||
--navds-select-color-border-hover: var(--navds-color-blue-50);
|
||||
--navds-select-color-border-error: var(--navds-color-red-50);
|
||||
--navds-select-color-shadow-error: var(--navds-color-red-50);
|
||||
--navds-select-color-border-disabled: var(--navds-color-gray-40);
|
||||
--navds-select-color-background-disabled: var(--navds-color-gray-10);
|
||||
--navds-select-color-text-disabled: var(--navds-color-darkgray);
|
||||
}
|
||||
|
||||
.navds-select__input {
|
||||
appearance: none;
|
||||
padding: 0.5rem;
|
||||
background-color: white;
|
||||
background-color: var(--navds-select-color-background);
|
||||
border-radius: 4px;
|
||||
border: 1px solid var(--navds-color-gray-40);
|
||||
border: 1px solid var(--navds-select-color-border);
|
||||
width: 100%;
|
||||
box-sizing: border-box;
|
||||
min-height: 48px;
|
||||
@@ -13,7 +24,7 @@
|
||||
}
|
||||
|
||||
.navds-select__input:hover {
|
||||
border-color: var(--navds-color-blue-50);
|
||||
border-color: var(--navds-select-color-border-hover);
|
||||
}
|
||||
|
||||
.navds-select__input:focus {
|
||||
@@ -35,7 +46,7 @@
|
||||
pointer-events: none;
|
||||
}
|
||||
|
||||
.navds-form-field--s .navds-select__input {
|
||||
.navds-form-field--small .navds-select__input {
|
||||
min-height: 32px;
|
||||
padding: 0.25rem;
|
||||
}
|
||||
@@ -44,19 +55,16 @@
|
||||
Error handling
|
||||
*/
|
||||
.navds-select--error > * select:not(:hover):not(:focus):not(:disabled) {
|
||||
box-shadow: 0 0 0 1px var(--navds-color-red-50);
|
||||
border-color: var(--navds-color-red-50);
|
||||
box-shadow: 0 0 0 1px var(--navds-select-color-shadow-error);
|
||||
border-color: var(--navds-select-color-border-error);
|
||||
}
|
||||
|
||||
/*
|
||||
Disabled handling
|
||||
TODO: Oppdatere farger her
|
||||
*/
|
||||
/* Disabled handling */
|
||||
.navds-select__input:disabled,
|
||||
.navds-select__input[read-only] {
|
||||
background-color: var(--navds-color-gray-10);
|
||||
border-color: var(--navds-color-gray-40);
|
||||
background-color: var(--navds-select-color-background-disabled);
|
||||
border-color: var(--navds-select-color-border-disabled);
|
||||
box-shadow: none;
|
||||
color: var(--navds-color-darkgray);
|
||||
color: var(--navds-select-color-text-disabled);
|
||||
cursor: not-allowed;
|
||||
}
|
||||
@@ -1,20 +1,31 @@
|
||||
:root {
|
||||
--navds-text-field-color-background: var(--navds-color-white);
|
||||
--navds-text-field-color-border: var(--navds-color-gray-60);
|
||||
--navds-text-field-color-border-hover: var(--navds-color-blue-50);
|
||||
--navds-text-field-color-border-error: var(--navds-color-red-50);
|
||||
--navds-text-field-color-shadow-error: var(--navds-color-red-50);
|
||||
--navds-text-field-color-border-disabled: var(--navds-color-gray-40);
|
||||
--navds-text-field-color-background-disabled: var(--navds-color-gray-10);
|
||||
--navds-text-field-color-text-disabled: var(--navds-color-darkgray);
|
||||
}
|
||||
|
||||
.navds-text-field__input {
|
||||
appearance: none;
|
||||
padding: 0.5rem;
|
||||
background-color: white;
|
||||
background-color: var(--navds-text-field-color-background);
|
||||
border-radius: 4px;
|
||||
border: 1px solid var(--navds-color-border);
|
||||
border: 1px solid var(--navds-text-field-color-border);
|
||||
min-height: 48px;
|
||||
width: 100%;
|
||||
}
|
||||
|
||||
.navds-form-field--s > .navds-text-field__input {
|
||||
padding: 0.25rem;
|
||||
.navds-form-field--small > .navds-text-field__input {
|
||||
padding: 0.15rem;
|
||||
min-height: 32px;
|
||||
}
|
||||
|
||||
.navds-text-field__input:hover {
|
||||
border-color: var(--navds-color-blue-50);
|
||||
border-color: var(--navds-text-field-color-border-hover);
|
||||
}
|
||||
|
||||
.navds-text-field__input:focus {
|
||||
@@ -27,19 +38,26 @@
|
||||
*/
|
||||
.navds-text-field--error
|
||||
> .navds-text-field__input:not(:hover):not(:focus):not(:disabled) {
|
||||
box-shadow: 0 0 0 1px var(--navds-color-red-50);
|
||||
border-color: var(--navds-color-red-50);
|
||||
box-shadow: 0 0 0 1px var(--navds-text-field-color-shadow-error);
|
||||
border-color: var(--navds-text-field-color-border-error);
|
||||
}
|
||||
|
||||
/*
|
||||
TODO: Oppdater denne til riktige farger
|
||||
Disabled handling
|
||||
*/
|
||||
/* Disabled handling */
|
||||
.navds-text-field__input:disabled,
|
||||
.navds-text-field__input[readonly] {
|
||||
background-color: #f1f1f1;
|
||||
border-color: #6a6a6a;
|
||||
background-color: var(--navds-text-field-color-background-disabled);
|
||||
border-color: var(--navds-text-field-color-border-disabled);
|
||||
box-shadow: none;
|
||||
color: #262626;
|
||||
color: var(--navds-text-field-color-text-disabled);
|
||||
cursor: not-allowed;
|
||||
}
|
||||
|
||||
/**
|
||||
* Removes default search icon
|
||||
*/
|
||||
.navds-text-field__input[type="search"]::-webkit-search-decoration,
|
||||
.navds-text-field__input[type="search"]::-webkit-search-cancel-button,
|
||||
.navds-text-field__input[type="search"]::-webkit-search-results-button,
|
||||
.navds-text-field__input[type="search"]::-webkit-search-results-decoration {
|
||||
-webkit-appearance: none;
|
||||
}
|
||||
@@ -1,3 +1,16 @@
|
||||
:root {
|
||||
--navds-textarea-color-background: var(--navds-color-white);
|
||||
--navds-textarea-color-border: var(--navds-color-gray-60);
|
||||
--navds-textarea-color-border-hover: var(--navds-color-blue-50);
|
||||
--navds-textarea-color-border-error: var(--navds-color-red-50);
|
||||
--navds-textarea-color-shadow-error: var(--navds-color-red-50);
|
||||
--navds-textarea-color-counter-text: var(--navds-color-gray-40);
|
||||
--navds-textarea-color-counter-text-error: var(--navds-color-red-50);
|
||||
--navds-textarea-color-text-disabled: var(--navds-color-darkgray);
|
||||
--navds-textarea-color-border-disabled: var(--navds-color-gray-40);
|
||||
--navds-textarea-color-background-disabled: var(--navds-color-gray-10);
|
||||
}
|
||||
|
||||
.navds-textarea__wrapper {
|
||||
position: relative;
|
||||
width: 100%;
|
||||
@@ -6,9 +19,9 @@
|
||||
.navds-textarea__input {
|
||||
appearance: none;
|
||||
padding: var(--navds-spacing-2);
|
||||
background-color: white;
|
||||
background-color: var(--navds-textarea-color-background);
|
||||
border-radius: 4px;
|
||||
border: 1px solid var(--navds-color-border);
|
||||
border: 1px solid var(--navds-textarea-color-border);
|
||||
resize: none;
|
||||
width: 100%;
|
||||
transition: height 0.1s ease-out;
|
||||
@@ -21,7 +34,7 @@
|
||||
}
|
||||
|
||||
.navds-textarea__input:hover {
|
||||
border-color: var(--navds-color-blue-50);
|
||||
border-color: var(--navds-textarea-color-border-hover);
|
||||
}
|
||||
|
||||
.navds-textarea__input:focus {
|
||||
@@ -29,18 +42,18 @@
|
||||
box-shadow: var(--navds-shadow-focus);
|
||||
}
|
||||
|
||||
.navds-form-field--s .navds-textarea__input {
|
||||
.navds-form-field--small .navds-textarea__input {
|
||||
padding: var(--navds-spacing-1);
|
||||
min-height: 32px;
|
||||
}
|
||||
|
||||
.navds-form-field--s .navds-textarea--counter.navds-textarea__input {
|
||||
.navds-form-field--small .navds-textarea--counter.navds-textarea__input {
|
||||
padding-bottom: var(--navds-spacing-7);
|
||||
}
|
||||
|
||||
.navds-textarea__counter {
|
||||
pointer-events: none;
|
||||
color: var(--navds-color-gray-40);
|
||||
color: var(--navds-textarea-color-counter-text);
|
||||
font-style: italic;
|
||||
position: absolute;
|
||||
text-align: right;
|
||||
@@ -50,7 +63,7 @@
|
||||
}
|
||||
|
||||
.navds-textarea__counter--error {
|
||||
color: var(--navds-color-red-50);
|
||||
color: var(--navds-textarea-color-counter-text-error);
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -58,19 +71,18 @@
|
||||
*/
|
||||
.navds-textarea--error
|
||||
.navds-textarea__input:not(:hover):not(:focus):not(:disabled) {
|
||||
box-shadow: 0 0 0 1px var(--navds-color-red-50);
|
||||
border-color: var(--navds-color-red-50);
|
||||
box-shadow: 0 0 0 1px var(--navds-textarea-color-shadow-error);
|
||||
border-color: var(--navds-textarea-color-border-error);
|
||||
}
|
||||
|
||||
/*
|
||||
TODO: Oppdater denne til riktige farger
|
||||
Disabled handling
|
||||
*/
|
||||
.navds-textarea__input:disabled,
|
||||
.navds-textarea__input[readonly] {
|
||||
background-color: #f1f1f1;
|
||||
border-color: #6a6a6a;
|
||||
background-color: var(--navds-textarea-color-background-disabled);
|
||||
border-color: var(--navds-textarea-color-border-disabled);
|
||||
box-shadow: none;
|
||||
color: #262626;
|
||||
color: var(--navds-textarea-color-text-disabled);
|
||||
cursor: not-allowed;
|
||||
}
|
||||
@@ -0,0 +1,76 @@
|
||||
:root {
|
||||
--navds-guide-panel-color-background: var(--navds-color-background);
|
||||
--navds-guide-panel-color-border: var(--navds-color-blue-40);
|
||||
--navds-guide-panel-color-illustration-background: var(--navds-color-blue-20);
|
||||
}
|
||||
|
||||
/**
|
||||
* GuidePanel component
|
||||
*/
|
||||
.navds-guide-panel {
|
||||
position: relative;
|
||||
padding-left: 2.5rem;
|
||||
}
|
||||
|
||||
.navds-guide-panel__content {
|
||||
background-color: var(--navds-guide-panel-color-background);
|
||||
border-radius: 4px;
|
||||
border: 2px solid var(--navds-guide-panel-color-border);
|
||||
min-height: 7.25rem;
|
||||
padding: 1.5rem;
|
||||
padding-left: 3.5rem;
|
||||
}
|
||||
|
||||
.navds-guide-panel--poster {
|
||||
padding-left: 0;
|
||||
padding-top: 3.125rem;
|
||||
}
|
||||
|
||||
.navds-guide-panel--poster .navds-guide-panel__content {
|
||||
padding: 2rem;
|
||||
padding-top: 4.25rem;
|
||||
}
|
||||
|
||||
.navds-guide-panel .navds-guide {
|
||||
position: absolute;
|
||||
top: 1rem;
|
||||
transform: translateX(-50%);
|
||||
}
|
||||
|
||||
.navds-guide-panel--poster .navds-guide {
|
||||
left: 50%;
|
||||
top: 0;
|
||||
}
|
||||
|
||||
/**
|
||||
* Guide component
|
||||
*/
|
||||
.navds-guide {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
}
|
||||
|
||||
/* Guide illustration frame */
|
||||
.navds-guide__illustration {
|
||||
background: var(--navds-guide-panel-color-illustration-background);
|
||||
border-radius: 50%;
|
||||
overflow: hidden;
|
||||
}
|
||||
|
||||
.navds-guide__illustration svg,
|
||||
.navds-guide__illustration img {
|
||||
height: 100%;
|
||||
width: 100%;
|
||||
}
|
||||
|
||||
/* Illustration sizes */
|
||||
.navds-guide__illustration--small {
|
||||
height: 5rem;
|
||||
width: 5rem;
|
||||
}
|
||||
|
||||
.navds-guide__illustration--medium {
|
||||
height: 6.25rem;
|
||||
width: 6.25rem;
|
||||
}
|
||||
@@ -1,63 +0,0 @@
|
||||
.navds-header {
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
background-color: var(--navds-color-background);
|
||||
padding-top: 1.5rem;
|
||||
padding-bottom: 1.5rem;
|
||||
padding-left: calc((100vw - 100%) / 2);
|
||||
padding-right: calc((100vw - 100%) / 2);
|
||||
margin-left: calc((100vw - 100%) / -2);
|
||||
margin-right: calc((100vw - 100%) / -2);
|
||||
}
|
||||
|
||||
.navds-header__wrapper {
|
||||
width: 100%;
|
||||
max-width: 56.5rem;
|
||||
text-align: start;
|
||||
}
|
||||
|
||||
.navds-header__title {
|
||||
display: flex;
|
||||
margin: 0 auto;
|
||||
width: 100%;
|
||||
position: relative;
|
||||
flex-direction: column;
|
||||
}
|
||||
|
||||
.navds-header--left > .navds-header__wrapper {
|
||||
text-align: start;
|
||||
}
|
||||
|
||||
.navds-header--center > .navds-header__wrapper {
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
.navds-header__illustration {
|
||||
margin-right: 1.5rem;
|
||||
pointer-events: none;
|
||||
}
|
||||
|
||||
.navds-header__illustration > svg {
|
||||
width: 5rem;
|
||||
height: 5rem;
|
||||
}
|
||||
|
||||
.navds-header--situation {
|
||||
box-shadow: 0 -4px 0 var(--navds-color-orange-40) inset;
|
||||
}
|
||||
.navds-header--product {
|
||||
box-shadow: 0 -4px 0 var(--navds-color-green-40) inset;
|
||||
}
|
||||
.navds-header--guide {
|
||||
box-shadow: 0 -4px 0 var(--navds-color-deepblue-40) inset;
|
||||
}
|
||||
|
||||
@media (max-width: 649px) {
|
||||
.navds-header__illustration > svg {
|
||||
width: 3rem;
|
||||
height: 3rem;
|
||||
}
|
||||
.navds-header__title {
|
||||
font-size: var(--navds-font-size-title-xl);
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,54 @@
|
||||
:root {
|
||||
--navds-help-text-color-button-background: transparent;
|
||||
--navds-help-text-color-icon: var(--navds-color-blue-50);
|
||||
--navds-help-text-color-icon-hover: var(--navds-color-white);
|
||||
--navds-help-text-color-icon-background-hover: var(--navds-color-blue-50);
|
||||
--navds-help-text-color-icon-shadow-hover: var(--navds-color-blue-50);
|
||||
--navds-help-text-color-icon-focus: var(--navds-color-white);
|
||||
--navds-help-text-color-icon-background-focus: var(--navds-color-blue-50);
|
||||
--navds-help-text-color-icon-shadow-focus: var(--navds-color-blue-80);
|
||||
--navds-help-text-color-popover-background: var(--navds-color-lightblue-10);
|
||||
}
|
||||
|
||||
.navds-help-text__button {
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
border: 0;
|
||||
cursor: pointer;
|
||||
background-color: var(--navds-help-text-color-button-background);
|
||||
border-radius: 50%;
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.navds-help-text__button:focus {
|
||||
outline: none;
|
||||
}
|
||||
|
||||
.navds-help-text__icon {
|
||||
border-radius: 50%;
|
||||
font-size: 1.5rem;
|
||||
color: var(--navds-help-text-color-icon);
|
||||
}
|
||||
|
||||
.navds-help-text__button:hover > .navds-help-text__icon {
|
||||
color: var(--navds-help-text-color-icon-hover);
|
||||
background: var(--navds-help-text-color-icon-background-hover);
|
||||
box-shadow: 0 0 0 2px var(--navds-help-text-color-icon-shadow-hover);
|
||||
}
|
||||
|
||||
.navds-help-text__button:focus > .navds-help-text__icon {
|
||||
outline: none;
|
||||
color: var(--navds-help-text-color-icon-focus);
|
||||
background: var(--navds-help-text-color-icon-background-focus);
|
||||
box-shadow: 0 0 0 3px var(--navds-help-text-color-icon-shadow-focus);
|
||||
}
|
||||
|
||||
.navds-help-text__popover > .navds-popover__arrow::before {
|
||||
background-color: var(--navds-help-text-color-popover-background);
|
||||
}
|
||||
|
||||
.navds-help-text__popover.navds-popover {
|
||||
background-color: var(--navds-help-text-color-popover-background);
|
||||
}
|
||||
@@ -6,12 +6,12 @@
|
||||
@import "accordion-menu.css";
|
||||
@import "alert.css";
|
||||
@import "button.css";
|
||||
@import "card.css";
|
||||
@import "content-container.css";
|
||||
@import "copy-to-clipboard.css";
|
||||
@import "header.css";
|
||||
@import "internal-header.css";
|
||||
@import "guide-panel.css";
|
||||
@import "form/index.css";
|
||||
@import "help-text.css";
|
||||
@import "link.css";
|
||||
@import "loader.css";
|
||||
@import "modal.css";
|
||||
@@ -20,3 +20,7 @@
|
||||
@import "panel.css";
|
||||
@import "link-panel.css";
|
||||
@import "speech-bubble.css";
|
||||
|
||||
/* Navno spesific packages */
|
||||
@import "page-header.css";
|
||||
@import "card.css";
|
||||
@@ -1,3 +1,9 @@
|
||||
:root {
|
||||
--navds-internal-header-color-background: var(--navds-color-darkgray);
|
||||
--navds-internal-header-color-border: var(--navds-color-gray-40);
|
||||
--navds-internal-header-color-text: var(--navds-color-text-inverse);
|
||||
}
|
||||
|
||||
/**************************
|
||||
* .navds-header *
|
||||
**************************/
|
||||
@@ -5,8 +11,8 @@
|
||||
.navds-interal-header {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
background: var(--navds-color-darkgray);
|
||||
color: white;
|
||||
background: var(--navds-internal-header-color-background);
|
||||
color: var(--navds-internal-header-color-text);
|
||||
max-width: 100vw;
|
||||
min-height: 50px;
|
||||
}
|
||||
@@ -22,13 +28,13 @@
|
||||
|
||||
.navds-interal-header__title {
|
||||
padding: 0 var(--navds-spacing-6);
|
||||
border-right: 1px solid var(--navds-color-gray-40);
|
||||
border-right: 1px solid var(--navds-internal-header-color-border);
|
||||
display: flex;
|
||||
align-self: stretch;
|
||||
align-items: center;
|
||||
text-decoration: none;
|
||||
margin: 0;
|
||||
color: var(--navds-color-text-inverse);
|
||||
color: var(--navds-internal-header-color-text);
|
||||
}
|
||||
|
||||
.navds-interal-header__title > span > a {
|
||||
@@ -46,10 +52,10 @@
|
||||
**************************/
|
||||
|
||||
.navds-interal-header__user {
|
||||
color: var(--navds-color-text-inverse);
|
||||
color: var(--navds-internal-header-color-text);
|
||||
padding: 0 var(--navds-spacing-6);
|
||||
margin-left: auto;
|
||||
border-left: 1px solid var(--navds-color-gray-40);
|
||||
border-left: 1px solid var(--navds-internal-header-color-border);
|
||||
display: flex;
|
||||
align-self: stretch;
|
||||
align-items: center;
|
||||
|
||||
@@ -1,19 +1,26 @@
|
||||
.navds-link-panel {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
text-decoration: none;
|
||||
color: var(--navds-color-gray-90);
|
||||
:root {
|
||||
--navds-link-panel-color-text: var(--navds-color-gray-90);
|
||||
--navds-link-panel-color-border-hover: var(--navds-color-blue-50);
|
||||
--navds-link-panel-color-title-hover: var(--navds-color-text-link);
|
||||
}
|
||||
|
||||
.navds-link-panel:hover .navds-link-panel-title {
|
||||
.navds-link-panel {
|
||||
text-decoration: none;
|
||||
color: var(--navds-link-panel-color-text);
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: space-between;
|
||||
gap: var(--navds-spacing-2);
|
||||
}
|
||||
|
||||
.navds-link-panel:hover .navds-link-panel__title {
|
||||
text-decoration: underline;
|
||||
color: var(--navds-color-text-link);
|
||||
color: var(--navds-link-panel-color-title-hover);
|
||||
}
|
||||
|
||||
.navds-link-panel:hover {
|
||||
box-shadow: var(--navds-shadow-hover);
|
||||
border-color: var(--navds-color-blue-50);
|
||||
border-color: var(--navds-link-panel-color-border-hover);
|
||||
}
|
||||
|
||||
.navds-link-panel:focus {
|
||||
@@ -22,6 +29,7 @@
|
||||
}
|
||||
|
||||
.navds-link-panel__chevron {
|
||||
flex-shrink: 0;
|
||||
font-size: 1.5rem;
|
||||
transition: transform 200ms;
|
||||
}
|
||||
@@ -30,3 +38,7 @@
|
||||
.navds-link-panel:focus-within > .navds-link-panel__chevron {
|
||||
transform: translateX(4px);
|
||||
}
|
||||
|
||||
.navds-link-panel__description {
|
||||
margin-top: var(--navds-spacing-2);
|
||||
}
|
||||
+30
-10
@@ -1,10 +1,30 @@
|
||||
:root {
|
||||
--navds-link-color-text: var(--navds-color-text-link);
|
||||
--navds-link-color-text-focus: var(--navds-color-text-inverse);
|
||||
--navds-link-color-text-active: var(--navds-color-text-inverse);
|
||||
--navds-link-color-background-focus: var(--navds-text-focus);
|
||||
--navds-link-color-background-active: var(--navds-text-focus);
|
||||
--navds-link-color-icon: var(--navds-color-text-link);
|
||||
--navds-link-color-icon-focus: var(--navds-color-text-inverse);
|
||||
--navds-link-color-on-info-background: var(--navds-color-text-primary);
|
||||
--navds-link-color-on-error-background: var(--navds-color-text-primary);
|
||||
}
|
||||
|
||||
.navds-link {
|
||||
color: var(--navds-color-text-link);
|
||||
color: var(--navds-link-color-text);
|
||||
text-decoration: underline;
|
||||
display: inline-grid;
|
||||
grid-auto-flow: column;
|
||||
display: inline-flex;
|
||||
align-items: center;
|
||||
gap: 0.25rem;
|
||||
gap: var(--navds-spacing-1);
|
||||
}
|
||||
|
||||
.navds-alert--info .navds-link {
|
||||
color: var(--navds-link-color-on-info-background);
|
||||
}
|
||||
|
||||
.navds-alert--error .navds-link,
|
||||
.navds-confirmation-panel--error .navds-link {
|
||||
color: var(--navds-link-color-on-error-background);
|
||||
}
|
||||
|
||||
.navds-link:hover {
|
||||
@@ -13,24 +33,24 @@
|
||||
|
||||
.navds-link:focus {
|
||||
outline: none;
|
||||
color: var(--navds-color-text-inverse);
|
||||
color: var(--navds-link-color-text-focus);
|
||||
text-decoration: none;
|
||||
background-color: var(--navds-text-focus);
|
||||
background-color: var(--navds-link-color-background-focus);
|
||||
box-shadow: var(--navds-text-shadow);
|
||||
}
|
||||
|
||||
.navds-link:active {
|
||||
outline: none;
|
||||
color: var(--navds-color-text-inverse);
|
||||
color: var(--navds-link-color-text-active);
|
||||
text-decoration: none;
|
||||
background-color: var(--navds-text-focus);
|
||||
background-color: var(--navds-link-color-background-active);
|
||||
box-shadow: var(--navds-text-shadow);
|
||||
}
|
||||
|
||||
.navds-link svg {
|
||||
color: var(--navds-color-text-link);
|
||||
color: var(--navds-link-color-icon);
|
||||
}
|
||||
|
||||
.navds-link:focus svg {
|
||||
color: var(--navds-color-text-inverse);
|
||||
color: var(--navds-link-color-icon-focus);
|
||||
}
|
||||
+30
-18
@@ -1,3 +1,15 @@
|
||||
:root {
|
||||
--navds-loader-color-foreground: var(--navds-color-gray-40);
|
||||
--navds-loader-color-background: var(--navds-color-gray-10);
|
||||
--navds-loader-color-neutral-foreground: var(--navds-color-gray-40);
|
||||
--navds-loader-color-interaction-foreground: var(--navds-color-blue-50);
|
||||
--navds-loader-color-inverted-foreground: var(--navds-color-white);
|
||||
--navds-loader-color-inverted-background: rgba(255, 255, 255, 0.3);
|
||||
--navds-loader-color-transparent-background: transparent;
|
||||
--navds-loader-color-on-button-background: rgba(255, 255, 255, 0.3);
|
||||
--navds-loader-color-on-button-foreground: currentColor;
|
||||
}
|
||||
|
||||
.navds-loader {
|
||||
width: 1.5rem;
|
||||
display: inline-block;
|
||||
@@ -9,54 +21,54 @@
|
||||
animation: loader-dasharray 1.4s ease-in-out infinite;
|
||||
stroke-dasharray: 80px, 200px;
|
||||
stroke-dashoffset: 0;
|
||||
stroke: var(--navds-color-gray-40);
|
||||
stroke: var(--navds-loader-color-foreground);
|
||||
}
|
||||
|
||||
.navds-loader__background {
|
||||
stroke: var(--navds-color-gray-10);
|
||||
stroke: var(--navds-loader-color-background);
|
||||
}
|
||||
|
||||
.navds-loader--neutral .navds-loader__foreground {
|
||||
stroke: var(--navds-color-gray-40);
|
||||
stroke: var(--navds-loader-color-neutral-foreground);
|
||||
}
|
||||
|
||||
.navds-loader--interaction .navds-loader__foreground {
|
||||
stroke: var(--navds-color-blue-50);
|
||||
stroke: var(--navds-loader-color-interaction-foreground);
|
||||
}
|
||||
|
||||
.navds-loader--inverted .navds-loader__foreground {
|
||||
stroke: white;
|
||||
stroke: var(--navds-loader-color-inverted-foreground);
|
||||
}
|
||||
|
||||
.navds-loader--inverted .navds-loader__background {
|
||||
stroke: rgba(255, 255, 255, 0.3);
|
||||
stroke: var(--navds-loader-color-inverted-background);
|
||||
}
|
||||
|
||||
.navds-loader--transparent .navds-loader__background {
|
||||
stroke: transparent;
|
||||
stroke: var(--navds-loader-color-transparent-background);
|
||||
}
|
||||
|
||||
.navds-loader--2xl {
|
||||
.navds-loader--2xlarge {
|
||||
width: 4rem;
|
||||
}
|
||||
|
||||
.navds-loader--xl {
|
||||
.navds-loader--xlarge {
|
||||
width: 2.5rem;
|
||||
}
|
||||
|
||||
.navds-loader--l {
|
||||
.navds-loader--large {
|
||||
width: 2rem;
|
||||
}
|
||||
|
||||
.navds-loader--m {
|
||||
.navds-loader--medium {
|
||||
width: 1.5rem;
|
||||
}
|
||||
|
||||
.navds-loader--s {
|
||||
.navds-loader--small {
|
||||
width: 1.25rem;
|
||||
}
|
||||
|
||||
.navds-loader--xs {
|
||||
.navds-loader--xsmall {
|
||||
width: 1rem;
|
||||
}
|
||||
|
||||
@@ -65,20 +77,20 @@
|
||||
*/
|
||||
|
||||
.navds-button .navds-loader .navds-loader__foreground {
|
||||
stroke: currentColor;
|
||||
stroke: var(--navds-loader-color-on-button-foreground);
|
||||
}
|
||||
|
||||
.navds-button:hover .navds-loader .navds-loader__background {
|
||||
stroke: rgba(255, 255, 255, 0.3);
|
||||
stroke: var(--navds-loader-color-on-button-background);
|
||||
}
|
||||
|
||||
.navds-button:active .navds-loader .navds-loader__background {
|
||||
stroke: rgba(255, 255, 255, 0.3);
|
||||
stroke: var(--navds-loader-color-on-button-background);
|
||||
}
|
||||
|
||||
.navds-button--action .navds-loader .navds-loader__background,
|
||||
.navds-button--primary .navds-loader .navds-loader__background,
|
||||
.navds-button--danger .navds-loader .navds-loader__background {
|
||||
stroke: rgba(255, 255, 255, 0.3);
|
||||
stroke: var(--navds-loader-color-on-button-background);
|
||||
}
|
||||
|
||||
@keyframes loader-rotate {
|
||||
|
||||
@@ -1,16 +1,23 @@
|
||||
:root {
|
||||
--navds-modal-color-background: var(--navds-color-background);
|
||||
--navds-modal-color-overlay: var(--navds-color-modal-overlay);
|
||||
}
|
||||
|
||||
.ReactModal__Body--open {
|
||||
overflow: hidden;
|
||||
}
|
||||
|
||||
.navds-modal {
|
||||
background-color: var(--navds-color-background);
|
||||
padding: var(--navds-spacing-4);
|
||||
background-color: var(--navds-modal-color-background);
|
||||
border-radius: 4px;
|
||||
display: block;
|
||||
position: relative;
|
||||
overflow: auto;
|
||||
max-height: 100%;
|
||||
z-index: var(--navds-z-index-modal-content);
|
||||
}
|
||||
|
||||
.navds-modal__content {
|
||||
padding: var(--navds-spacing-4);
|
||||
}
|
||||
|
||||
.navds-modal:focus,
|
||||
@@ -21,12 +28,12 @@
|
||||
|
||||
.navds-modal__overlay {
|
||||
position: fixed;
|
||||
z-index: var(--navds-z-index-modal-overlay);
|
||||
z-index: var(--navds-z-index-modal);
|
||||
top: 0;
|
||||
bottom: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background-color: var(--navds-color-modal-overlay);
|
||||
background-color: var(--navds-modal-color-overlay);
|
||||
padding: var(--navds-spacing-4);
|
||||
display: flex;
|
||||
align-items: center;
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "@navikt/ds-css",
|
||||
"version": "0.7.2",
|
||||
"version": "0.8.2",
|
||||
"private": false,
|
||||
"description": "Css for NAV Designsystem components",
|
||||
"author": "NAV Designsystem team",
|
||||
@@ -21,7 +21,7 @@
|
||||
"watch-css": "postcss -w --use postcss-import -o dist/index.css index.css"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@navikt/ds-tokens": "^0.4.4",
|
||||
"@navikt/ds-tokens": "^0.5.0",
|
||||
"normalize.css": "^8.0.1",
|
||||
"postcss": "^8.2.7",
|
||||
"postcss-cli": "^8.3.1",
|
||||
|
||||
@@ -0,0 +1,70 @@
|
||||
:root {
|
||||
--navds-page-header-color-background: var(--navds-color-background);
|
||||
--navds-page-header-color-shadow-situation: var(--navds-color-orange-40);
|
||||
--navds-page-header-color-shadow-product: var(--navds-color-green-40);
|
||||
--navds-page-header-color-shadow-guide: var(--navds-color-deepblue-40);
|
||||
}
|
||||
|
||||
.navds-page-header {
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
background-color: var(--navds-page-header-color-background);
|
||||
padding-top: 1.5rem;
|
||||
padding-bottom: 1.5rem;
|
||||
padding-left: calc((100vw - 100%) / 2);
|
||||
padding-right: calc((100vw - 100%) / 2);
|
||||
margin-left: calc((100vw - 100%) / -2);
|
||||
margin-right: calc((100vw - 100%) / -2);
|
||||
}
|
||||
|
||||
.navds-page-header__wrapper {
|
||||
width: 100%;
|
||||
max-width: 56.5rem;
|
||||
text-align: start;
|
||||
}
|
||||
|
||||
.navds-page-header__title {
|
||||
display: flex;
|
||||
margin: 0 auto;
|
||||
width: 100%;
|
||||
position: relative;
|
||||
flex-direction: column;
|
||||
}
|
||||
|
||||
.navds-page-header--left > .navds-page-header__wrapper {
|
||||
text-align: start;
|
||||
}
|
||||
|
||||
.navds-page-header--center > .navds-page-header__wrapper {
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
.navds-page-header__illustration {
|
||||
margin-right: 1.5rem;
|
||||
pointer-events: none;
|
||||
}
|
||||
|
||||
.navds-page-header__illustration > svg {
|
||||
width: 5rem;
|
||||
height: 5rem;
|
||||
}
|
||||
|
||||
.navds-page-header--situation {
|
||||
box-shadow: 0 -4px 0 var(--navds-page-header-color-shadow-situation) inset;
|
||||
}
|
||||
.navds-page-header--product {
|
||||
box-shadow: 0 -4px 0 var(--navds-page-header-color-shadow-product) inset;
|
||||
}
|
||||
.navds-page-header--guide {
|
||||
box-shadow: 0 -4px 0 var(--navds-page-header-color-shadow-guide) inset;
|
||||
}
|
||||
|
||||
@media (max-width: 649px) {
|
||||
.navds-page-header__illustration > svg {
|
||||
width: 3rem;
|
||||
height: 3rem;
|
||||
}
|
||||
.navds-page-header__title {
|
||||
font-size: var(--navds-font-size-title-xl);
|
||||
}
|
||||
}
|
||||
@@ -1,11 +1,15 @@
|
||||
:root {
|
||||
--navds-panel-color-background: var(--navds-color-white);
|
||||
--navds-panel-color-border: var(--navds-color-border);
|
||||
}
|
||||
|
||||
.navds-panel {
|
||||
background-color: var(--navds-color-white);
|
||||
display: block;
|
||||
background-color: var(--navds-panel-color-background);
|
||||
padding: var(--navds-spacing-4);
|
||||
border-radius: var(--navds-border-radius);
|
||||
border: 1px solid transparent;
|
||||
}
|
||||
|
||||
.navds-panel--border {
|
||||
border-color: var(--navds-color-border);
|
||||
border-color: var(--navds-panel-color-border);
|
||||
}
|
||||
+24
-15
@@ -1,9 +1,20 @@
|
||||
:root {
|
||||
--navds-popover-color-background: var(--navds-color-background);
|
||||
--navds-popover-color-border: var(--navds-color-gray-40);
|
||||
--navds-popover-color-shadow: var(--navds-color-gray-20);
|
||||
}
|
||||
|
||||
.navds-popover {
|
||||
z-index: var(--navds-z-index-popover-default);
|
||||
background-color: var(--navds-color-background);
|
||||
box-shadow: 0 0.05rem 0.25rem 0.125rem rgba(0, 0, 0, 0.08);
|
||||
border: var(--navds-border-default);
|
||||
border-radius: 2px;
|
||||
z-index: var(--navds-z-index-popover);
|
||||
background-color: var(--navds-popover-color-background);
|
||||
box-shadow: 0 2px 4px 0 var(--navds-popover-color-shadow);
|
||||
border: 1px solid;
|
||||
border-color: var(--navds-popover-color-border);
|
||||
border-radius: 4px;
|
||||
}
|
||||
|
||||
.navds-popover__content {
|
||||
padding: var(--navds-spacing-4);
|
||||
}
|
||||
|
||||
.navds-popover--hidden {
|
||||
@@ -16,22 +27,20 @@
|
||||
}
|
||||
|
||||
.navds-popover__arrow {
|
||||
z-index: var(--navds-z-index-popover-arrow);
|
||||
z-index: -1;
|
||||
}
|
||||
|
||||
.navds-popover__arrow::before {
|
||||
content: "";
|
||||
display: block;
|
||||
content: "";
|
||||
transform: rotate(45deg);
|
||||
background-color: var(--navds-popover-color-background);
|
||||
border: 1px solid;
|
||||
border-color: var(--navds-popover-color-border);
|
||||
width: 1rem;
|
||||
height: 1rem;
|
||||
transform: rotate(45deg);
|
||||
background-color: var(--navds-color-background);
|
||||
border: var(--navds-border-default);
|
||||
}
|
||||
|
||||
.navds-popover__arrow::before .navds-popover--small {
|
||||
width: 0.67rem;
|
||||
height: 0.67rem;
|
||||
top: 0;
|
||||
left: 0;
|
||||
}
|
||||
|
||||
.navds-popover[data-popper-placement^="top"] > .navds-popover__arrow {
|
||||
|
||||
@@ -1,3 +1,13 @@
|
||||
:root {
|
||||
--navds-speechbubble-color-background: var(--navds-color-gray-10);
|
||||
--navds-speechbubble-color-shadow: var(--navds-color-gray-20);
|
||||
--navds-speechbubble-color-illustration: var(--navds-color-darkgray);
|
||||
--navds-speechbubble-color-illustration-background: var(
|
||||
--navds-color-gray-20
|
||||
);
|
||||
--navds-speechbubble-color-detail-text: var(--navds-color-gray-60);
|
||||
}
|
||||
|
||||
.navds-speechbubble {
|
||||
display: flex;
|
||||
align-items: flex-end;
|
||||
@@ -23,8 +33,8 @@
|
||||
|
||||
.navds-speechbubble__illustration {
|
||||
align-items: center;
|
||||
background: var(--navds-color-gray-20);
|
||||
color: var(--navds-color-darkgray);
|
||||
background: var(--navds-speechbubble-color-illustration-background);
|
||||
color: var(--navds-speechbubble-color-illustration);
|
||||
border-radius: 50%;
|
||||
display: flex;
|
||||
flex-shrink: 0;
|
||||
@@ -42,10 +52,10 @@
|
||||
|
||||
.navds-speechbubble__bubble {
|
||||
padding: 1rem;
|
||||
box-shadow: 0 2px 4px 0 var(--navds-color-gray-20);
|
||||
box-shadow: 0 2px 4px 0 var(--navds-speechbubble-color-shadow);
|
||||
width: fit-content;
|
||||
max-width: 37.5rem;
|
||||
background-color: var(--navds-color-gray-10);
|
||||
background-color: var(--navds-speechbubble-color-background);
|
||||
border-radius: 12px;
|
||||
border-bottom-left-radius: 2px;
|
||||
display: flex;
|
||||
@@ -61,9 +71,12 @@
|
||||
.navds-speechbubble--right .navds-speechbubble__bubble {
|
||||
border-radius: 12px;
|
||||
border-bottom-right-radius: 2px;
|
||||
align-items: flex-end;
|
||||
}
|
||||
|
||||
.navds-speechbubble__top-text {
|
||||
color: var(--navds-color-gray-60);
|
||||
color: var(--navds-speechbubble-color-detail-text);
|
||||
}
|
||||
|
||||
.navds-speechbubble--right .navds-speechbubble__top-text {
|
||||
align-self: flex-end;
|
||||
}
|
||||
+40
-16
@@ -1,30 +1,54 @@
|
||||
.navds-tag {
|
||||
border-radius: 4px;
|
||||
border: var(--navds-border-default);
|
||||
background-color: var(--navds-color-tag-info-background);
|
||||
border-color: var(--navds-color-tag-info-border);
|
||||
display: inline-block;
|
||||
:root {
|
||||
--navds-tag-color-border: var(--navds-color-gray-40);
|
||||
--navds-tag-color-background: var(--navds-color-gray-10);
|
||||
--navds-tag-color-info-background: var(--navds-color-tag-info-background);
|
||||
--navds-tag-color-info-border: var(--navds-color-tag-info-border);
|
||||
--navds-tag-color-warning-background: var(
|
||||
--navds-color-tag-warning-background
|
||||
);
|
||||
--navds-tag-color-warning-border: var(--navds-color-tag-warning-border);
|
||||
--navds-tag-color-success-background: var(
|
||||
--navds-color-tag-success-background
|
||||
);
|
||||
--navds-tag-color-success-border: var(--navds-color-tag-success-border);
|
||||
--navds-tag-color-error-background: var(--navds-color-tag-error-background);
|
||||
--navds-tag-color-error-border: var(--navds-color-tag-error-border);
|
||||
}
|
||||
|
||||
/* Padding calculated based on 16px font for 24px tall tag */
|
||||
padding: 0.0625rem var(--navds-spacing-2);
|
||||
.navds-tag {
|
||||
border: 1px solid;
|
||||
border-color: var(--navds-tag-color-border);
|
||||
border-radius: 4px;
|
||||
background-color: var(--navds-tag-color-background);
|
||||
display: inline-flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
padding: 0.125rem var(--navds-spacing-3);
|
||||
min-height: 32px;
|
||||
}
|
||||
|
||||
.navds-tag--small {
|
||||
min-height: 24px;
|
||||
padding-right: var(--navds-spacing-1);
|
||||
padding-left: var(--navds-spacing-1);
|
||||
}
|
||||
|
||||
.navds-tag--error {
|
||||
background-color: var(--navds-color-tag-error-background);
|
||||
border-color: var(--navds-color-tag-error-border);
|
||||
background-color: var(--navds-tag-color-error-background);
|
||||
border-color: var(--navds-tag-color-error-border);
|
||||
}
|
||||
|
||||
.navds-tag--success {
|
||||
background-color: var(--navds-color-tag-success-background);
|
||||
border-color: var(--navds-color-tag-success-border);
|
||||
background-color: var(--navds-tag-color-success-background);
|
||||
border-color: var(--navds-tag-color-success-border);
|
||||
}
|
||||
|
||||
.navds-tag--warning {
|
||||
background-color: var(--navds-color-tag-warning-background);
|
||||
border-color: var(--navds-color-tag-warning-border);
|
||||
background-color: var(--navds-tag-color-warning-background);
|
||||
border-color: var(--navds-tag-color-warning-border);
|
||||
}
|
||||
|
||||
.navds-tag--info {
|
||||
background-color: var(--navds-color-tag-info-background);
|
||||
border-color: var(--navds-color-tag-info-border);
|
||||
background-color: var(--navds-tag-color-info-background);
|
||||
border-color: var(--navds-tag-color-info-border);
|
||||
}
|
||||
@@ -1,64 +1,75 @@
|
||||
/* Title */
|
||||
.navds-title {
|
||||
/* Heading */
|
||||
.navds-heading {
|
||||
font-weight: var(--navds-font-weight-bold);
|
||||
margin: 0;
|
||||
}
|
||||
|
||||
.navds-title--2xl {
|
||||
font-size: var(--navds-font-size-title-2xl);
|
||||
.navds-heading--2xlarge {
|
||||
font-size: var(--navds-font-size-heading-2xl);
|
||||
letter-spacing: -0.01em;
|
||||
line-height: var(--navds-font-line-height-s);
|
||||
line-height: var(--navds-font-line-height-heading-2xl);
|
||||
}
|
||||
|
||||
.navds-title--2xl.navds-typo--spacing {
|
||||
.navds-heading--2xlarge.navds-typo--spacing {
|
||||
margin-bottom: var(--navds-spacing-5);
|
||||
}
|
||||
|
||||
.navds-title--xl {
|
||||
font-size: var(--navds-font-size-title-xl);
|
||||
.navds-heading--xlarge {
|
||||
font-size: var(--navds-font-size-heading-xl);
|
||||
letter-spacing: -0.008em;
|
||||
line-height: var(--navds-font-line-height-s);
|
||||
line-height: var(--navds-font-line-height-heading-xl);
|
||||
}
|
||||
|
||||
.navds-title--xl.navds-typo--spacing {
|
||||
.navds-heading--xlarge.navds-typo--spacing {
|
||||
margin-bottom: var(--navds-spacing-4);
|
||||
}
|
||||
|
||||
.navds-title--l {
|
||||
font-size: var(--navds-font-size-title-l);
|
||||
.navds-heading--large {
|
||||
font-size: var(--navds-font-size-heading-l);
|
||||
letter-spacing: -0.004em;
|
||||
line-height: var(--navds-font-line-height-s);
|
||||
line-height: var(--navds-font-line-height-heading-l);
|
||||
}
|
||||
|
||||
.navds-title--l.navds-typo--spacing {
|
||||
.navds-heading--large.navds-typo--spacing {
|
||||
margin-bottom: var(--navds-spacing-3);
|
||||
}
|
||||
|
||||
.navds-title--m {
|
||||
font-size: var(--navds-font-size-title-m);
|
||||
.navds-heading--medium {
|
||||
font-size: var(--navds-font-size-heading-m);
|
||||
letter-spacing: -0.002em;
|
||||
line-height: var(--navds-font-line-height-s);
|
||||
line-height: var(--navds-font-line-height-heading-m);
|
||||
}
|
||||
|
||||
.navds-title--m.navds-typo--spacing {
|
||||
.navds-heading--medium.navds-typo--spacing {
|
||||
margin-bottom: var(--navds-spacing-3);
|
||||
}
|
||||
|
||||
.navds-title--s {
|
||||
font-size: var(--navds-font-size-title-s);
|
||||
.navds-heading--small {
|
||||
font-size: var(--navds-font-size-heading-s);
|
||||
letter-spacing: -0.001em;
|
||||
line-height: var(--navds-font-line-height-s);
|
||||
line-height: var(--navds-font-line-height-heading-s);
|
||||
}
|
||||
|
||||
.navds-title--s.navds-typo--spacing {
|
||||
.navds-heading--small.navds-typo--spacing {
|
||||
margin-bottom: var(--navds-spacing-3);
|
||||
}
|
||||
|
||||
.navds-heading--xsmall {
|
||||
font-size: var(--navds-font-size-heading-xs);
|
||||
letter-spacing: -0.001em;
|
||||
line-height: var(--navds-font-line-height-heading-xs);
|
||||
}
|
||||
|
||||
.navds-heading--xsmall.navds-typo--spacing {
|
||||
margin-bottom: var(--navds-spacing-3);
|
||||
}
|
||||
|
||||
/* Ingress */
|
||||
.navds-ingress {
|
||||
font-size: var(--navds-font-size-xl);
|
||||
font-weight: var(--navds-font-weight-regular);
|
||||
letter-spacing: -0.001em;
|
||||
line-height: var(--navds-font-line-height-m);
|
||||
line-height: var(--navds-font-line-height-xl);
|
||||
margin: 0;
|
||||
}
|
||||
|
||||
@@ -69,15 +80,9 @@
|
||||
/* Body */
|
||||
.navds-body-long {
|
||||
font-size: var(--navds-font-size-l);
|
||||
font-weight: var(--navds-font-weight-regular);
|
||||
letter-spacing: 0;
|
||||
line-height: var(--navds-font-line-height-m);
|
||||
margin: 0;
|
||||
}
|
||||
|
||||
.navds-body-short {
|
||||
font-size: var(--navds-font-size-l);
|
||||
letter-spacing: 0;
|
||||
line-height: var(--navds-font-line-height-s);
|
||||
line-height: var(--navds-font-line-height-xl);
|
||||
margin: 0;
|
||||
}
|
||||
|
||||
@@ -85,30 +90,44 @@
|
||||
margin-bottom: var(--navds-spacing-7);
|
||||
}
|
||||
|
||||
.navds-body-long--small {
|
||||
font-size: var(--navds-font-size-m);
|
||||
letter-spacing: 0.002em;
|
||||
line-height: var(--navds-font-line-height-l);
|
||||
}
|
||||
|
||||
.navds-body-long--small.navds-typo--spacing {
|
||||
margin-bottom: var(--navds-spacing-6);
|
||||
}
|
||||
|
||||
.navds-body-short {
|
||||
font-size: var(--navds-font-size-l);
|
||||
font-weight: var(--navds-font-weight-regular);
|
||||
letter-spacing: 0;
|
||||
line-height: var(--navds-font-line-height-l);
|
||||
margin: 0;
|
||||
}
|
||||
|
||||
.navds-body-short.navds-typo--spacing {
|
||||
margin-bottom: var(--navds-spacing-3);
|
||||
}
|
||||
|
||||
.navds-body--s {
|
||||
.navds-body-short--small {
|
||||
font-size: var(--navds-font-size-m);
|
||||
letter-spacing: 0.002em;
|
||||
line-height: var(--navds-font-line-height-s);
|
||||
line-height: var(--navds-font-line-height-m);
|
||||
}
|
||||
|
||||
.navds-body-long.navds-body--s.navds-typo--spacing {
|
||||
margin-bottom: var(--navds-spacing-6);
|
||||
}
|
||||
|
||||
.navds-body-short.navds-body--s.navds-typo--spacing {
|
||||
.navds-body-short--small.navds-typo--spacing {
|
||||
margin-bottom: var(--navds-spacing-2);
|
||||
}
|
||||
|
||||
/* Label */
|
||||
.navds-label {
|
||||
font-size: var(--navds-font-size-l);
|
||||
letter-spacing: 0;
|
||||
line-height: var(--navds-font-line-height-s);
|
||||
font-weight: var(--navds-font-weight-bold);
|
||||
letter-spacing: 0;
|
||||
line-height: var(--navds-font-line-height-l);
|
||||
margin: 0;
|
||||
}
|
||||
|
||||
@@ -116,22 +135,22 @@
|
||||
margin-bottom: var(--navds-spacing-3);
|
||||
}
|
||||
|
||||
.navds-label--s {
|
||||
.navds-label--small {
|
||||
font-size: var(--navds-font-size-m);
|
||||
letter-spacing: 0.002em;
|
||||
line-height: var(--navds-font-line-height-s);
|
||||
line-height: var(--navds-font-line-height-m);
|
||||
}
|
||||
|
||||
.navds-label--s.navds-typo--spacing {
|
||||
.navds-label--small.navds-typo--spacing {
|
||||
margin-bottom: var(--navds-spacing-2);
|
||||
}
|
||||
|
||||
/* Small text */
|
||||
.navds-detail {
|
||||
font-size: var(--navds-font-size-s);
|
||||
letter-spacing: 0.004em;
|
||||
line-height: var(--navds-font-line-height-s);
|
||||
font-weight: var(--navds-font-weight-bold);
|
||||
letter-spacing: 0.004em;
|
||||
line-height: var(--navds-font-line-height-m);
|
||||
margin: 0;
|
||||
}
|
||||
|
||||
@@ -139,10 +158,10 @@
|
||||
margin-bottom: var(--navds-spacing-2);
|
||||
}
|
||||
|
||||
.navds-detail--s {
|
||||
.navds-detail--small {
|
||||
font-weight: var(--navds-font-weight-regular);
|
||||
}
|
||||
|
||||
.navds-detail--s.navds-typo--spacing {
|
||||
.navds-detail--small.navds-typo--spacing {
|
||||
margin-bottom: var(--navds-spacing-2);
|
||||
}
|
||||
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "@navikt/ds-react",
|
||||
"version": "0.7.5",
|
||||
"version": "0.8.2",
|
||||
"private": false,
|
||||
"description": "NAV designsystem react components",
|
||||
"author": "NAV Designsystem team",
|
||||
@@ -42,12 +42,15 @@
|
||||
"react-merge-refs": "^1.1.0",
|
||||
"react-modal": "3.12.1",
|
||||
"react-popper": "^2.2.4",
|
||||
"short-uuid": "^4.2.0"
|
||||
"uuid": "^8.3.2"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@types/react-router-dom": "^5.1.8",
|
||||
"@types/styled-components": "^5.1.14",
|
||||
"copyfiles": "^2.4.1",
|
||||
"react-router-dom": "^5.2.0",
|
||||
"rimraf": "3.0.2"
|
||||
"rimraf": "3.0.2",
|
||||
"styled-components": "^5.3.1"
|
||||
},
|
||||
"peerDependencies": {
|
||||
"react": "^16.8.0 || ^17.0.0"
|
||||
|
||||
@@ -1,11 +1,23 @@
|
||||
import React, { forwardRef, HTMLAttributes } from "react";
|
||||
import React, { forwardRef } from "react";
|
||||
import cl from "classnames";
|
||||
import MenuItems from "./MenuItems";
|
||||
import Collapsable, {
|
||||
AccordionMenuCollapsableType,
|
||||
} from "./AccordionMenuCollapsable";
|
||||
import Item, { AccordionMenuItemType } from "./AccordionMenuItem";
|
||||
|
||||
export interface AccordionMenuProps extends HTMLAttributes<HTMLElement> {
|
||||
export interface AccordionMenuProps extends React.HTMLAttributes<HTMLElement> {
|
||||
children: React.ReactNode;
|
||||
}
|
||||
|
||||
interface AccordionMenuComponent
|
||||
extends React.ForwardRefExoticComponent<
|
||||
AccordionMenuProps & React.RefAttributes<HTMLElement>
|
||||
> {
|
||||
Collapsable: AccordionMenuCollapsableType;
|
||||
Item: AccordionMenuItemType;
|
||||
}
|
||||
|
||||
const AccordionMenu = forwardRef<HTMLElement, AccordionMenuProps>(
|
||||
({ children, className, ...rest }, ref) => {
|
||||
return (
|
||||
@@ -19,6 +31,9 @@ const AccordionMenu = forwardRef<HTMLElement, AccordionMenuProps>(
|
||||
</nav>
|
||||
);
|
||||
}
|
||||
);
|
||||
) as AccordionMenuComponent;
|
||||
|
||||
AccordionMenu.Collapsable = Collapsable;
|
||||
AccordionMenu.Item = Item;
|
||||
|
||||
export default AccordionMenu;
|
||||
@@ -10,35 +10,38 @@ export interface AccordionMenuCollapsableProps
|
||||
children: React.ReactNode;
|
||||
}
|
||||
|
||||
const AccordionMenuCollapsable = forwardRef<
|
||||
HTMLDivElement,
|
||||
AccordionMenuCollapsableProps
|
||||
>(({ children, defaultOpen = false, title, className, ...rest }, ref) => {
|
||||
const [isOpen, setIsOpen] = useState(defaultOpen);
|
||||
export type AccordionMenuCollapsableType = React.ForwardRefExoticComponent<
|
||||
AccordionMenuCollapsableProps & React.RefAttributes<HTMLDivElement>
|
||||
>;
|
||||
|
||||
return (
|
||||
<div
|
||||
ref={ref}
|
||||
className={cl("navds-accordion-menu-collapsable", className, {
|
||||
"navds-accordion-menu-collapsable--open": isOpen,
|
||||
})}
|
||||
{...rest}
|
||||
>
|
||||
<button
|
||||
onClick={() => setIsOpen(!isOpen)}
|
||||
className="navds-accordion-menu-collapsable__button"
|
||||
const Collapsable: AccordionMenuCollapsableType = forwardRef(
|
||||
({ children, defaultOpen = false, title, className, ...rest }, ref) => {
|
||||
const [isOpen, setIsOpen] = useState(defaultOpen);
|
||||
|
||||
return (
|
||||
<div
|
||||
ref={ref}
|
||||
className={cl("navds-accordion-menu-collapsable", className, {
|
||||
"navds-accordion-menu-collapsable--open": isOpen,
|
||||
})}
|
||||
{...rest}
|
||||
>
|
||||
{title}
|
||||
<Expand
|
||||
role="img"
|
||||
focusable="false"
|
||||
aria-label={isOpen ? "Pil peker opp" : "Pil peker ned"}
|
||||
className="navds-accordion-menu-collapsable__expand-icon"
|
||||
/>
|
||||
</button>
|
||||
{isOpen && <MenuItems>{children}</MenuItems>}
|
||||
</div>
|
||||
);
|
||||
});
|
||||
<button
|
||||
onClick={() => setIsOpen(!isOpen)}
|
||||
className="navds-accordion-menu-collapsable__button"
|
||||
>
|
||||
{title}
|
||||
<Expand
|
||||
role="img"
|
||||
focusable="false"
|
||||
aria-label={isOpen ? "Pil peker opp" : "Pil peker ned"}
|
||||
className="navds-accordion-menu-collapsable__expand-icon"
|
||||
/>
|
||||
</button>
|
||||
{isOpen && <MenuItems>{children}</MenuItems>}
|
||||
</div>
|
||||
);
|
||||
}
|
||||
);
|
||||
|
||||
export default AccordionMenuCollapsable;
|
||||
export default Collapsable;
|
||||
@@ -1,26 +1,25 @@
|
||||
import React, { forwardRef } from "react";
|
||||
import { OverridableComponent } from "../util";
|
||||
import { OverridableComponent } from "..";
|
||||
import cl from "classnames";
|
||||
|
||||
export type AccordionMenuItemType = OverridableComponent<AccordionMenuItemProps>;
|
||||
|
||||
export interface AccordionMenuItemProps {
|
||||
props: {
|
||||
children: React.ReactNode;
|
||||
active?: boolean;
|
||||
} & React.HTMLAttributes<HTMLAnchorElement>;
|
||||
defaultComponent: "a";
|
||||
export interface AccordionMenuItemProps
|
||||
extends React.AnchorHTMLAttributes<HTMLAnchorElement> {
|
||||
children: React.ReactNode;
|
||||
/**
|
||||
* Sets active styling if true
|
||||
* @default false
|
||||
*/
|
||||
active?: boolean;
|
||||
}
|
||||
|
||||
const AccordionMenuItem: AccordionMenuItemType = forwardRef(
|
||||
export type AccordionMenuItemType = OverridableComponent<
|
||||
AccordionMenuItemProps,
|
||||
HTMLAnchorElement
|
||||
>;
|
||||
|
||||
const Item: AccordionMenuItemType = forwardRef(
|
||||
(
|
||||
{
|
||||
children,
|
||||
component: Component = "a",
|
||||
active = false,
|
||||
className,
|
||||
...rest
|
||||
},
|
||||
{ children, as: Component = "a", active = false, className, ...rest },
|
||||
ref
|
||||
) => {
|
||||
return (
|
||||
@@ -37,4 +36,4 @@ const AccordionMenuItem: AccordionMenuItemType = forwardRef(
|
||||
}
|
||||
);
|
||||
|
||||
export default AccordionMenuItem;
|
||||
export default Item;
|
||||
@@ -1,6 +1,3 @@
|
||||
export { default as AccordionMenu } from "./AccordionMenu";
|
||||
export { default as AccordionMenuCollapsable } from "./AccordionMenuCollapsable";
|
||||
export {
|
||||
default as AccordionMenuItem,
|
||||
AccordionMenuItemType,
|
||||
} from "./AccordionMenuItem";
|
||||
export { default as AccordionMenu, AccordionMenuProps } from "./AccordionMenu";
|
||||
export { AccordionMenuCollapsableProps } from "./AccordionMenuCollapsable";
|
||||
export { AccordionMenuItemProps } from "./AccordionMenuItem";
|
||||
@@ -1,9 +1,5 @@
|
||||
import { Meta, Canvas } from "@storybook/addon-docs";
|
||||
import {
|
||||
AccordionMenu,
|
||||
AccordionMenuItem,
|
||||
AccordionMenuCollapsable,
|
||||
} from "../../index";
|
||||
import { AccordionMenu } from "../../index";
|
||||
|
||||
<Meta title="ds-react/accordion-menu/intro" />
|
||||
|
||||
@@ -11,59 +7,59 @@ import {
|
||||
|
||||
```jsx
|
||||
<AccordionMenu>
|
||||
<AccordionMenuItem href="#leo">Leo</AccordionMenuItem>
|
||||
<AccordionMenuCollapsable title="Proin">
|
||||
<AccordionMenuItem href="#nulla" active>
|
||||
<AccordionMenu.item href="#leo">Leo</AccordionMenu.item>
|
||||
<AccordionMenu.Collapsable title="Proin">
|
||||
<AccordionMenu.item href="#nulla" active>
|
||||
Nulla
|
||||
</AccordionMenuItem>
|
||||
<AccordionMenuItem href="#luctus">Luctus</AccordionMenuItem>
|
||||
</AccordionMenuCollapsable>
|
||||
<AccordionMenuCollapsable title="Accumsan">
|
||||
<AccordionMenuItem href="#justo" aria-current="page">
|
||||
</AccordionMenu.item>
|
||||
<AccordionMenu.item href="#luctus">Luctus</AccordionMenu.item>
|
||||
</AccordionMenu.Collapsable>
|
||||
<AccordionMenu.Collapsable title="Accumsan">
|
||||
<AccordionMenu.item href="#justo" aria-current="page">
|
||||
Justo
|
||||
</AccordionMenuItem>
|
||||
<AccordionMenuCollapsable title="Proin">
|
||||
<AccordionMenuItem href="#nulla">Nulla</AccordionMenuItem>
|
||||
<AccordionMenuItem href="#luctus">Luctus</AccordionMenuItem>
|
||||
</AccordionMenuCollapsable>
|
||||
</AccordionMenuCollapsable>
|
||||
</AccordionMenu.item>
|
||||
<AccordionMenu.Collapsable title="Proin">
|
||||
<AccordionMenu.item href="#nulla">Nulla</AccordionMenu.item>
|
||||
<AccordionMenu.item href="#luctus">Luctus</AccordionMenu.item>
|
||||
</AccordionMenu.Collapsable>
|
||||
</AccordionMenu.Collapsable>
|
||||
</AccordionMenu>
|
||||
```
|
||||
|
||||
<Canvas>
|
||||
<AccordionMenu>
|
||||
<AccordionMenuItem href="#leo">Leo</AccordionMenuItem>
|
||||
<AccordionMenuCollapsable title="Proin">
|
||||
<AccordionMenuItem href="#nulla" active>
|
||||
<AccordionMenu.Item href="#leo">Leo</AccordionMenu.Item>
|
||||
<AccordionMenu.Collapsable title="Proin">
|
||||
<AccordionMenu.Item href="#nulla" active>
|
||||
Nulla
|
||||
</AccordionMenuItem>
|
||||
<AccordionMenuItem href="#luctus">Luctus</AccordionMenuItem>
|
||||
</AccordionMenuCollapsable>
|
||||
<AccordionMenuCollapsable title="Accumsan">
|
||||
<AccordionMenuItem href="#justo" aria-current="page">
|
||||
</AccordionMenu.Item>
|
||||
<AccordionMenu.Item href="#luctus">Luctus</AccordionMenu.Item>
|
||||
</AccordionMenu.Collapsable>
|
||||
<AccordionMenu.Collapsable title="Accumsan">
|
||||
<AccordionMenu.Item href="#justo" aria-current="page">
|
||||
Justo
|
||||
</AccordionMenuItem>
|
||||
<AccordionMenuCollapsable title="Proin">
|
||||
<AccordionMenuItem href="#nulla">Nulla</AccordionMenuItem>
|
||||
<AccordionMenuItem href="#luctus">Luctus</AccordionMenuItem>
|
||||
</AccordionMenuCollapsable>
|
||||
</AccordionMenuCollapsable>
|
||||
</AccordionMenu.Item>
|
||||
<AccordionMenu.Collapsable title="Proin">
|
||||
<AccordionMenu.Item href="#nulla">Nulla</AccordionMenu.Item>
|
||||
<AccordionMenu.Item href="#luctus">Luctus</AccordionMenu.Item>
|
||||
</AccordionMenu.Collapsable>
|
||||
</AccordionMenu.Collapsable>
|
||||
</AccordionMenu>
|
||||
</Canvas>
|
||||
|
||||
Accordion-menu støtter opp til maks to-nivårer av `AccordionMenuCollapsable` akkurat nå.
|
||||
Accordion-menu støtter opp til maks to-nivårer av `AccordionMenu.Collapsable` akkurat nå.
|
||||
|
||||
`AccordionMenuItem` er implementert med `OverridableComponent`, noe som
|
||||
`AccordionMenu.Item` er implementert med `OverridableComponent`, noe som
|
||||
gjør at man kan ta i bruk eks react-router slik:
|
||||
|
||||
```jsx
|
||||
<Item
|
||||
component={NavLink}
|
||||
<AccordionMenu.item
|
||||
as={NavLink}
|
||||
activeClassName="navds-accordion-menu-item--active"
|
||||
to="/1"
|
||||
>
|
||||
Lenketekst
|
||||
</Item>
|
||||
</AccordionMenu.item>
|
||||
```
|
||||
|
||||
Her er `NavLink` fra `react-router-dom` brukt, og man får da
|
||||
|
||||
@@ -1,29 +1,10 @@
|
||||
import * as React from "react";
|
||||
import {
|
||||
AccordionMenu,
|
||||
AccordionMenuItem as Item,
|
||||
AccordionMenuCollapsable as Collapsable,
|
||||
} from "../index";
|
||||
import { AccordionMenu } from "../index";
|
||||
import { NavLink, HashRouter as Router } from "react-router-dom";
|
||||
|
||||
export default {
|
||||
title: "ds-react/accordion-menu",
|
||||
component: { AccordionMenu },
|
||||
parameters: {
|
||||
backgrounds: {
|
||||
default: "light",
|
||||
values: [
|
||||
{
|
||||
name: "light",
|
||||
value: "#F1F1F1",
|
||||
},
|
||||
{
|
||||
name: "white",
|
||||
value: "#fff",
|
||||
},
|
||||
],
|
||||
},
|
||||
},
|
||||
};
|
||||
|
||||
export const All = () => (
|
||||
@@ -34,113 +15,113 @@ export const All = () => (
|
||||
}}
|
||||
>
|
||||
<AccordionMenu>
|
||||
<Item href="#leo">Leo</Item>
|
||||
<Collapsable title="Proin">
|
||||
<Item href="#nulla" active>
|
||||
<AccordionMenu.Item href="#leo">Leo</AccordionMenu.Item>
|
||||
<AccordionMenu.Collapsable title="Proin">
|
||||
<AccordionMenu.Item href="#nulla" active>
|
||||
Nulla
|
||||
</Item>
|
||||
<Item href="#luctus">Luctus</Item>
|
||||
</Collapsable>
|
||||
<Collapsable title="Accumsan">
|
||||
<Item href="#justo" aria-current="page">
|
||||
</AccordionMenu.Item>
|
||||
<AccordionMenu.Item href="#luctus">Luctus</AccordionMenu.Item>
|
||||
</AccordionMenu.Collapsable>
|
||||
<AccordionMenu.Collapsable title="Accumsan">
|
||||
<AccordionMenu.Item href="#justo" aria-current="page">
|
||||
Justo
|
||||
</Item>
|
||||
<Item href="#pariatur" active aria-current="page">
|
||||
</AccordionMenu.Item>
|
||||
<AccordionMenu.Item href="#pariatur" active aria-current="page">
|
||||
Pariatur
|
||||
</Item>
|
||||
<Collapsable title="Proin">
|
||||
<Item href="#nulla" active>
|
||||
</AccordionMenu.Item>
|
||||
<AccordionMenu.Collapsable title="Proin">
|
||||
<AccordionMenu.Item href="#nulla" active>
|
||||
Nulla
|
||||
</Item>
|
||||
<Item href="#luctus">Luctus</Item>
|
||||
</Collapsable>
|
||||
</Collapsable>
|
||||
<Item href="#justo" active>
|
||||
</AccordionMenu.Item>
|
||||
<AccordionMenu.Item href="#luctus">Luctus</AccordionMenu.Item>
|
||||
</AccordionMenu.Collapsable>
|
||||
</AccordionMenu.Collapsable>
|
||||
<AccordionMenu.Item href="#justo" active>
|
||||
Justo
|
||||
</Item>
|
||||
<Item href="#pariatur">Pariatur</Item>
|
||||
</AccordionMenu.Item>
|
||||
<AccordionMenu.Item href="#pariatur">Pariatur</AccordionMenu.Item>
|
||||
</AccordionMenu>
|
||||
</div>
|
||||
);
|
||||
|
||||
export const ReactRouter = () => (
|
||||
<AccordionMenu>
|
||||
<Collapsable title="Nivå 1 – 3 rems høy">
|
||||
<Item
|
||||
component={NavLink}
|
||||
<AccordionMenu.Collapsable title="Nivå 1 – 3 rems høy">
|
||||
<AccordionMenu.Item
|
||||
as={NavLink}
|
||||
activeClassName="navds-accordion-menu-item--active"
|
||||
to="/1"
|
||||
>
|
||||
Nivå 2 innrykk 2 rems
|
||||
</Item>
|
||||
<Item
|
||||
component={NavLink}
|
||||
</AccordionMenu.Item>
|
||||
<AccordionMenu.Item
|
||||
as={NavLink}
|
||||
activeClassName="navds-accordion-menu-item--active"
|
||||
to="/2"
|
||||
>
|
||||
Subtitle 3
|
||||
</Item>
|
||||
</Collapsable>
|
||||
<Collapsable title="Skjema og søknad">
|
||||
<Collapsable title="Satser">
|
||||
<Item
|
||||
component={NavLink}
|
||||
</AccordionMenu.Item>
|
||||
</AccordionMenu.Collapsable>
|
||||
<AccordionMenu.Collapsable title="Skjema og søknad">
|
||||
<AccordionMenu.Collapsable title="Satser">
|
||||
<AccordionMenu.Item
|
||||
as={NavLink}
|
||||
activeClassName="navds-accordion-menu-item--active"
|
||||
to="/3"
|
||||
>
|
||||
Nivå 3 – 3 rems innrykk Har du rett til dagpenger når du mottar annen
|
||||
økonomisk støtte fra NAV?
|
||||
</Item>
|
||||
</Collapsable>
|
||||
<Item
|
||||
component={NavLink}
|
||||
</AccordionMenu.Item>
|
||||
</AccordionMenu.Collapsable>
|
||||
<AccordionMenu.Item
|
||||
as={NavLink}
|
||||
activeClassName="navds-accordion-menu-item--active"
|
||||
to="/4"
|
||||
>
|
||||
Subtitle 2
|
||||
</Item>
|
||||
<Item
|
||||
component={NavLink}
|
||||
</AccordionMenu.Item>
|
||||
<AccordionMenu.Item
|
||||
as={NavLink}
|
||||
activeClassName="navds-accordion-menu-item--active"
|
||||
to="/5"
|
||||
>
|
||||
Subtitle 3
|
||||
</Item>
|
||||
</Collapsable>
|
||||
<Collapsable title="Sakbehandlingstider">
|
||||
<Collapsable title="Subtitle 4 Lang tittel på andre nivå lorem ipsum">
|
||||
<Item
|
||||
component={NavLink}
|
||||
</AccordionMenu.Item>
|
||||
</AccordionMenu.Collapsable>
|
||||
<AccordionMenu.Collapsable title="Sakbehandlingstider">
|
||||
<AccordionMenu.Collapsable title="Subtitle 4 Lang tittel på andre nivå lorem ipsum">
|
||||
<AccordionMenu.Item
|
||||
as={NavLink}
|
||||
activeClassName="navds-accordion-menu-item--active"
|
||||
to="/6"
|
||||
>
|
||||
Subtitle 5
|
||||
</Item>
|
||||
</Collapsable>
|
||||
</Collapsable>
|
||||
<Item
|
||||
component={NavLink}
|
||||
</AccordionMenu.Item>
|
||||
</AccordionMenu.Collapsable>
|
||||
</AccordionMenu.Collapsable>
|
||||
<AccordionMenu.Item
|
||||
as={NavLink}
|
||||
activeClassName="navds-accordion-menu-item--active"
|
||||
to="/7"
|
||||
>
|
||||
Internasjonalt
|
||||
</Item>
|
||||
<Collapsable title="Meld fra om endringer lang tittel på første nivå">
|
||||
<Item
|
||||
component={NavLink}
|
||||
</AccordionMenu.Item>
|
||||
<AccordionMenu.Collapsable title="Meld fra om endringer lang tittel på første nivå">
|
||||
<AccordionMenu.Item
|
||||
as={NavLink}
|
||||
activeClassName="navds-accordion-menu-item--active"
|
||||
to="/8"
|
||||
>
|
||||
Subtitle 6
|
||||
</Item>
|
||||
</Collapsable>
|
||||
<Item
|
||||
component={NavLink}
|
||||
</AccordionMenu.Item>
|
||||
</AccordionMenu.Collapsable>
|
||||
<AccordionMenu.Item
|
||||
as={NavLink}
|
||||
activeClassName="navds-accordion-menu-item--active"
|
||||
to="/9"
|
||||
>
|
||||
Nivå 1
|
||||
</Item>
|
||||
</AccordionMenu.Item>
|
||||
</AccordionMenu>
|
||||
);
|
||||
|
||||
|
||||
@@ -1,108 +1,33 @@
|
||||
import React, { forwardRef, useEffect, useState } from "react";
|
||||
import cl from "classnames";
|
||||
import { UnmountClosed, Collapse } from "react-collapse";
|
||||
import { Expand, ExpandFilled } from "@navikt/ds-icons";
|
||||
import { useId } from "..";
|
||||
import React, { forwardRef } from "react";
|
||||
import AccordionItem, { AccordionItemType } from "./AccordionItem";
|
||||
import AccordionContent, { AccordionContentType } from "./AccordionContent";
|
||||
import AccordionHeader, { AccordionHeaderType } from "./AccordionHeader";
|
||||
|
||||
export interface AccordionProps
|
||||
extends React.HTMLAttributes<HTMLButtonElement> {
|
||||
/**
|
||||
* Component content
|
||||
*/
|
||||
children: React.ReactNode;
|
||||
/**
|
||||
* Content on interactive surface of component
|
||||
*/
|
||||
heading: React.ReactNode;
|
||||
/**
|
||||
* Opens component if 'true', closes if 'false'
|
||||
* Using this props removes automatic control of open-state
|
||||
* @default false
|
||||
*/
|
||||
open?: boolean;
|
||||
/**
|
||||
* Callback for when user interacts with component
|
||||
*/
|
||||
onClick?: (event: React.MouseEvent<HTMLElement, MouseEvent>) => void;
|
||||
/**
|
||||
* Removes content-element from dom when closed
|
||||
* @default false
|
||||
*/
|
||||
renderContentWhenClosed?: boolean;
|
||||
interface AccordionComponent
|
||||
extends React.ForwardRefExoticComponent<
|
||||
AccordionProps & React.RefAttributes<HTMLDivElement>
|
||||
> {
|
||||
Item: AccordionItemType;
|
||||
Header: AccordionHeaderType;
|
||||
Content: AccordionContentType;
|
||||
}
|
||||
|
||||
const Accordion = forwardRef<HTMLButtonElement, AccordionProps>(
|
||||
(
|
||||
{
|
||||
children,
|
||||
heading,
|
||||
open = false,
|
||||
className,
|
||||
renderContentWhenClosed = false,
|
||||
onClick,
|
||||
id,
|
||||
...rest
|
||||
},
|
||||
ref
|
||||
) => {
|
||||
const [internalOpen, setInternalOpen] = useState<boolean>(open);
|
||||
export interface AccordionProps extends React.HTMLAttributes<HTMLDivElement> {
|
||||
/**
|
||||
* Content inside accordion
|
||||
*/
|
||||
children: React.ReactNode;
|
||||
}
|
||||
|
||||
const buttonId = useId(id);
|
||||
const contentId = useId();
|
||||
const Accordion = forwardRef<HTMLDivElement, AccordionProps>(
|
||||
({ className, ...rest }, ref) => (
|
||||
<div {...rest} className={cl("navds-accordion", className)} ref={ref} />
|
||||
)
|
||||
) as AccordionComponent;
|
||||
|
||||
useEffect(() => {
|
||||
setInternalOpen(open);
|
||||
}, [open]);
|
||||
|
||||
const CollapseComponent = renderContentWhenClosed
|
||||
? Collapse
|
||||
: UnmountClosed;
|
||||
|
||||
return (
|
||||
<div
|
||||
className={cl("navds-accordion", className, {
|
||||
"navds-accordion--open": internalOpen,
|
||||
"navds-accordion--closed": !internalOpen,
|
||||
})}
|
||||
>
|
||||
<button
|
||||
ref={ref}
|
||||
id={buttonId}
|
||||
className="navds-accordion__button"
|
||||
aria-expanded={open}
|
||||
aria-controls={contentId}
|
||||
onClick={onClick ? onClick : () => setInternalOpen((open) => !open)}
|
||||
{...rest}
|
||||
>
|
||||
<span className="navds-accordion__heading navds-title navds-title--s">
|
||||
{heading}
|
||||
</span>
|
||||
<Expand
|
||||
focusable="false"
|
||||
role="img"
|
||||
className={cl(
|
||||
"navds-accordion__chevron",
|
||||
`navds-accordion__chevron--${internalOpen ? "up" : "down"}`
|
||||
)}
|
||||
/>
|
||||
<ExpandFilled
|
||||
focusable="false"
|
||||
role="img"
|
||||
className={cl(
|
||||
"navds-accordion__chevron",
|
||||
"navds-accordion__chevron--filled",
|
||||
`navds-accordion__chevron--${internalOpen ? "up" : "down"}`
|
||||
)}
|
||||
/>
|
||||
</button>
|
||||
<div id={contentId} role="region" aria-labelledby={buttonId}>
|
||||
<CollapseComponent isOpened={internalOpen}>
|
||||
<div className="navds-accordion__content">{children}</div>
|
||||
</CollapseComponent>
|
||||
</div>
|
||||
</div>
|
||||
);
|
||||
}
|
||||
);
|
||||
Accordion.Header = AccordionHeader;
|
||||
Accordion.Content = AccordionContent;
|
||||
Accordion.Item = AccordionItem;
|
||||
|
||||
export default Accordion;
|
||||
@@ -0,0 +1,59 @@
|
||||
import cl from "classnames";
|
||||
import React, { forwardRef, useContext } from "react";
|
||||
import { Collapse, UnmountClosed } from "react-collapse";
|
||||
import { useClientLayoutEffect, useId } from "../util";
|
||||
import { AccordionItemContext } from "./AccordionItem";
|
||||
|
||||
export interface AccordionContentProps
|
||||
extends React.HTMLAttributes<HTMLDivElement> {
|
||||
/**
|
||||
* Accordion panel content
|
||||
*/
|
||||
children: React.ReactNode;
|
||||
}
|
||||
|
||||
export type AccordionContentType = React.ForwardRefExoticComponent<
|
||||
AccordionContentProps & React.RefAttributes<HTMLDivElement>
|
||||
>;
|
||||
|
||||
const AccordionContent: AccordionContentType = forwardRef(
|
||||
({ children, className, id, ...rest }, ref) => {
|
||||
const context = useContext(AccordionItemContext);
|
||||
|
||||
const newId = useId(id);
|
||||
const setContentId = context && context.setContentId;
|
||||
|
||||
useClientLayoutEffect(() => {
|
||||
setContentId && setContentId(id ? newId : `accordionContent-${newId}`);
|
||||
}, [setContentId, newId]);
|
||||
|
||||
if (context === null) {
|
||||
console.error(
|
||||
"<Accordion.Content> has to be used within an <Accordion.Item>"
|
||||
);
|
||||
return null;
|
||||
}
|
||||
|
||||
const CollapseComponent = context.renderContentWhenClosed
|
||||
? Collapse
|
||||
: UnmountClosed;
|
||||
|
||||
return (
|
||||
<div
|
||||
ref={ref}
|
||||
id={context.contentId}
|
||||
role="region"
|
||||
aria-labelledby={context.buttonId}
|
||||
{...rest}
|
||||
>
|
||||
<CollapseComponent isOpened={context.open}>
|
||||
<div className={cl("navds-accordion__content", className)}>
|
||||
{children}
|
||||
</div>
|
||||
</CollapseComponent>
|
||||
</div>
|
||||
);
|
||||
}
|
||||
);
|
||||
|
||||
export default AccordionContent;
|
||||
@@ -0,0 +1,84 @@
|
||||
import { Expand, ExpandFilled } from "@navikt/ds-icons";
|
||||
import cl from "classnames";
|
||||
import React, { forwardRef, useContext } from "react";
|
||||
import { AccordionItemContext } from "./AccordionItem";
|
||||
import { useClientLayoutEffect, useId } from "..";
|
||||
|
||||
export interface AccordionHeaderProps
|
||||
extends React.ButtonHTMLAttributes<HTMLButtonElement> {
|
||||
/**
|
||||
* Button content
|
||||
*/
|
||||
children: React.ReactNode;
|
||||
}
|
||||
|
||||
export type AccordionHeaderType = React.ForwardRefExoticComponent<
|
||||
AccordionHeaderProps & React.RefAttributes<HTMLButtonElement>
|
||||
>;
|
||||
|
||||
const AccordionHeader: AccordionHeaderType = forwardRef(
|
||||
({ children, className, id, onClick, ...rest }, ref) => {
|
||||
const context = useContext(AccordionItemContext);
|
||||
const newId = useId(id);
|
||||
|
||||
const setButtonId = context && context.setButtonId;
|
||||
|
||||
useClientLayoutEffect(() => {
|
||||
setButtonId && setButtonId(id ? newId : `accordionContent-${newId}`);
|
||||
}, [setButtonId, newId]);
|
||||
|
||||
if (context === null) {
|
||||
console.error(
|
||||
"<Accordion.Header> has to be used within an <Accordion.Item>"
|
||||
);
|
||||
return null;
|
||||
}
|
||||
|
||||
const handleClick = (
|
||||
e: React.MouseEvent<HTMLButtonElement, MouseEvent>
|
||||
) => {
|
||||
context.toggleOpen();
|
||||
onClick && onClick(e);
|
||||
};
|
||||
|
||||
return (
|
||||
<button
|
||||
ref={ref}
|
||||
id={context.buttonId}
|
||||
className={cl(
|
||||
"navds-accordion__header",
|
||||
className,
|
||||
"navds-heading",
|
||||
"navds-heading--small"
|
||||
)}
|
||||
onClick={handleClick}
|
||||
aria-controls={context.contentId}
|
||||
{...rest}
|
||||
>
|
||||
{children}
|
||||
<Expand
|
||||
focusable="false"
|
||||
role="img"
|
||||
aria-label={context.open ? "Lukk panel ikon" : "Åpne panel ikon"}
|
||||
className={cl("navds-accordion__expand-icon", {
|
||||
"navds-accordion__expand-icon--flip": context.open,
|
||||
})}
|
||||
/>
|
||||
<ExpandFilled
|
||||
focusable="false"
|
||||
role="img"
|
||||
aria-label={context.open ? "Lukk panel ikon" : "Åpne panel ikon"}
|
||||
className={cl(
|
||||
"navds-accordion__expand-icon",
|
||||
"navds-accordion__expand-icon--filled",
|
||||
{
|
||||
"navds-accordion__expand-icon--flip": context.open,
|
||||
}
|
||||
)}
|
||||
/>
|
||||
</button>
|
||||
);
|
||||
}
|
||||
);
|
||||
|
||||
export default AccordionHeader;
|
||||
@@ -0,0 +1,93 @@
|
||||
import cl from "classnames";
|
||||
import React, { createContext, forwardRef, useState } from "react";
|
||||
|
||||
export interface AccordionItemProps
|
||||
extends React.HTMLAttributes<HTMLDivElement> {
|
||||
/**
|
||||
* Content inside accordion item
|
||||
*/
|
||||
children: React.ReactNode;
|
||||
/**
|
||||
* Opens component if 'true', closes if 'false'
|
||||
* Using this props removes automatic control of open-state
|
||||
*/
|
||||
open?: boolean;
|
||||
/**
|
||||
* Defaults the accordion to opened state
|
||||
* @default false
|
||||
*/
|
||||
defaultOpen?: boolean;
|
||||
/**
|
||||
* Removes content-element from dom when closed
|
||||
* @default false
|
||||
*/
|
||||
renderContentWhenClosed?: boolean;
|
||||
}
|
||||
|
||||
export type AccordionItemType = React.ForwardRefExoticComponent<
|
||||
AccordionItemProps & React.RefAttributes<HTMLDivElement>
|
||||
>;
|
||||
|
||||
export interface AccordionItemContextProps {
|
||||
open: boolean;
|
||||
toggleOpen: () => void;
|
||||
setButtonId: (id: string) => void;
|
||||
setContentId: (id: string) => void;
|
||||
buttonId: string;
|
||||
contentId: string;
|
||||
renderContentWhenClosed: boolean;
|
||||
}
|
||||
|
||||
export const AccordionItemContext = createContext<AccordionItemContextProps | null>(
|
||||
null
|
||||
);
|
||||
|
||||
const AccordionItem: AccordionItemType = forwardRef(
|
||||
(
|
||||
{
|
||||
children,
|
||||
className,
|
||||
open,
|
||||
defaultOpen = false,
|
||||
renderContentWhenClosed = false,
|
||||
onClick,
|
||||
id,
|
||||
...rest
|
||||
},
|
||||
ref
|
||||
) => {
|
||||
const [internalOpen, setInternalOpen] = useState<boolean>(defaultOpen);
|
||||
const [buttonId, setButtonId] = useState("");
|
||||
const [contentId, setContentId] = useState("");
|
||||
|
||||
return (
|
||||
<div
|
||||
className={cl("navds-accordion__item", className, {
|
||||
"navds-accordion__item--open": open ?? internalOpen,
|
||||
})}
|
||||
ref={ref}
|
||||
{...rest}
|
||||
>
|
||||
<AccordionItemContext.Provider
|
||||
value={{
|
||||
open: open ?? internalOpen,
|
||||
toggleOpen: () => {
|
||||
if (open === undefined) {
|
||||
setInternalOpen((iOpen) => !iOpen);
|
||||
}
|
||||
},
|
||||
renderContentWhenClosed,
|
||||
setButtonId,
|
||||
buttonId,
|
||||
setContentId,
|
||||
contentId,
|
||||
}}
|
||||
>
|
||||
{children}
|
||||
</AccordionItemContext.Provider>
|
||||
</div>
|
||||
);
|
||||
}
|
||||
);
|
||||
|
||||
export default AccordionItem;
|
||||
@@ -1,4 +1,4 @@
|
||||
import { Meta, Canvas } from "@storybook/addon-docs";
|
||||
import { Meta, Canvas, Props } from "@storybook/addon-docs";
|
||||
import { Accordion } from "../../index";
|
||||
|
||||
<Meta title="ds-react/accordion/intro" />
|
||||
@@ -6,28 +6,67 @@ import { Accordion } from "../../index";
|
||||
# Hvordan ta i bruk Accordion
|
||||
|
||||
```jsx
|
||||
<Accordion heading="Qui id id ad cupidatat ullamco.">
|
||||
Et anim nostrud reprehenderit duis eu tempor et irure proident. Eu ea occaecat
|
||||
aliqua commodo sunt. Sit cupidatat ad id occaecat exercitation ipsum laboris
|
||||
duis velit consequat adipisicing do amet aute. Aliquip culpa minim commodo
|
||||
laborum eiusmod eu magna elit veniam ullamco ullamco minim.
|
||||
<Accordion>
|
||||
<Accordion.Item>
|
||||
<Accordion.Header>Accordion header text</Accordion.Header>
|
||||
<Accordion.Content>
|
||||
Magna aliquip aliquip fugiat nostrud nostrud velit pariatur veniam officia
|
||||
laboris voluptate officia pariatur.Lorem est ex anim velit occaecat nisi
|
||||
qui nostrud sit.
|
||||
</Accordion.Content>
|
||||
</Accordion.Item>
|
||||
<Accordion.Item>
|
||||
<Accordion.Header>Aliquip amet irure consectetur occaecat</Accordion.Header>
|
||||
<Accordion.Content>
|
||||
Cupidatat aliqua eu ea et anim excepteur. Labore aliquip dolore laborum
|
||||
consequat. Reprehenderit ad velit quis eiusmod ex sint aliquip do deserunt
|
||||
amet exercitation velit Lorem.
|
||||
</Accordion.Content>
|
||||
</Accordion.Item>
|
||||
</Accordion>
|
||||
```
|
||||
|
||||
<Canvas>
|
||||
<Accordion heading="Qui id id ad cupidatat ullamco.">
|
||||
Et anim nostrud reprehenderit duis eu tempor et irure proident. Eu ea
|
||||
occaecat aliqua commodo sunt. Sit cupidatat ad id occaecat exercitation
|
||||
ipsum laboris duis velit consequat adipisicing do amet aute. Aliquip culpa
|
||||
minim commodo laborum eiusmod eu magna elit veniam ullamco ullamco minim.
|
||||
<Accordion>
|
||||
<Accordion.Item>
|
||||
<Accordion.Header>Accordion header text</Accordion.Header>
|
||||
<Accordion.Content>
|
||||
Magna aliquip aliquip fugiat nostrud nostrud velit pariatur veniam
|
||||
officia laboris voluptate officia pariatur.Lorem est ex anim velit
|
||||
occaecat nisi qui nostrud sit.
|
||||
</Accordion.Content>
|
||||
</Accordion.Item>
|
||||
<Accordion.Item>
|
||||
<Accordion.Header>
|
||||
Aliquip amet irure consectetur occaecat
|
||||
</Accordion.Header>
|
||||
<Accordion.Content>
|
||||
Cupidatat aliqua eu ea et anim excepteur. Labore aliquip dolore laborum
|
||||
consequat. Reprehenderit ad velit quis eiusmod ex sint aliquip do
|
||||
deserunt amet exercitation velit Lorem.
|
||||
</Accordion.Content>
|
||||
</Accordion.Item>
|
||||
</Accordion>
|
||||
</Canvas>
|
||||
|
||||
Accordion-komponeten styrer selv open/closed state, men om man ønsker kan man selv overskrive denne med
|
||||
`open`-prop + `onClick`-prop.
|
||||
## Controlled state
|
||||
|
||||
Note: Hvis man tar i bruk `onClick`, så tolker komponeten det slik at du ønsker å styre state selv, så
|
||||
man må da også bruke `open`-prop
|
||||
Accordion-komponeten styrer selv open-state, men om man ønsker kan man selv overskrive denne med
|
||||
`open`-prop + `onClick`-prop slik det er gjort på eksemplet.
|
||||
|
||||
`renderContentWhenClosed`-prop bestemmer om innholdet (children) skal beholdes i dom-strukturen mens
|
||||
```jsx
|
||||
<Accordion>
|
||||
<Accordion.Item open={open}>
|
||||
<Accordion.Header onClick={(open) => setOpen(!open)}>
|
||||
Accordion header text
|
||||
</Accordion.Header>
|
||||
<Accordion.Content>
|
||||
Magna aliquip aliquip fugiat nostrud nostrud velit pariatur veniam officia
|
||||
laboris voluptate officia pariatur.Lorem est ex anim velit
|
||||
</Accordion.Content>
|
||||
</Accordion.Item>
|
||||
</Accordion>
|
||||
```
|
||||
|
||||
`renderContentWhenClosed`-prop på `Accordion.Item` bestemmer om innholdet (children) skal beholdes i dom-strukturen mens
|
||||
Accordion er lukket. Defaulter til `false`.
|
||||
@@ -1,9 +1,17 @@
|
||||
import React, { useState } from "react";
|
||||
import AccordionContent from "../AccordionContent";
|
||||
import AccordionHeader from "../AccordionHeader";
|
||||
import AccordionItem from "../AccordionItem";
|
||||
import { Accordion } from "../index";
|
||||
|
||||
export default {
|
||||
title: "ds-react/accordion",
|
||||
component: Accordion,
|
||||
subcomponents: {
|
||||
AccordionItem,
|
||||
AccordionContent,
|
||||
AccordionHeader,
|
||||
},
|
||||
};
|
||||
|
||||
export const All = () => {
|
||||
@@ -11,49 +19,74 @@ export const All = () => {
|
||||
|
||||
return (
|
||||
<>
|
||||
<h1>Accordion</h1>
|
||||
<Accordion heading="tittel" open={open} onClick={(e) => setOpen(!open)}>
|
||||
Eu magna fugiat officia sit ullamco reprehenderit reprehenderit officia.
|
||||
Culpa fugiat irure deserunt irure enim adipisicing qui id. Pariatur
|
||||
commodo dolore consequat nulla cupidatat commodo nisi sunt. Ad proident
|
||||
occaecat cillum eu Lorem proident sunt anim officia voluptate. Veniam
|
||||
ullamco magna elit amet mollit exercitation magna quis ad occaecat in
|
||||
elit. Labore ad id pariatur consequat consectetur ullamco culpa dolor
|
||||
dolor. Sunt irure eiusmod velit duis excepteur veniam consectetur eu
|
||||
occaecat reprehenderit qui anim dolore. Ea voluptate dolore proident
|
||||
esse aliqua amet magna pariatur incididunt ea excepteur. Aliquip magna
|
||||
ut ipsum veniam eu laborum id commodo.
|
||||
</Accordion>
|
||||
<h1>Open</h1>
|
||||
<Accordion heading="tittel" open={true} onClick={(e) => null}>
|
||||
Eu magna fugiat officia sit ullamco reprehenderit reprehenderit officia.
|
||||
Culpa fugiat irure deserunt irure enim adipisicing qui id. Pariatur
|
||||
commodo dolore consequat nulla cupidatat commodo nisi sunt. Ad proident
|
||||
occaecat cillum eu Lorem proident sunt anim officia voluptate. Veniam
|
||||
ullamco magna elit amet mollit exercitation magna quis ad occaecat in
|
||||
elit. Labore ad id pariatur consequat consectetur ullamco culpa dolor
|
||||
dolor. Sunt irure eiusmod velit duis excepteur veniam consectetur eu
|
||||
occaecat reprehenderit qui anim dolore. Ea voluptate dolore proident
|
||||
esse aliqua amet magna pariatur incididunt ea excepteur. Aliquip magna
|
||||
ut ipsum veniam eu laborum id commodo.
|
||||
</Accordion>
|
||||
<h1>Long heading</h1>
|
||||
<Accordion
|
||||
heading="Consequat incididunt aliquip aliquip fugiat anim cupidatat eu do ipsum pariatur."
|
||||
open={open}
|
||||
onClick={(e) => setOpen(!open)}
|
||||
>
|
||||
Eu magna fugiat officia sit ullamco reprehenderit reprehenderit officia.
|
||||
Culpa fugiat irure deserunt irure enim adipisicing qui id. Pariatur
|
||||
commodo dolore consequat nulla cupidatat commodo nisi sunt. Ad proident
|
||||
occaecat cillum eu Lorem proident sunt anim officia voluptate. Veniam
|
||||
ullamco magna elit amet mollit exercitation magna quis ad occaecat in
|
||||
elit. Labore ad id pariatur consequat consectetur ullamco culpa dolor
|
||||
dolor. Sunt irure eiusmod velit duis excepteur veniam consectetur eu
|
||||
occaecat reprehenderit qui anim dolore. Ea voluptate dolore proident
|
||||
esse aliqua amet magna pariatur incididunt ea excepteur. Aliquip magna
|
||||
ut ipsum veniam eu laborum id commodo.
|
||||
</Accordion>
|
||||
<div>
|
||||
<h1>Accordion</h1>
|
||||
<h2>Controlled</h2>
|
||||
<Accordion>
|
||||
<Accordion.Item open={open}>
|
||||
<Accordion.Header onClick={() => setOpen(!open)}>
|
||||
Accordion header text
|
||||
</Accordion.Header>
|
||||
<Accordion.Content>
|
||||
Magna aliquip aliquip fugiat nostrud nostrud velit pariatur veniam
|
||||
officia laboris voluptate officia pariatur.Lorem est ex anim velit
|
||||
occaecat nisi qui nostrud sit consectetur consectetur officia
|
||||
nostrud ullamco. Est ex duis proident nostrud elit qui laborum
|
||||
anim minim eu eiusmod. Veniam in nostrud sunt tempor velit
|
||||
incididunt sint ex dolor qui velit id eu. Deserunt magna sunt
|
||||
velit in. Est exercitation id cillum qui do. Minim adipisicing
|
||||
nostrud commodo proident occaecat aliquip nulla anim proident
|
||||
reprehenderit. Magna ipsum officia veniam cupidatat duis veniam
|
||||
dolore reprehenderit mollit velit.Ut consequat commodo minim
|
||||
occaecat id pariatur. Nisi enim tempor laborum commodo. Tempor sit
|
||||
quis nostrud eu cupidatat sunt commodo reprehenderit irure
|
||||
deserunt eiusmod ipsum. Exercitation quis commodo cillum eiusmod
|
||||
eiusmod. Do laborum qui proident commodo adipisicing eiusmod id.
|
||||
</Accordion.Content>
|
||||
</Accordion.Item>
|
||||
</Accordion>
|
||||
<h2>Un-controlled</h2>
|
||||
<Accordion>
|
||||
<Accordion.Item>
|
||||
<Accordion.Header>Accordion header text</Accordion.Header>
|
||||
<Accordion.Content>
|
||||
Magna aliquip aliquip fugiat nostrud nostrud velit pariatur veniam
|
||||
officia laboris voluptate officia pariatur.Lorem est ex anim velit
|
||||
occaecat nisi qui nostrud sit consectetur consectetur officia
|
||||
nostrud ullamco. Est ex duis proident nostrud elit qui laborum
|
||||
anim minim eu eiusmod. Veniam in nostrud sunt tempor velit
|
||||
incididunt sint ex dolor qui velit id eu. Deserunt magna sunt
|
||||
velit in. Est exercitation id cillum qui do. Minim adipisicing
|
||||
nostrud commodo proident occaecat aliquip nulla anim proident
|
||||
reprehenderit. Magna ipsum officia veniam cupidatat duis veniam
|
||||
dolore reprehenderit mollit velit.Ut consequat commodo minim
|
||||
occaecat id pariatur. Nisi enim tempor laborum commodo. Tempor sit
|
||||
quis nostrud eu cupidatat sunt commodo reprehenderit irure
|
||||
deserunt eiusmod ipsum. Exercitation quis commodo cillum eiusmod
|
||||
eiusmod. Do laborum qui proident commodo adipisicing eiusmod id.
|
||||
</Accordion.Content>
|
||||
</Accordion.Item>
|
||||
<Accordion.Item>
|
||||
<Accordion.Header>Accordion header text</Accordion.Header>
|
||||
<Accordion.Content>
|
||||
Magna aliquip aliquip fugiat nostrud nostrud velit pariatur veniam
|
||||
officia laboris voluptate officia pariatur.Lorem est ex anim velit
|
||||
occaecat nisi qui nostrud sit consectetur consectetur officia
|
||||
nostrud ullamco. Est ex duis proident nostrud elit qui laborum
|
||||
anim minim eu eiusmod. Veniam in nostrud sunt tempor velit
|
||||
incididunt sint ex dolor qui velit id eu. Deserunt magna sunt
|
||||
velit in. Est exercitation id cillum qui do. Minim adipisicing
|
||||
nostrud commodo proident occaecat aliquip nulla anim proident
|
||||
reprehenderit. Magna ipsum officia veniam cupidatat duis veniam
|
||||
dolore reprehenderit mollit velit.Ut consequat commodo minim
|
||||
occaecat id pariatur. Nisi enim tempor laborum commodo. Tempor sit
|
||||
quis nostrud eu cupidatat sunt commodo reprehenderit irure
|
||||
deserunt eiusmod ipsum. Exercitation quis commodo cillum eiusmod
|
||||
eiusmod. Do laborum qui proident commodo adipisicing eiusmod id.
|
||||
</Accordion.Content>
|
||||
</Accordion.Item>
|
||||
</Accordion>
|
||||
</div>
|
||||
</>
|
||||
);
|
||||
};
|
||||
@@ -1,4 +1,4 @@
|
||||
import React, { forwardRef } from "react";
|
||||
import React, { createContext, forwardRef } from "react";
|
||||
import cl from "classnames";
|
||||
import {
|
||||
ErrorFilled,
|
||||
@@ -6,80 +6,103 @@ import {
|
||||
InformationFilled,
|
||||
SuccessFilled,
|
||||
} from "@navikt/ds-icons";
|
||||
import AlertContent, { AlertContentType } from "./AlertContent";
|
||||
import AlertTitle, { AlertTitleType } from "./AlertTitle";
|
||||
import { BodyLong } from "..";
|
||||
|
||||
export interface AlertProps extends React.HTMLAttributes<HTMLDivElement> {
|
||||
/**
|
||||
* Alert content
|
||||
*/
|
||||
children: React.ReactNode;
|
||||
/**
|
||||
* Decides what design the alert will have
|
||||
*/
|
||||
variant: "error" | "warning" | "info" | "success";
|
||||
children: React.ReactNode;
|
||||
/**
|
||||
* Changes padding and font-sizes
|
||||
* @default "m"
|
||||
* @default "medium"
|
||||
*/
|
||||
size?: "m" | "s";
|
||||
size?: "medium" | "small";
|
||||
/**
|
||||
* Toggles full-width Alert
|
||||
* @default false
|
||||
*/
|
||||
fullWidth?: boolean;
|
||||
/**
|
||||
* Removes background from Alert
|
||||
*/
|
||||
inline?: boolean;
|
||||
}
|
||||
|
||||
const Icon = ({ variant }) => {
|
||||
const Icon = ({ variant, ...props }) => {
|
||||
switch (variant) {
|
||||
case "error":
|
||||
return (
|
||||
<ErrorFilled
|
||||
aria-label={`${variant}-ikon`}
|
||||
focusable="false"
|
||||
role="img"
|
||||
/>
|
||||
);
|
||||
return <ErrorFilled {...props} />;
|
||||
case "warning":
|
||||
return (
|
||||
<WarningFilled
|
||||
aria-label={`${variant}-ikon`}
|
||||
focusable="false"
|
||||
role="img"
|
||||
/>
|
||||
);
|
||||
return <WarningFilled {...props} />;
|
||||
case "info":
|
||||
return (
|
||||
<InformationFilled
|
||||
aria-label={`${variant}-ikon`}
|
||||
focusable="false"
|
||||
role="img"
|
||||
/>
|
||||
);
|
||||
return <InformationFilled {...props} />;
|
||||
case "success":
|
||||
return (
|
||||
<SuccessFilled
|
||||
aria-label={`${variant}-ikon`}
|
||||
focusable="false"
|
||||
role="img"
|
||||
/>
|
||||
);
|
||||
return <SuccessFilled {...props} />;
|
||||
default:
|
||||
return null;
|
||||
}
|
||||
};
|
||||
|
||||
export interface AlertContextProps {
|
||||
size: "medium" | "small";
|
||||
}
|
||||
|
||||
export const AlertContext = createContext<AlertContextProps | null>(null);
|
||||
interface AlertComponent
|
||||
extends React.ForwardRefExoticComponent<
|
||||
AlertProps & React.RefAttributes<HTMLDivElement>
|
||||
> {
|
||||
Title: AlertTitleType;
|
||||
Content: AlertContentType;
|
||||
}
|
||||
|
||||
const Alert = forwardRef<HTMLDivElement, AlertProps>(
|
||||
({ variant, children, className, size = "m", ...rest }, ref) => (
|
||||
(
|
||||
{
|
||||
children,
|
||||
className,
|
||||
variant,
|
||||
size = "medium",
|
||||
fullWidth = false,
|
||||
inline = false,
|
||||
...rest
|
||||
},
|
||||
ref
|
||||
) => (
|
||||
<div
|
||||
{...rest}
|
||||
ref={ref}
|
||||
className={cl(
|
||||
className,
|
||||
"navds-alert",
|
||||
`navds-alert--${variant}`,
|
||||
`navds-alert--${size}`,
|
||||
"navds-body-long",
|
||||
{ "navds-body--s": size === "s" }
|
||||
{ "navds-alert--full-width": fullWidth, "navds-alert--inline": inline }
|
||||
)}
|
||||
{...rest}
|
||||
>
|
||||
<span>
|
||||
<span className="sr-only">{`${variant}-ikon`}</span>
|
||||
<Icon variant={variant} />
|
||||
</span>
|
||||
<div>{children}</div>
|
||||
<Icon
|
||||
aria-label={`${variant}-ikon`}
|
||||
focusable="false"
|
||||
role="img"
|
||||
variant={variant}
|
||||
alt={`${variant}-ikon`}
|
||||
className="navds-alert__icon"
|
||||
/>
|
||||
<BodyLong as="div" size={size} className="navds-alert__wrapper">
|
||||
{children}
|
||||
</BodyLong>
|
||||
</div>
|
||||
)
|
||||
);
|
||||
) as AlertComponent;
|
||||
|
||||
Alert.Title = AlertTitle;
|
||||
Alert.Content = AlertContent;
|
||||
|
||||
export default Alert;
|
||||
@@ -0,0 +1,41 @@
|
||||
import React, { forwardRef, useContext } from "react";
|
||||
import cl from "classnames";
|
||||
import { BodyLong } from "..";
|
||||
import { AlertContext } from ".";
|
||||
|
||||
export interface AlertContentProps
|
||||
extends React.HTMLAttributes<HTMLDivElement> {
|
||||
/**
|
||||
* Alert content
|
||||
*/
|
||||
children: React.ReactNode;
|
||||
}
|
||||
|
||||
export type AlertContentType = React.ForwardRefExoticComponent<
|
||||
AlertContentProps & React.RefAttributes<HTMLDivElement>
|
||||
>;
|
||||
|
||||
const AlertContent: AlertContentType = forwardRef(
|
||||
({ children, className, ...rest }, ref) => {
|
||||
const context = useContext(AlertContext);
|
||||
|
||||
if (context === null) {
|
||||
console.warn("AlertContent has to be wrapped in <Alert />");
|
||||
return null;
|
||||
}
|
||||
|
||||
return (
|
||||
<BodyLong
|
||||
{...rest}
|
||||
as="div"
|
||||
className={cl(className, "navds-alert__content")}
|
||||
ref={ref}
|
||||
size={context.size ?? "medium"}
|
||||
>
|
||||
{children}
|
||||
</BodyLong>
|
||||
);
|
||||
}
|
||||
);
|
||||
|
||||
export default AlertContent;
|
||||
@@ -0,0 +1,41 @@
|
||||
import React, { forwardRef, useContext } from "react";
|
||||
import cl from "classnames";
|
||||
import { AlertContext, Heading } from "..";
|
||||
|
||||
export interface AlertTitleProps extends React.HTMLAttributes<HTMLDivElement> {
|
||||
/**
|
||||
* Alert content
|
||||
*/
|
||||
children: React.ReactNode;
|
||||
}
|
||||
|
||||
export type AlertTitleType = React.ForwardRefExoticComponent<
|
||||
AlertTitleProps & React.RefAttributes<HTMLDivElement>
|
||||
>;
|
||||
|
||||
const AlertTitle: AlertTitleType = forwardRef(
|
||||
({ children, className, ...rest }, ref) => {
|
||||
const context = useContext(AlertContext);
|
||||
|
||||
if (context === null) {
|
||||
console.warn("AlertTitle has to be wrapped in <Alert />");
|
||||
return null;
|
||||
}
|
||||
|
||||
const size = context.size === "medium" ? "small" : "xsmall";
|
||||
|
||||
return (
|
||||
<Heading
|
||||
{...rest}
|
||||
ref={ref}
|
||||
className={cl(className, "navds-alert__title")}
|
||||
as="div"
|
||||
size={size}
|
||||
>
|
||||
{children}
|
||||
</Heading>
|
||||
);
|
||||
}
|
||||
);
|
||||
|
||||
export default AlertTitle;
|
||||
@@ -1,5 +1,5 @@
|
||||
import { Meta, Canvas } from "@storybook/addon-docs";
|
||||
import { Alert } from "../../index";
|
||||
import { Alert, Heading, BodyLong } from "../../index";
|
||||
|
||||
<Meta title="ds-react/alert/intro" />
|
||||
|
||||
@@ -26,7 +26,7 @@ import { Alert } from "../../index";
|
||||
## Varianter
|
||||
|
||||
`variants`-prop kan brukes for å endre utseende mellom
|
||||
`info`, `success`, `warning` og `error`
|
||||
`info`, `success`, `warning` og `error`.
|
||||
|
||||
<Canvas>
|
||||
<Alert variant="info">Id elit esse enim reprehenderit.</Alert>
|
||||
@@ -37,19 +37,60 @@ import { Alert } from "../../index";
|
||||
|
||||
## Sizing
|
||||
|
||||
Alert har to størrelser: Default 64px min-height og small 32px min-height
|
||||
Alert har to størrelser: Default 64px height og small 32px height default.
|
||||
|
||||
<Canvas>
|
||||
<Alert size="s" variant="info">
|
||||
<Alert size="small" variant="info">
|
||||
Id elit esse enim reprehenderit.
|
||||
</Alert>
|
||||
<Alert size="s" variant="success">
|
||||
<Alert size="small" variant="success">
|
||||
Id elit esse enim reprehenderit.
|
||||
</Alert>
|
||||
<Alert size="s" variant="warning">
|
||||
<Alert size="small" variant="warning">
|
||||
Id elit esse enim reprehenderit.
|
||||
</Alert>
|
||||
<Alert size="s" variant="error">
|
||||
<Alert size="small" variant="error">
|
||||
Id elit esse enim reprehenderit.
|
||||
</Alert>
|
||||
</Canvas>
|
||||
|
||||
## fullWidth
|
||||
|
||||
<Canvas>
|
||||
<div style={{ margin: 32, display: "grid", gap: 16 }}>
|
||||
<Alert fullWidth variant="info">
|
||||
Id elit esse enim reprehenderit.
|
||||
</Alert>
|
||||
<Alert fullWidth size="small" variant="info">
|
||||
Id elit esse enim reprehenderit.
|
||||
</Alert>
|
||||
</div>
|
||||
</Canvas>
|
||||
|
||||
## Med heading
|
||||
|
||||
```jsx
|
||||
<Alert variant="info">
|
||||
<Heading spacing size="small" level="2">
|
||||
Aliquip duis est in commodo pariatur
|
||||
</Heading>
|
||||
<BodyLong>
|
||||
Ullamco ullamco laborum et commodo sint culpa cupidatat culpa qui laboris
|
||||
ex. Labore ex occaecat proident qui qui fugiat magna. Fugiat sint commodo
|
||||
consequat eu aute.
|
||||
</BodyLong>
|
||||
</Alert>
|
||||
```
|
||||
|
||||
<Canvas>
|
||||
<Alert variant="info">
|
||||
<Heading spacing size="small" level="3">
|
||||
Aliquip duis est in commodo pariatur
|
||||
</Heading>
|
||||
<BodyLong>
|
||||
Ullamco ullamco laborum et commodo sint culpa cupidatat culpa qui laboris
|
||||
ex. Labore ex occaecat proident qui qui fugiat magna. Fugiat sint commodo
|
||||
consequat eu aute.
|
||||
</BodyLong>
|
||||
</Alert>
|
||||
</Canvas>
|
||||
@@ -1,5 +1,6 @@
|
||||
import React from "react";
|
||||
import { Alert } from "../index";
|
||||
import { Alert } from "..";
|
||||
import { BodyLong, Heading } from "../..";
|
||||
|
||||
export default {
|
||||
title: "ds-react/alert",
|
||||
@@ -17,21 +18,104 @@ export const All = () => {
|
||||
return (
|
||||
<>
|
||||
<h1>Alert</h1>
|
||||
{variants.map((variant) => (
|
||||
{variants.map((variant, i) => (
|
||||
<Alert key={variant} variant={variant}>
|
||||
Id elit esse enim reprehenderit.Tempor tempor ex exercitation id aute
|
||||
eu.Laborum nulla nisi irure voluptate mollit fugiat.Est quis culpa
|
||||
nostrud et reprehenderit ea sint.Eu veniam labore enim labore qui
|
||||
eiusmod Lorem amet ad esse.
|
||||
{new Array(i + 1).fill(
|
||||
"Id elit esse enim reprehenderit enim nisi veniam nostrud."
|
||||
)}
|
||||
</Alert>
|
||||
))}
|
||||
<h2>Small</h2>
|
||||
<div>
|
||||
{variants.map((variant) => (
|
||||
<Alert key={variant} variant={variant} size="s">
|
||||
Exercitation enim nisi veniam nostrud Lorem ipsum ea fugiat. Aute
|
||||
exercitation voluptate proident sit ex reprehenderit quis ex ut
|
||||
mollit.
|
||||
{variants.map((variant, i) => (
|
||||
<Alert key={variant} variant={variant} size="small">
|
||||
{new Array(i + 1).fill(
|
||||
"Id elit esse enim reprehenderit enim nisi veniam nostrud."
|
||||
)}
|
||||
</Alert>
|
||||
))}
|
||||
</div>
|
||||
<h2>Alert fullWidth</h2>
|
||||
{variants.map((variant, i) => (
|
||||
<Alert fullWidth key={variant} variant={variant}>
|
||||
{new Array(i + 1).fill(
|
||||
"Id elit esse enim reprehenderit enim nisi veniam nostrud."
|
||||
)}
|
||||
</Alert>
|
||||
))}
|
||||
<h2>Small</h2>
|
||||
<div>
|
||||
{variants.map((variant, i) => (
|
||||
<Alert fullWidth key={variant} variant={variant} size="small">
|
||||
{new Array(i + 1).fill(
|
||||
"Id elit esse enim reprehenderit enim nisi veniam nostrud."
|
||||
)}
|
||||
</Alert>
|
||||
))}
|
||||
</div>
|
||||
<h2>Inline</h2>
|
||||
<div>
|
||||
{variants.map((variant, i) => (
|
||||
<Alert inline key={variant} variant={variant}>
|
||||
{new Array(i + 1).fill(
|
||||
"Id elit esse enim reprehenderit enim nisi veniam nostrud."
|
||||
)}
|
||||
</Alert>
|
||||
))}
|
||||
</div>
|
||||
<h2>Inline small</h2>
|
||||
<div>
|
||||
{variants.map((variant, i) => (
|
||||
<Alert inline key={variant} variant={variant} size="small">
|
||||
{new Array(i + 1).fill(
|
||||
"Id elit esse enim reprehenderit enim nisi veniam nostrud."
|
||||
)}
|
||||
</Alert>
|
||||
))}
|
||||
</div>
|
||||
<h2>Med Heading</h2>
|
||||
<div>
|
||||
{variants.map((variant, i) => (
|
||||
<Alert key={variant} variant={variant}>
|
||||
<Heading spacing size="small" level="3">
|
||||
Aliquip duis est in commodo pariatur
|
||||
</Heading>
|
||||
<BodyLong spacing>
|
||||
Ullamco ullamco laborum et commodo sint culpa cupidatat culpa qui
|
||||
laboris ex. Labore ex occaecat proident qui qui fugiat magna.
|
||||
Fugiat sint commodo consequat eu aute.
|
||||
</BodyLong>
|
||||
<Heading level="4" size="xsmall" spacing>
|
||||
Ullamco eiusmod Lorem eiusmod eu.
|
||||
</Heading>
|
||||
<BodyLong>
|
||||
Ullamco ullamco laborum et commodo sint culpa cupidatat culpa qui
|
||||
laboris ex. Labore ex occaecat proident qui qui fugiat magna.
|
||||
Fugiat sint commodo consequat eu aute.
|
||||
</BodyLong>
|
||||
</Alert>
|
||||
))}
|
||||
</div>
|
||||
<h2>Med Heading small</h2>
|
||||
<div>
|
||||
{variants.map((variant, i) => (
|
||||
<Alert key={variant} variant={variant} size="small">
|
||||
<Heading spacing size="small" level="3">
|
||||
Aliquip duis est in commodo pariatur
|
||||
</Heading>
|
||||
<BodyLong spacing>
|
||||
Ullamco ullamco laborum et commodo sint culpa cupidatat culpa qui
|
||||
laboris ex. Labore ex occaecat proident qui qui fugiat magna.
|
||||
Fugiat sint commodo consequat eu aute.
|
||||
</BodyLong>
|
||||
<Heading level="4" size="xsmall" spacing>
|
||||
Ullamco eiusmod Lorem eiusmod eu.
|
||||
</Heading>
|
||||
<BodyLong>
|
||||
Ullamco ullamco laborum et commodo sint culpa cupidatat culpa qui
|
||||
laboris ex. Labore ex occaecat proident qui qui fugiat magna.
|
||||
Fugiat sint commodo consequat eu aute.
|
||||
</BodyLong>
|
||||
</Alert>
|
||||
))}
|
||||
</div>
|
||||
|
||||
@@ -1,5 +1,6 @@
|
||||
import React, { forwardRef } from "react";
|
||||
import cl from "classnames";
|
||||
import { BodyShort, OverridableComponent } from "../";
|
||||
|
||||
export interface ButtonProps
|
||||
extends React.ButtonHTMLAttributes<HTMLButtonElement> {
|
||||
@@ -11,12 +12,12 @@ export interface ButtonProps
|
||||
* Changes design and interactions
|
||||
* @default "primary"
|
||||
*/
|
||||
variant?: "primary" | "secondary" | "action" | "danger";
|
||||
variant?: "primary" | "secondary" | "tertiary" | "danger";
|
||||
/**
|
||||
* Changes padding, height and font-size
|
||||
* @default "m"
|
||||
* @default "medium"
|
||||
*/
|
||||
size?: "m" | "s";
|
||||
size?: "medium" | "small";
|
||||
/**
|
||||
* Prevent the user from interacting with the button: it cannot be pressed or focused.
|
||||
* @note Avoid using if possible for accessibility purposes
|
||||
@@ -25,20 +26,32 @@ export interface ButtonProps
|
||||
disabled?: boolean;
|
||||
}
|
||||
|
||||
const Button = forwardRef<HTMLButtonElement, ButtonProps>(
|
||||
({ variant = "primary", className, size = "m", ...rest }, ref) => (
|
||||
<button
|
||||
const Button: OverridableComponent<ButtonProps, HTMLButtonElement> = forwardRef(
|
||||
(
|
||||
{
|
||||
as: Component = "button",
|
||||
variant = "primary",
|
||||
className,
|
||||
children,
|
||||
size = "medium",
|
||||
...rest
|
||||
},
|
||||
ref
|
||||
) => (
|
||||
<Component
|
||||
{...rest}
|
||||
ref={ref}
|
||||
className={cl(
|
||||
className,
|
||||
"navds-button",
|
||||
`navds-button--${variant}`,
|
||||
`navds-button--${size}`,
|
||||
"navds-body-short",
|
||||
{ "navds-body--s": size === "s" }
|
||||
`navds-button--${size}`
|
||||
)}
|
||||
{...rest}
|
||||
/>
|
||||
>
|
||||
<BodyShort as="span" className="navds-button__inner" size={size}>
|
||||
{children}
|
||||
</BodyShort>
|
||||
</Component>
|
||||
)
|
||||
);
|
||||
|
||||
|
||||
@@ -1,29 +1,29 @@
|
||||
import { Meta, Canvas } from "@storybook/addon-docs";
|
||||
import { Button, Loader } from "../../index";
|
||||
import { Success } from "@navikt/ds-react";
|
||||
import { Success } from "@navikt/ds-icons";
|
||||
|
||||
<Meta title="ds-react/button/intro" />
|
||||
|
||||
# Hvordan ta i bruk Button
|
||||
|
||||
```jsx
|
||||
<Button>Buttontekst</Button>
|
||||
<Button>Button</Button>
|
||||
```
|
||||
|
||||
<Canvas>
|
||||
<Button>Buttontekst</Button>
|
||||
<Button>Button</Button>
|
||||
</Canvas>
|
||||
|
||||
## Varianter
|
||||
|
||||
`variants`-prop kan brukes for å endre utseende mellom
|
||||
`primary`, `secondary`, `action` og `danger`
|
||||
`primary`, `secondary`, `tertiary` og `danger`
|
||||
|
||||
<Canvas>
|
||||
<Button variant="primary">Buttontekst</Button>
|
||||
<Button variant="secondary">Buttontekst</Button>
|
||||
<Button variant="action">Buttontekst</Button>
|
||||
<Button variant="danger">Buttontekst</Button>
|
||||
<Button variant="primary">Primary</Button>
|
||||
<Button variant="secondary">Secondary</Button>
|
||||
<Button variant="tertiary">Tertiary</Button>
|
||||
<Button variant="danger">Danger</Button>
|
||||
</Canvas>
|
||||
|
||||
## Sizing
|
||||
@@ -31,35 +31,40 @@ import { Success } from "@navikt/ds-react";
|
||||
Button har to størrelser: Default 48px min-height og small 32px min-height
|
||||
|
||||
<Canvas>
|
||||
<Button size="s" variant="primary">
|
||||
Buttontekst
|
||||
<Button size="small" variant="primary">
|
||||
Primary
|
||||
</Button>
|
||||
<Button size="s" variant="secondary">
|
||||
Buttontekst
|
||||
<Button size="small" variant="secondary">
|
||||
Secondary
|
||||
</Button>
|
||||
<Button size="s" variant="action">
|
||||
Buttontekst
|
||||
<Button size="small" variant="tertiary">
|
||||
Tertiary
|
||||
</Button>
|
||||
<Button size="s" variant="danger">
|
||||
Buttontekst
|
||||
<Button size="small" variant="danger">
|
||||
Danger
|
||||
</Button>
|
||||
</Canvas>
|
||||
|
||||
## Med ikon eller `<Loader />`
|
||||
|
||||
Hvis man setter ikoner (svg) eller `<Loader />` rett på button vil størrelsen
|
||||
bli justert automatisk. For å få riktige marginer rundt ikonet må man da wrappe innholdet
|
||||
i et element
|
||||
bli justert automatisk og sentrert.
|
||||
|
||||
<Canvas>
|
||||
<Button>
|
||||
<span>Buttontekst</span> <Loader />
|
||||
<Loader /> Laster... <Loader />
|
||||
</Button>
|
||||
<Button size="s">
|
||||
<span>Buttontekst</span>
|
||||
<Button size="small">
|
||||
<Loader />
|
||||
Laster...
|
||||
<Loader />
|
||||
</Button>
|
||||
<Button>
|
||||
<Loader /> <span>Buttontekst</span>
|
||||
<Success /> Laster... <Success />
|
||||
</Button>
|
||||
<Button size="small">
|
||||
<Success />
|
||||
Laster...
|
||||
<Success />
|
||||
</Button>
|
||||
</Canvas>
|
||||
@@ -10,33 +10,40 @@ export default {
|
||||
const Section = ({ children }) => (
|
||||
<div
|
||||
style={{
|
||||
display: "grid",
|
||||
display: "flex",
|
||||
gap: 16,
|
||||
gridAutoFlow: "column",
|
||||
justifyContent: "start",
|
||||
padding: 24,
|
||||
background: "lightgray",
|
||||
paddingLeft: 0,
|
||||
}}
|
||||
>
|
||||
{children}
|
||||
</div>
|
||||
);
|
||||
|
||||
const variants: Array<"primary" | "secondary" | "action" | "danger"> = [
|
||||
const variants: Array<"primary" | "secondary" | "tertiary" | "danger"> = [
|
||||
"primary",
|
||||
"secondary",
|
||||
"action",
|
||||
"tertiary",
|
||||
"danger",
|
||||
];
|
||||
|
||||
const varSwitch = {
|
||||
primary: "Primary",
|
||||
secondary: "Secondary",
|
||||
tertiary: "Tertiary",
|
||||
danger: "Danger",
|
||||
};
|
||||
|
||||
export const All = () => {
|
||||
return (
|
||||
<>
|
||||
<div style={{ paddingLeft: "1rem" }}>
|
||||
<h1>Button</h1>
|
||||
<Section>
|
||||
{variants.map((variant) => (
|
||||
<Button key={variant} variant={variant}>
|
||||
{variant}
|
||||
{varSwitch[variant]}
|
||||
</Button>
|
||||
))}
|
||||
</Section>
|
||||
@@ -44,27 +51,23 @@ export const All = () => {
|
||||
<Section>
|
||||
{variants.map((variant) => (
|
||||
<Button key={variant} variant={variant} disabled>
|
||||
{variant}
|
||||
{varSwitch[variant]}
|
||||
</Button>
|
||||
))}
|
||||
</Section>
|
||||
<h2>As link</h2>
|
||||
<Section>
|
||||
{variants.map((variant) => (
|
||||
<a
|
||||
key={variant}
|
||||
className={`navds-button navds-button--${variant} navds-body-short`}
|
||||
href="the-link"
|
||||
>
|
||||
{variant}
|
||||
</a>
|
||||
<Button as="a" key={variant} variant={variant} href="the-link">
|
||||
{varSwitch[variant]}
|
||||
</Button>
|
||||
))}
|
||||
</Section>
|
||||
<h2>Small</h2>
|
||||
<Section>
|
||||
{variants.map((variant) => (
|
||||
<Button key={variant} variant={variant} size="s">
|
||||
{variant}
|
||||
<Button key={variant} variant={variant} size="small">
|
||||
{varSwitch[variant]}
|
||||
</Button>
|
||||
))}
|
||||
</Section>
|
||||
@@ -72,26 +75,34 @@ export const All = () => {
|
||||
<Section>
|
||||
{variants.map((variant) => (
|
||||
<Button key={variant} variant={variant}>
|
||||
<span>{variant}</span> <Success />
|
||||
{variant} <Success />
|
||||
</Button>
|
||||
))}
|
||||
</Section>
|
||||
<Section>
|
||||
{variants.map((variant) => (
|
||||
<Button key={variant} variant={variant}>
|
||||
<span className="sr-only">Success ikon</span>
|
||||
<Success />
|
||||
</Button>
|
||||
))}
|
||||
</Section>
|
||||
<h2>Small w/icon</h2>
|
||||
<Section>
|
||||
{variants.map((variant) => (
|
||||
<Button key={variant} variant={variant} size="s">
|
||||
<Success /> <span>{variant}</span>
|
||||
<Button key={variant} variant={variant} size="small">
|
||||
<Success /> {variant}
|
||||
</Button>
|
||||
))}
|
||||
</Section>
|
||||
<Section>
|
||||
{variants.map((variant) => (
|
||||
<Button key={variant} variant={variant} size="s">
|
||||
<Button key={variant} variant={variant} size="small">
|
||||
<span className="sr-only">Success ikon</span>
|
||||
<Success />
|
||||
</Button>
|
||||
))}
|
||||
</Section>
|
||||
</>
|
||||
</div>
|
||||
);
|
||||
};
|
||||
@@ -1,30 +1,32 @@
|
||||
import React, { forwardRef } from "react";
|
||||
import cl from "classnames";
|
||||
import { OverridableComponent } from "../util";
|
||||
import { OverridableComponent } from "..";
|
||||
|
||||
export interface MicroCardProps {
|
||||
props: {
|
||||
children: string;
|
||||
} & React.HTMLAttributes<HTMLAnchorElement>;
|
||||
defaultComponent: "a";
|
||||
export interface MicroCardProps
|
||||
extends React.AnchorHTMLAttributes<HTMLAnchorElement> {
|
||||
/**
|
||||
* Link text
|
||||
*/
|
||||
children: React.ReactNode;
|
||||
}
|
||||
|
||||
export const MicroCard: OverridableComponent<MicroCardProps> = forwardRef(
|
||||
({ className, component: Component = "a", children, ...rest }, ref) => (
|
||||
<Component
|
||||
ref={ref}
|
||||
className={cl(
|
||||
"navds-card__micro",
|
||||
"navds-detail",
|
||||
"navds-detail--s",
|
||||
className
|
||||
)}
|
||||
title={children}
|
||||
{...rest}
|
||||
>
|
||||
{children}
|
||||
</Component>
|
||||
)
|
||||
);
|
||||
export const MicroCard: OverridableComponent<
|
||||
MicroCardProps,
|
||||
HTMLAnchorElement
|
||||
> = forwardRef(({ className, as: Component = "a", children, ...rest }, ref) => (
|
||||
<Component
|
||||
ref={ref}
|
||||
className={cl(
|
||||
"navds-card__micro",
|
||||
"navds-detail",
|
||||
"navds-detail--small",
|
||||
className
|
||||
)}
|
||||
title={children}
|
||||
{...rest}
|
||||
>
|
||||
{children}
|
||||
</Component>
|
||||
));
|
||||
|
||||
export default MicroCard;
|
||||
@@ -1,2 +0,0 @@
|
||||
export { default as ContentContainer } from "./ContentContainer";
|
||||
export * from "./ContentContainer";
|
||||
@@ -1,31 +0,0 @@
|
||||
import { Meta, Canvas } from "@storybook/addon-docs";
|
||||
|
||||
<Meta title="ds-react/content-container/intro" />
|
||||
|
||||
# Hvordan ta i bruk ContentContainer
|
||||
|
||||
```jsx
|
||||
<ContentContainer>
|
||||
<div>innhold...</div>
|
||||
</ContentContainer>
|
||||
```
|
||||
|
||||
## Bruk
|
||||
|
||||
Komponenten fungerer som en wrapper rundt innholdet ditt på siden for å
|
||||
justere padding og max-width. Dette er all stylingen som blir applied
|
||||
|
||||
```css
|
||||
.navds-content-container {
|
||||
margin-left: auto;
|
||||
margin-right: auto;
|
||||
max-width: var(--navds-content-container-max-width);
|
||||
padding: var(--navds-content-container-padding-small);
|
||||
}
|
||||
|
||||
@media (min-width: 448px) {
|
||||
.navds-content-container {
|
||||
padding: var(--navds-content-container-padding-medium-and-larger);
|
||||
}
|
||||
}
|
||||
```
|
||||
@@ -1,33 +0,0 @@
|
||||
import * as React from "react";
|
||||
import { ContentContainer } from "../index";
|
||||
import { BodyLong } from "../../index";
|
||||
import "./style.css";
|
||||
|
||||
export default {
|
||||
title: "ds-react/content-container",
|
||||
component: ContentContainer,
|
||||
parameters: {
|
||||
layout: "fullscreen",
|
||||
backgrounds: {
|
||||
default: "NAV gray",
|
||||
values: [
|
||||
{
|
||||
name: "NAV gray",
|
||||
value: "#f1f1f1",
|
||||
},
|
||||
{
|
||||
name: "white",
|
||||
value: "#ffffff",
|
||||
},
|
||||
],
|
||||
},
|
||||
},
|
||||
};
|
||||
|
||||
export const All = () => {
|
||||
return (
|
||||
<ContentContainer className={"navds-story-content-container"}>
|
||||
<BodyLong size="m">-- Innhold --</BodyLong>
|
||||
</ContentContainer>
|
||||
);
|
||||
};
|
||||
@@ -1,15 +0,0 @@
|
||||
.navds-story-content-container {
|
||||
display: flex;
|
||||
border-radius: 0.25rem;
|
||||
justify-content: center;
|
||||
align-items: center;
|
||||
margin-bottom: 1.5rem;
|
||||
min-height: 10rem;
|
||||
background: repeating-linear-gradient(
|
||||
45deg,
|
||||
#d6d6d6,
|
||||
#d6d6d6 10px,
|
||||
transparent 10px,
|
||||
transparent 20px
|
||||
);
|
||||
}
|
||||
@@ -1,18 +1,12 @@
|
||||
import { Copy } from "@navikt/ds-icons";
|
||||
import copy from "copy-to-clipboard";
|
||||
import { Placement } from "@popperjs/core";
|
||||
import cl from "classnames";
|
||||
import React, {
|
||||
forwardRef,
|
||||
HTMLAttributes,
|
||||
useEffect,
|
||||
useRef,
|
||||
useState,
|
||||
} from "react";
|
||||
import copy from "copy-to-clipboard";
|
||||
import React, { forwardRef, useEffect, useRef, useState } from "react";
|
||||
import mergeRefs from "react-merge-refs";
|
||||
import { Popover, Button } from "..";
|
||||
import { BodyShort, Button, ButtonProps, Popover } from "..";
|
||||
|
||||
export interface CopyToClipboardProps
|
||||
extends HTMLAttributes<HTMLButtonElement> {
|
||||
export interface CopyToClipboardProps extends Omit<ButtonProps, "children"> {
|
||||
/**
|
||||
* Button text
|
||||
*/
|
||||
@@ -20,20 +14,31 @@ export interface CopyToClipboardProps
|
||||
/**
|
||||
* Text to be copied to clipboard
|
||||
*/
|
||||
text: string;
|
||||
copyText: string;
|
||||
/**
|
||||
* Description of text, examples: "personnummer", "navn", "epost" etc.
|
||||
*/
|
||||
label: string;
|
||||
popoverText: string;
|
||||
/**
|
||||
* Use a differnet icon to display
|
||||
* @default "Files" from @navikt/ds-icons
|
||||
* Allows extending popover properties like "placement"
|
||||
* @default "right"
|
||||
*/
|
||||
icon?: React.ReactElement;
|
||||
popoverPlacement?: Placement;
|
||||
}
|
||||
|
||||
const CopyToClipboard = forwardRef<HTMLButtonElement, CopyToClipboardProps>(
|
||||
({ children, text, label, icon, className, ...rest }, ref) => {
|
||||
(
|
||||
{
|
||||
children,
|
||||
copyText,
|
||||
popoverText,
|
||||
className,
|
||||
size = "medium",
|
||||
popoverPlacement = "right",
|
||||
...rest
|
||||
},
|
||||
ref
|
||||
) => {
|
||||
const buttonRef = useRef<HTMLButtonElement>(null);
|
||||
const mergedRef = mergeRefs([buttonRef, ref]);
|
||||
const timeoutRef = useRef<number | null>();
|
||||
@@ -48,10 +53,10 @@ const CopyToClipboard = forwardRef<HTMLButtonElement, CopyToClipboardProps>(
|
||||
};
|
||||
}, [openPopover]);
|
||||
|
||||
const title = `Kopier ${label} (${text})`;
|
||||
const title = `Kopier ${copyText}`;
|
||||
|
||||
const handleClick = () => {
|
||||
copy(text);
|
||||
copy(copyText);
|
||||
setOpenPopover(true);
|
||||
};
|
||||
|
||||
@@ -63,17 +68,14 @@ const CopyToClipboard = forwardRef<HTMLButtonElement, CopyToClipboardProps>(
|
||||
title={title}
|
||||
className={cl("navds-copy-to-clipboard", className)}
|
||||
onClick={handleClick}
|
||||
size={size}
|
||||
{...rest}
|
||||
>
|
||||
{icon ? (
|
||||
<>{icon}</>
|
||||
) : (
|
||||
<Copy
|
||||
focusable="false"
|
||||
role="img"
|
||||
aria-label="Fil ikon for kopiering"
|
||||
/>
|
||||
)}
|
||||
<Copy
|
||||
focusable="false"
|
||||
role="img"
|
||||
aria-label="Fil ikon for kopiering"
|
||||
/>
|
||||
{children ? children : <span className="sr-only">{title}</span>}
|
||||
</Button>
|
||||
<Popover
|
||||
@@ -81,11 +83,13 @@ const CopyToClipboard = forwardRef<HTMLButtonElement, CopyToClipboardProps>(
|
||||
anchorEl={buttonRef.current}
|
||||
open={openPopover}
|
||||
onClose={() => setOpenPopover(false)}
|
||||
placement="right"
|
||||
placement={popoverPlacement}
|
||||
arrow={false}
|
||||
className="navds-copy-to-clipboard__popover"
|
||||
>
|
||||
{label}
|
||||
<BodyShort size={size} as="span">
|
||||
{popoverText}
|
||||
</BodyShort>
|
||||
</Popover>
|
||||
</div>
|
||||
);
|
||||
|
||||
@@ -1,7 +1,6 @@
|
||||
import * as React from "react";
|
||||
|
||||
import { CopyToClipboard } from "../index";
|
||||
import { Link } from "@navikt/ds-icons";
|
||||
|
||||
export default {
|
||||
title: "@ds-react/copy-to-clipboard",
|
||||
@@ -15,24 +14,24 @@ export const All = () => {
|
||||
return (
|
||||
<div>
|
||||
<h2>Fritstående knapp</h2>
|
||||
<CopyToClipboard label={label} text={text} />
|
||||
<CopyToClipboard popoverText={label} copyText={text} />
|
||||
|
||||
<h2>Sammen med tekst</h2>
|
||||
<CopyToClipboard label={label} text={text}>
|
||||
<CopyToClipboard popoverText={label} copyText={text}>
|
||||
Kopier tekst
|
||||
</CopyToClipboard>
|
||||
|
||||
<h2>Tilpasser seg fontstørrelse</h2>
|
||||
<CopyToClipboard label={label} text={text} style={{ fontSize: "0.8rem" }}>
|
||||
<h2>Small size</h2>
|
||||
<CopyToClipboard popoverText={label} copyText={text} size="small">
|
||||
Kopier tekst
|
||||
</CopyToClipboard>
|
||||
<CopyToClipboard popoverText={label} copyText={text} size="small" />
|
||||
|
||||
<h2>Custom icon</h2>
|
||||
<h2>Endrer placement av popover</h2>
|
||||
<CopyToClipboard
|
||||
icon={<Link />}
|
||||
label={label}
|
||||
text={text}
|
||||
style={{ fontSize: "0.8rem" }}
|
||||
popoverText={label}
|
||||
copyText={text}
|
||||
popoverPlacement="bottom-end"
|
||||
>
|
||||
Kopier tekst
|
||||
</CopyToClipboard>
|
||||
|
||||
@@ -6,30 +6,40 @@ import { Success } from "@navikt/ds-react";
|
||||
|
||||
# Hvordan ta i bruk CopyToClipboard
|
||||
|
||||
Innholdet i `text` vil da bli kopiert til clipboard, mens innholdet i `label`
|
||||
brukes i popovertekst og `sr-only` span som rendres hvis knappen ikke har noe tekstinnhold
|
||||
`sr-only` tekst blir da `Kopier ${label} (${text})`
|
||||
Innholdet i `copyText` vil bli kopiert til clipboard, mens innholdet i `popoverText`
|
||||
brukes i popover. Hvis komponenten ikke har noen children (tekst i button) vil da en "sr-only" tekst blie
|
||||
lagt på knappen med tekst "Kopier copyText"
|
||||
|
||||
```jsx
|
||||
<CopyToClipboard label={"Kopierte PI til clipboard"} text={"3.14"}>
|
||||
Kopier Pi{" "}
|
||||
<CopyToClipboard popoverText={"Kopierte adresse"} copyText={"0660 OSLO"}>
|
||||
Kopier adresse
|
||||
</CopyToClipboard>
|
||||
```
|
||||
|
||||
<Canvas>
|
||||
<CopyToClipboard label={"Kopierte PI til clipboard"} text={"3.14"}>
|
||||
Kopier Pi{" "}
|
||||
<CopyToClipboard popoverText={"Kopiert adresse"} copyText={"0660 OSLO"}>
|
||||
Kopier adresse
|
||||
</CopyToClipboard>
|
||||
</Canvas>
|
||||
|
||||
## Custom ikon
|
||||
|
||||
Man kan sette andre ikoner en `Copy` ved `icon`-proppen
|
||||
## Sizing
|
||||
|
||||
```jsx
|
||||
<CopyToClipboard
|
||||
icon={<Link />}
|
||||
label={"Kopierte PI til clipboard"}
|
||||
text={"3.14"}
|
||||
/>
|
||||
popoverText={"Kopierte adressen"}
|
||||
copyText={"0660 OSLO"}
|
||||
size="small"
|
||||
>
|
||||
Kopier adresse
|
||||
</CopyToClipboard>
|
||||
```
|
||||
|
||||
<Canvas>
|
||||
<CopyToClipboard
|
||||
popoverText={"Kopierte adressen"}
|
||||
copyText={"0660 OSLO"}
|
||||
size="small"
|
||||
>
|
||||
Kopier adresse
|
||||
</CopyToClipboard>
|
||||
</Canvas>
|
||||
@@ -23,7 +23,7 @@ const ConfirmationPanel = forwardRef<HTMLDivElement, ConfirmationPanelProps>(
|
||||
<div
|
||||
ref={ref}
|
||||
className={cl("navds-confirmation-panel", className, {
|
||||
"navds-confirmation-panel--s": props.size === "s",
|
||||
"navds-confirmation-panel--s": props.size === "small",
|
||||
"navds-confirmation-panel--error": !!props.error,
|
||||
"navds-confirmation-panel--checked": !!props.checked,
|
||||
})}
|
||||
|
||||
@@ -5,11 +5,11 @@ import { Label } from "..";
|
||||
const ErrorMessage = (props) => (
|
||||
<Label
|
||||
{...props}
|
||||
component="div"
|
||||
as="div"
|
||||
className={cl(
|
||||
"navds-error-message",
|
||||
props.className,
|
||||
`navds-error-message--${props.size ?? "m"}`
|
||||
`navds-error-message--${props.size ?? "medium"}`
|
||||
)}
|
||||
/>
|
||||
);
|
||||
|
||||
@@ -17,7 +17,7 @@ export type FieldsetContextProps = {
|
||||
/**
|
||||
* Changes paddings, margins and font-sizes
|
||||
*/
|
||||
size: "m" | "s";
|
||||
size: "medium" | "small";
|
||||
disabled: boolean;
|
||||
};
|
||||
|
||||
@@ -94,7 +94,7 @@ const Fieldset = forwardRef<HTMLFieldSetElement, FieldsetProps>(
|
||||
>
|
||||
<Label
|
||||
size={size}
|
||||
component="legend"
|
||||
as="legend"
|
||||
className={cl("navds-fieldset__legend", {
|
||||
"sr-only": !!hideLegend,
|
||||
})}
|
||||
|
||||
@@ -58,7 +58,7 @@ const Select = forwardRef<HTMLSelectElement, SelectProps>((props, ref) => {
|
||||
<Label
|
||||
htmlFor={inputProps.id}
|
||||
size={size}
|
||||
component="label"
|
||||
as="label"
|
||||
className={cl("navds-select__label", {
|
||||
"sr-only": hideLabel,
|
||||
})}
|
||||
@@ -85,7 +85,7 @@ const Select = forwardRef<HTMLSelectElement, SelectProps>((props, ref) => {
|
||||
className,
|
||||
"navds-select__input",
|
||||
"navds-body-short",
|
||||
`navds-body--${size ?? "m"}`
|
||||
`navds-body--${size ?? "medium"}`
|
||||
)}
|
||||
size={props.htmlSize}
|
||||
>
|
||||
|
||||
@@ -52,7 +52,7 @@ const TextField = forwardRef<HTMLInputElement, TextFieldProps>((props, ref) => {
|
||||
<Label
|
||||
htmlFor={inputProps.id}
|
||||
size={size}
|
||||
component="label"
|
||||
as="label"
|
||||
className={cl("navds-text-field__label", { "sr-only": hideLabel })}
|
||||
>
|
||||
{label}
|
||||
|
||||
@@ -72,7 +72,7 @@ const Textarea = forwardRef<HTMLTextAreaElement, TextareaProps>(
|
||||
<Label
|
||||
htmlFor={inputProps.id}
|
||||
size={size}
|
||||
component="label"
|
||||
as="label"
|
||||
className={cl("navds-textarea__label", {
|
||||
"sr-only": hideLabel,
|
||||
})}
|
||||
@@ -99,7 +99,7 @@ const Textarea = forwardRef<HTMLTextAreaElement, TextareaProps>(
|
||||
className,
|
||||
"navds-textarea__input",
|
||||
"navds-body-short",
|
||||
`navds-body-${size ?? "m"}`,
|
||||
`navds-body-${size ?? "medium"}`,
|
||||
{
|
||||
"navds-textarea--counter": hasMaxLength,
|
||||
}
|
||||
@@ -140,7 +140,7 @@ export const Counter = ({ maxLength, currentLength, size }) => {
|
||||
className={cl("navds-textarea__counter", {
|
||||
"navds-textarea__counter--error": difference < 0,
|
||||
})}
|
||||
aria-live="polite"
|
||||
aria-live={difference < 20 ? "polite" : "off"}
|
||||
size={size}
|
||||
>
|
||||
{difference < 0
|
||||
|
||||
@@ -59,7 +59,7 @@ const Checkbox = forwardRef<HTMLInputElement, CheckboxProps>((props, ref) => {
|
||||
ref={ref}
|
||||
/>
|
||||
<BodyShort
|
||||
component="label"
|
||||
as="label"
|
||||
htmlFor={inputProps.id}
|
||||
size={size}
|
||||
className="navds-checkbox__label"
|
||||
|
||||
@@ -54,7 +54,7 @@ const CheckboxGroup = forwardRef<HTMLFieldSetElement, CheckboxGroupProps>(
|
||||
className={cl(
|
||||
className,
|
||||
"navds-checkbox-group",
|
||||
`navds-checkbox-group--${rest.size ?? fieldset?.size ?? "m"}`
|
||||
`navds-checkbox-group--${rest.size ?? fieldset?.size ?? "medium"}`
|
||||
)}
|
||||
>
|
||||
<CheckboxGroupContext.Provider
|
||||
|
||||
@@ -95,10 +95,14 @@ Man kan både sette en description på CheckboxGroup og selve checkbox
|
||||
|
||||
## Sizing
|
||||
|
||||
Checkboxer har default 44px høy klikkflate. Med size="s" blir denne til 24px slik som før
|
||||
Checkboxer har default 44px høy klikkflate. Med size="small" blir denne til 24px slik som før
|
||||
|
||||
```jsx
|
||||
<CheckboxGroup legend="Mollit eiusmod" error="Boks nr 2 må være valgt" size="s">
|
||||
<CheckboxGroup
|
||||
legend="Mollit eiusmod"
|
||||
error="Boks nr 2 må være valgt"
|
||||
size="small"
|
||||
>
|
||||
<Checkbox value="Apple">Apple</Checkbox>
|
||||
<Checkbox value="Orange">Orange</Checkbox>
|
||||
<Checkbox value="Melon">Melon</Checkbox>
|
||||
@@ -109,7 +113,7 @@ Checkboxer har default 44px høy klikkflate. Med size="s" blir denne til 24px sl
|
||||
<CheckboxGroup
|
||||
legend="Mollit eiusmod"
|
||||
error="Boks nr 2 må være valgt"
|
||||
size="s"
|
||||
size="small"
|
||||
>
|
||||
<Checkbox value="Apple">Apple</Checkbox>
|
||||
<Checkbox value="Orange" error="Boksen må være valgt">
|
||||
|
||||
@@ -48,7 +48,7 @@ export const All = () => {
|
||||
<CheckboxGroup
|
||||
legend="Mollit eiusmod"
|
||||
error="Boks nr 2 må være valgt"
|
||||
size="s"
|
||||
size="small"
|
||||
>
|
||||
<Checkbox value="Apple">Apple</Checkbox>
|
||||
<Checkbox value="Orange">Orange</Checkbox>
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
import React, { forwardRef, HTMLAttributes } from "react";
|
||||
import cl from "classnames";
|
||||
import { Title } from "../..";
|
||||
import { Heading, BodyShort } from "../..";
|
||||
|
||||
export interface ErrorSummaryProps extends HTMLAttributes<HTMLDivElement> {
|
||||
/**
|
||||
@@ -9,9 +9,9 @@ export interface ErrorSummaryProps extends HTMLAttributes<HTMLDivElement> {
|
||||
children: React.ReactNode;
|
||||
/**
|
||||
* Changes padding and font-sizes
|
||||
* @default "m"
|
||||
* @default "medium"
|
||||
*/
|
||||
size?: "m" | "s";
|
||||
size?: "medium" | "small";
|
||||
/**
|
||||
* Heading above links
|
||||
*/
|
||||
@@ -25,7 +25,14 @@ export interface ErrorSummaryProps extends HTMLAttributes<HTMLDivElement> {
|
||||
|
||||
const ErrorSummary = forwardRef<HTMLDivElement, ErrorSummaryProps>(
|
||||
(
|
||||
{ children, className, size = "m", headingTag = "h2", heading, ...rest },
|
||||
{
|
||||
children,
|
||||
className,
|
||||
size = "medium",
|
||||
headingTag = "h2",
|
||||
heading,
|
||||
...rest
|
||||
},
|
||||
ref
|
||||
) => {
|
||||
return (
|
||||
@@ -40,24 +47,18 @@ const ErrorSummary = forwardRef<HTMLDivElement, ErrorSummaryProps>(
|
||||
tabIndex={-1}
|
||||
role="region"
|
||||
>
|
||||
<Title
|
||||
className="navds-error-summary__title"
|
||||
component={headingTag}
|
||||
size="s"
|
||||
<Heading
|
||||
className="navds-error-summary__heading"
|
||||
as={headingTag}
|
||||
size="small"
|
||||
>
|
||||
{heading}
|
||||
</Title>
|
||||
<ul
|
||||
className={cl(
|
||||
"navds-error-summary__list",
|
||||
"navds-body-short",
|
||||
`navds-body--${size}`
|
||||
)}
|
||||
>
|
||||
</Heading>
|
||||
<BodyShort as="ul" size={size} className="navds-error-summary__list">
|
||||
{React.Children.map(children, (child) => {
|
||||
return <li key={child?.toString()}>{child}</li>;
|
||||
})}
|
||||
</ul>
|
||||
</BodyShort>
|
||||
</div>
|
||||
);
|
||||
}
|
||||
|
||||
@@ -2,20 +2,20 @@ import React, { forwardRef } from "react";
|
||||
import cl from "classnames";
|
||||
import { OverridableComponent } from "../..";
|
||||
|
||||
export type ErrorType = OverridableComponent<ErrorSummaryItemProps>;
|
||||
|
||||
export interface ErrorSummaryItemProps {
|
||||
props: {
|
||||
/**
|
||||
* Link text
|
||||
*/
|
||||
children: React.ReactNode;
|
||||
} & React.HTMLAttributes<HTMLAnchorElement>;
|
||||
defaultComponent: "a";
|
||||
export interface ErrorSummaryItemProps
|
||||
extends React.AnchorHTMLAttributes<HTMLAnchorElement> {
|
||||
/**
|
||||
* Link text
|
||||
*/
|
||||
children: React.ReactNode;
|
||||
}
|
||||
|
||||
export type ErrorType = OverridableComponent<
|
||||
ErrorSummaryItemProps,
|
||||
HTMLAnchorElement
|
||||
>;
|
||||
const ErrorSummaryItem: ErrorType = forwardRef(
|
||||
({ children, component: Component = "a", className, ...rest }, ref) => {
|
||||
({ children, as: Component = "a", className, ...rest }, ref) => {
|
||||
return (
|
||||
<Component
|
||||
{...rest}
|
||||
|
||||
@@ -16,8 +16,8 @@ export const All = () => {
|
||||
Tekstfeltet må ha en godkjent e-mail
|
||||
</ErrorSummaryItem>
|
||||
</ErrorSummary>
|
||||
<h2>size s</h2>
|
||||
<ErrorSummary size="s" heading="Feiloppsummering komponent">
|
||||
<h2>size small</h2>
|
||||
<ErrorSummary size="small" heading="Feiloppsummering komponent">
|
||||
<ErrorSummaryItem href="#1">Checkbox må fylles ut</ErrorSummaryItem>
|
||||
<ErrorSummaryItem href="#2">
|
||||
Tekstfeltet må ha en godkjent e-mail
|
||||
|
||||
@@ -46,7 +46,7 @@ const Radio = forwardRef<HTMLInputElement, RadioProps>((props, ref) => {
|
||||
ref={ref}
|
||||
/>
|
||||
<BodyShort
|
||||
component="label"
|
||||
as="label"
|
||||
htmlFor={inputProps.id}
|
||||
size={size}
|
||||
className="navds-radio__label"
|
||||
|
||||
@@ -67,7 +67,7 @@ const RadioGroup = forwardRef<HTMLFieldSetElement, RadioGroupProps>(
|
||||
className={cl(
|
||||
className,
|
||||
"navds-radio-group",
|
||||
`navds-radio-group--${rest.size ?? fieldset?.size ?? "m"}`
|
||||
`navds-radio-group--${rest.size ?? fieldset?.size ?? "medium"}`
|
||||
)}
|
||||
>
|
||||
<RadioGroupContext.Provider
|
||||
|
||||
@@ -95,10 +95,14 @@ Man kan både sette en description på RadioGroup og selve Radio
|
||||
|
||||
## Sizing
|
||||
|
||||
Radioer har default 44px høy klikkflate. Med size="s" blir denne til 24px slik som før
|
||||
Radioer har default 44px høy klikkflate. Med size="small" blir denne til 24px slik som før
|
||||
|
||||
```jsx
|
||||
<RadioGroup legend="Mollit eiusmod" error="Boks nr 2 må være valgt" size="s">
|
||||
<RadioGroup
|
||||
legend="Mollit eiusmod"
|
||||
error="Boks nr 2 må være valgt"
|
||||
size="small"
|
||||
>
|
||||
<Radio value="Apple">Apple</Radio>
|
||||
<Radio value="Orange">Orange</Radio>
|
||||
<Radio value="Melon">Melon</Radio>
|
||||
@@ -106,7 +110,11 @@ Radioer har default 44px høy klikkflate. Med size="s" blir denne til 24px slik
|
||||
```
|
||||
|
||||
<Canvas>
|
||||
<RadioGroup legend="Mollit eiusmod" error="Boks nr 2 må være valgt" size="s">
|
||||
<RadioGroup
|
||||
legend="Mollit eiusmod"
|
||||
error="Boks nr 2 må være valgt"
|
||||
size="small"
|
||||
>
|
||||
<Radio value="Apple">Apple</Radio>
|
||||
<Radio value="Orange" error="Boksen må være valgt">
|
||||
Orange
|
||||
|
||||
@@ -45,7 +45,7 @@ export const All = () => {
|
||||
<RadioGroup
|
||||
legend="Mollit eiusmod"
|
||||
error="Boks nr 2 må være valgt"
|
||||
size="s"
|
||||
size="small"
|
||||
>
|
||||
<Radio value="Apple">Apple</Radio>
|
||||
<Radio value="Orange">Orange</Radio>
|
||||
|
||||
@@ -11,7 +11,7 @@ export interface SearchFieldContextProps {
|
||||
"aria-describedby"?: string;
|
||||
disabled?: boolean;
|
||||
};
|
||||
size?: "m" | "s";
|
||||
size?: "medium" | "small";
|
||||
}
|
||||
|
||||
export const SearchFieldContext = React.createContext<SearchFieldContextProps | null>(
|
||||
@@ -63,7 +63,7 @@ const SearchField = forwardRef<HTMLDivElement, SearchFieldProps>(
|
||||
className={cl(
|
||||
className,
|
||||
"navds-form-field",
|
||||
`navds-form-field--${size ?? "m"}`,
|
||||
`navds-form-field--${size ?? "medium"}`,
|
||||
"navds-search-field",
|
||||
{ "navds-search-field--error": hasError }
|
||||
)}
|
||||
@@ -71,7 +71,7 @@ const SearchField = forwardRef<HTMLDivElement, SearchFieldProps>(
|
||||
<Label
|
||||
htmlFor={inputProps.id}
|
||||
size={size}
|
||||
component="label"
|
||||
as="label"
|
||||
className={cl("navds-text-field__label", {
|
||||
"sr-only": hideLabel,
|
||||
})}
|
||||
|
||||
@@ -11,13 +11,13 @@ export interface SearchFieldButtonProps extends Omit<ButtonProps, "size"> {
|
||||
children: React.ReactNode;
|
||||
/**
|
||||
* Changes design and interactions
|
||||
* @default "action"
|
||||
* @default "primary"
|
||||
*/
|
||||
variant?: "primary" | "action";
|
||||
variant?: "primary" | "secondary";
|
||||
}
|
||||
|
||||
const SearchFieldButton = forwardRef<HTMLButtonElement, SearchFieldButtonProps>(
|
||||
({ className, variant = "action", disabled, ...rest }, ref) => {
|
||||
({ className, variant = "primary", disabled, ...rest }, ref) => {
|
||||
const searchField = useContext(SearchFieldContext);
|
||||
|
||||
if (searchField === null) {
|
||||
|
||||
@@ -11,15 +11,15 @@ export interface SearchFieldClearButtonProps extends Omit<ButtonProps, "size"> {
|
||||
children: React.ReactNode;
|
||||
/**
|
||||
* Changes design and interactions
|
||||
* @default "primary"
|
||||
* @default "secondary"
|
||||
*/
|
||||
variant?: "primary" | "action";
|
||||
variant?: "primary" | "secondary";
|
||||
}
|
||||
|
||||
const SearchFieldClearButton = forwardRef<
|
||||
HTMLButtonElement,
|
||||
SearchFieldClearButtonProps
|
||||
>(({ className, variant = "primary", disabled, ...rest }, ref) => {
|
||||
>(({ className, variant = "secondary", disabled, ...rest }, ref) => {
|
||||
const searchField = useContext(SearchFieldContext);
|
||||
|
||||
if (searchField === null) {
|
||||
@@ -31,9 +31,9 @@ const SearchFieldClearButton = forwardRef<
|
||||
|
||||
return (
|
||||
<Button
|
||||
ref={ref}
|
||||
className={cl(className, "navds-search-field__button")}
|
||||
{...rest}
|
||||
ref={ref}
|
||||
className={cl(className, "navds-search-field__clear-button")}
|
||||
size={size}
|
||||
variant={variant}
|
||||
disabled={disabled ?? inputProps?.disabled}
|
||||
|
||||
@@ -20,14 +20,15 @@ const SearchFieldInput = forwardRef<HTMLInputElement, SearchFieldInputProps>(
|
||||
<input
|
||||
{...rest}
|
||||
{...inputProps}
|
||||
type="search"
|
||||
role="searchbox"
|
||||
ref={ref}
|
||||
type="text"
|
||||
className={cl(
|
||||
className,
|
||||
"navds-search-field__input",
|
||||
"navds-text-field__input",
|
||||
"navds-body-short",
|
||||
`navds-body-${size ?? "m"}`
|
||||
`navds-body-${size ?? "medium"}`
|
||||
)}
|
||||
/>
|
||||
);
|
||||
|
||||
@@ -7,24 +7,23 @@ import {
|
||||
SearchFieldClearButton,
|
||||
} from "../index";
|
||||
|
||||
export const Example = () => {
|
||||
export const Example = ({ size = "medium" }: { size: "medium" | "small" }) => {
|
||||
const [value, setValue] = useState("");
|
||||
|
||||
return (
|
||||
<SearchField
|
||||
label="Mollit eiusmod"
|
||||
description="Ea cupidatat eu sunt commodo"
|
||||
>
|
||||
<SearchField size={size} label="Skriv i søkefeltet for å vise clearbutton">
|
||||
<SearchFieldInput
|
||||
value={value}
|
||||
onChange={(e) => setValue(e.target.value)}
|
||||
/>
|
||||
<SearchFieldClearButton onClick={() => setValue("")}>
|
||||
<Close />
|
||||
<span>Tøm</span>
|
||||
</SearchFieldClearButton>
|
||||
{!!value && (
|
||||
<SearchFieldClearButton onClick={() => setValue("")}>
|
||||
<Close />
|
||||
Tøm
|
||||
</SearchFieldClearButton>
|
||||
)}
|
||||
<SearchFieldButton>
|
||||
<Search /> <span>Søk</span>
|
||||
<Search /> Søk
|
||||
</SearchFieldButton>
|
||||
</SearchField>
|
||||
);
|
||||
|
||||
@@ -24,7 +24,7 @@ Komponenten er ikke testet eller gått gjennom et design-review, så anbefalses
|
||||
<SearchField label="Mollit eiusmod" description="Ea cupidatat eu sunt commodo">
|
||||
<SearchFieldInput />
|
||||
<SearchFieldButton>
|
||||
<Search /> <span>Søk</span>
|
||||
<Search /> Søk
|
||||
</SearchFieldButton>
|
||||
</SearchField>
|
||||
```
|
||||
@@ -36,7 +36,7 @@ Komponenten er ikke testet eller gått gjennom et design-review, så anbefalses
|
||||
>
|
||||
<SearchFieldInput />
|
||||
<SearchFieldButton>
|
||||
<Search /> <span>Søk</span>
|
||||
<Search /> Søk
|
||||
</SearchFieldButton>
|
||||
</SearchField>
|
||||
</Canvas>
|
||||
@@ -54,7 +54,7 @@ Vi har satt `label` som required siden man vil bruke den i sammenheng med denne
|
||||
>
|
||||
<SearchFieldInput />
|
||||
<SearchFieldButton>
|
||||
<Search /> <span>Søk</span>
|
||||
<Search /> Søk
|
||||
</SearchFieldButton>
|
||||
</SearchField>
|
||||
```
|
||||
@@ -67,7 +67,7 @@ Vi har satt `label` som required siden man vil bruke den i sammenheng med denne
|
||||
>
|
||||
<SearchFieldInput />
|
||||
<SearchFieldButton>
|
||||
<Search /> <span>Søk</span>
|
||||
<Search /> Søk
|
||||
</SearchFieldButton>
|
||||
</SearchField>
|
||||
</Canvas>
|
||||
@@ -79,11 +79,11 @@ Vi har satt `label` som required siden man vil bruke den i sammenheng med denne
|
||||
label="Mollit eiusmod"
|
||||
description="Ea cupidatat eu sunt commodo"
|
||||
hideLabel
|
||||
size="s"
|
||||
size="small"
|
||||
>
|
||||
<SearchFieldInput />
|
||||
<SearchFieldButton>
|
||||
<Search /> <span>Søk</span>
|
||||
<Search /> Søk
|
||||
</SearchFieldButton>
|
||||
</SearchField>
|
||||
```
|
||||
@@ -93,11 +93,11 @@ Vi har satt `label` som required siden man vil bruke den i sammenheng med denne
|
||||
label="Mollit eiusmod"
|
||||
description="Ea cupidatat eu sunt commodo"
|
||||
hideLabel
|
||||
size="s"
|
||||
size="small"
|
||||
>
|
||||
<SearchFieldInput />
|
||||
<SearchFieldButton>
|
||||
<Search /> <span>Søk</span>
|
||||
<Search /> Søk
|
||||
</SearchFieldButton>
|
||||
</SearchField>
|
||||
</Canvas>
|
||||
@@ -113,7 +113,7 @@ Vi har satt `label` som required siden man vil bruke den i sammenheng med denne
|
||||
>
|
||||
<SearchFieldInput />
|
||||
<SearchFieldButton>
|
||||
<Search /> <span>Søk</span>
|
||||
<Search /> Søk
|
||||
</SearchFieldButton>
|
||||
</SearchField>
|
||||
```
|
||||
@@ -127,80 +127,35 @@ Vi har satt `label` som required siden man vil bruke den i sammenheng med denne
|
||||
>
|
||||
<SearchFieldInput />
|
||||
<SearchFieldButton>
|
||||
<Search /> <span>Søk</span>
|
||||
<Search /> Søk
|
||||
</SearchFieldButton>
|
||||
</SearchField>
|
||||
</Canvas>
|
||||
|
||||
## Plassering av knapp
|
||||
## ClearButton
|
||||
|
||||
Man kan bruke `SearchFieldClearButton` for å håndtere clearing av value i `<input />`. For å bruke denne
|
||||
kreves det da at `SearchFieldInput` er controlled slik at man styrer state selv slik som eksemplet under.
|
||||
Hvis man bare ønsker at den bare skal vises når bruker har begynt å skrive, anbefaler vi bare å rendre
|
||||
den når inputvalue ikke er empty.
|
||||
|
||||
```jsx
|
||||
<SearchField
|
||||
label="Mollit eiusmod"
|
||||
description="Ea cupidatat eu sunt commodo"
|
||||
hideLabel
|
||||
>
|
||||
<SearchField label="Mollit eiusmod" description="Ea cupidatat eu sunt commodo">
|
||||
<SearchFieldInput value={value} onChange={(e) => setValue(e.target.value)} />
|
||||
{!!value && (
|
||||
<SearchFieldClearButton onClick={() => setValue("")}>
|
||||
<Close /> Tøm
|
||||
</SearchFieldClearButton>
|
||||
)}
|
||||
<SearchFieldButton>
|
||||
<Search /> <span>Søk</span>
|
||||
</SearchFieldButton>
|
||||
<SearchFieldInput />
|
||||
</SearchField>
|
||||
<SearchField
|
||||
label="Mollit eiusmod"
|
||||
description="Ea cupidatat eu sunt commodo"
|
||||
hideLabel
|
||||
>
|
||||
<SearchFieldInput />
|
||||
<SearchFieldButton>
|
||||
<Search /> <span>Søk</span>
|
||||
<Search /> Søk
|
||||
</SearchFieldButton>
|
||||
</SearchField>
|
||||
```
|
||||
|
||||
<Canvas>
|
||||
<div>
|
||||
<SearchField
|
||||
label="Mollit eiusmod"
|
||||
description="Ea cupidatat eu sunt commodo"
|
||||
hideLabel
|
||||
>
|
||||
<SearchFieldButton>
|
||||
<Search /> <span>Søk</span>
|
||||
</SearchFieldButton>
|
||||
<SearchFieldInput />
|
||||
</SearchField>
|
||||
<br />
|
||||
<SearchField
|
||||
label="Mollit eiusmod"
|
||||
description="Ea cupidatat eu sunt commodo"
|
||||
hideLabel
|
||||
>
|
||||
<SearchFieldInput />
|
||||
<SearchFieldButton>
|
||||
<Search /> <span>Søk</span>
|
||||
</SearchFieldButton>
|
||||
</SearchField>
|
||||
<Example />
|
||||
<Example size="small" />
|
||||
</div>
|
||||
</Canvas>
|
||||
|
||||
<h2>ClearButton</h2>
|
||||
|
||||
Man kan bruke `SearchFieldClearButton` for å håndtere clearing av value i `<input />`. For å bruke denne
|
||||
kreves det da at `SearchFieldInput` er controlled slik at man styrer state selv slik som eksemplet under.
|
||||
|
||||
```jsx
|
||||
<SearchField label="Mollit eiusmod" description="Ea cupidatat eu sunt commodo">
|
||||
<SearchFieldInput value={value} onChange={(e) => setValue(e.target.value)} />
|
||||
<SearchFieldClearButton onClick={() => setValue("")}>
|
||||
<Close />
|
||||
<span>Tøm</span>
|
||||
</SearchFieldClearButton>
|
||||
<SearchFieldButton>
|
||||
<Search /> <span>Søk</span>
|
||||
</SearchFieldButton>
|
||||
</SearchField>
|
||||
```
|
||||
|
||||
<Canvas>
|
||||
<Example />
|
||||
</Canvas>
|
||||
@@ -1,4 +1,4 @@
|
||||
import React from "react";
|
||||
import React, { useState } from "react";
|
||||
import { Meta } from "@storybook/react/types-6-0";
|
||||
import { Close, Search } from "@navikt/ds-icons";
|
||||
import {
|
||||
@@ -14,6 +14,7 @@ export default {
|
||||
} as Meta;
|
||||
|
||||
export const All = () => {
|
||||
const [show, setShow] = useState(false);
|
||||
return (
|
||||
<>
|
||||
<h1>SearchField</h1>
|
||||
@@ -23,7 +24,7 @@ export const All = () => {
|
||||
>
|
||||
<SearchFieldInput />
|
||||
<SearchFieldButton>
|
||||
<Search /> <span>Søk</span>
|
||||
<Search /> Søk
|
||||
</SearchFieldButton>
|
||||
</SearchField>
|
||||
<SearchField
|
||||
@@ -31,7 +32,7 @@ export const All = () => {
|
||||
description="Ea cupidatat eu sunt commodo"
|
||||
>
|
||||
<SearchFieldButton>
|
||||
<Search /> <span>Søk</span>
|
||||
<Search /> Søk
|
||||
</SearchFieldButton>
|
||||
<SearchFieldInput />
|
||||
</SearchField>
|
||||
@@ -41,9 +42,12 @@ export const All = () => {
|
||||
label="Mollit eiusmod"
|
||||
description="Ea cupidatat eu sunt commodo"
|
||||
>
|
||||
<SearchFieldInput clearSearch />
|
||||
<SearchFieldButton>
|
||||
<Search /> <span>Søk</span>
|
||||
<SearchFieldInput />
|
||||
<SearchFieldClearButton>
|
||||
<Close />
|
||||
</SearchFieldClearButton>
|
||||
<SearchFieldButton onClick={() => setShow(!show)}>
|
||||
<Search /> Søk
|
||||
</SearchFieldButton>
|
||||
</SearchField>
|
||||
<SearchField
|
||||
@@ -51,10 +55,10 @@ export const All = () => {
|
||||
description="Ea cupidatat eu sunt commodo"
|
||||
>
|
||||
<SearchFieldButton>
|
||||
<Search /> <span>Søk</span>
|
||||
<Search /> Søk
|
||||
</SearchFieldButton>
|
||||
<SearchFieldClearButton>
|
||||
<Close /> <span>Tøm</span>
|
||||
<Close /> Tøm
|
||||
</SearchFieldClearButton>
|
||||
<SearchFieldInput />
|
||||
</SearchField>
|
||||
@@ -66,7 +70,7 @@ export const All = () => {
|
||||
hideLabel
|
||||
>
|
||||
<SearchFieldButton>
|
||||
<Search /> <span>Søk</span>
|
||||
<Search /> Søk
|
||||
</SearchFieldButton>
|
||||
<SearchFieldInput />
|
||||
</SearchField>
|
||||
@@ -75,7 +79,7 @@ export const All = () => {
|
||||
<SearchField
|
||||
label="Mollit eiusmod"
|
||||
description="Ea cupidatat eu sunt commodo"
|
||||
size="s"
|
||||
size="small"
|
||||
>
|
||||
<SearchFieldButton>
|
||||
<Search />
|
||||
@@ -87,7 +91,7 @@ export const All = () => {
|
||||
<SearchField
|
||||
label="Mollit eiusmod"
|
||||
description="Ea cupidatat eu sunt commodo"
|
||||
size="s"
|
||||
size="small"
|
||||
>
|
||||
<SearchFieldInput />
|
||||
<SearchFieldButton>
|
||||
@@ -95,6 +99,35 @@ export const All = () => {
|
||||
<span className="sr-only">Søk</span>
|
||||
</SearchFieldButton>
|
||||
</SearchField>
|
||||
<SearchField
|
||||
label="Mollit eiusmod"
|
||||
description="Ea cupidatat eu sunt commodo"
|
||||
size="small"
|
||||
>
|
||||
<SearchFieldButton>
|
||||
<Search />
|
||||
<span className="sr-only">Søk</span>
|
||||
</SearchFieldButton>
|
||||
<SearchFieldClearButton>
|
||||
<Close /> Tøm
|
||||
</SearchFieldClearButton>
|
||||
<SearchFieldInput />
|
||||
</SearchField>
|
||||
|
||||
<SearchField
|
||||
label="Mollit eiusmod"
|
||||
description="Ea cupidatat eu sunt commodo"
|
||||
size="small"
|
||||
>
|
||||
<SearchFieldInput />
|
||||
<SearchFieldClearButton>
|
||||
<Close /> Tøm
|
||||
</SearchFieldClearButton>
|
||||
<SearchFieldButton>
|
||||
<Search />
|
||||
<span className="sr-only">Søk</span>
|
||||
</SearchFieldButton>
|
||||
</SearchField>
|
||||
|
||||
<h2>SearchField w error</h2>
|
||||
<SearchField
|
||||
@@ -104,7 +137,7 @@ export const All = () => {
|
||||
>
|
||||
<SearchFieldInput />
|
||||
<SearchFieldButton>
|
||||
<Search /> <span>Søk</span>
|
||||
<Search /> Søk
|
||||
</SearchFieldButton>
|
||||
</SearchField>
|
||||
<SearchField
|
||||
@@ -113,7 +146,7 @@ export const All = () => {
|
||||
error="Errormsg"
|
||||
>
|
||||
<SearchFieldButton>
|
||||
<Search /> <span>Søk</span>
|
||||
<Search /> Søk
|
||||
</SearchFieldButton>
|
||||
<SearchFieldInput />
|
||||
</SearchField>
|
||||
@@ -128,7 +161,7 @@ export const All = () => {
|
||||
>
|
||||
<SearchFieldInput />
|
||||
<SearchFieldButton>
|
||||
<Search /> <span>Søk</span>
|
||||
<Search /> Søk
|
||||
</SearchFieldButton>
|
||||
</SearchField>
|
||||
<SearchField
|
||||
@@ -137,7 +170,7 @@ export const All = () => {
|
||||
hideLabel
|
||||
>
|
||||
<SearchFieldButton>
|
||||
<Search /> <span>Søk</span>
|
||||
<Search /> Søk
|
||||
</SearchFieldButton>
|
||||
<SearchFieldInput />
|
||||
</SearchField>
|
||||
|
||||
@@ -29,7 +29,7 @@ Kommer i størrelsene "m" og "s".
|
||||
checked={checked}
|
||||
onChange={() => setChecked(!checked)}
|
||||
label="Checkbox label text"
|
||||
size="s"
|
||||
size="small"
|
||||
>
|
||||
Ipsum voluptate pariatur <Link href="#123">demolink</Link> anim officia minim
|
||||
ut mollit voluptate exercitation nulla mollit.
|
||||
@@ -37,7 +37,7 @@ Kommer i størrelsene "m" og "s".
|
||||
```
|
||||
|
||||
<Canvas>
|
||||
<ConfirmationPanelExample size="s" />
|
||||
<ConfirmationPanelExample size="small" />
|
||||
</Canvas>
|
||||
|
||||
## Errors
|
||||
|
||||
@@ -20,12 +20,12 @@ export const All = () => {
|
||||
Ipsum voluptate pariatur <Link href="#123">testlink</Link> anim officia
|
||||
minim ut mollit voluptate exercitation nulla mollit.
|
||||
</ConfirmationPanel>
|
||||
<h2>size s</h2>
|
||||
<h2>size small</h2>
|
||||
<ConfirmationPanel
|
||||
checked={checked}
|
||||
onChange={() => setChecked(!checked)}
|
||||
label="Checkbox label text"
|
||||
size="s"
|
||||
size="small"
|
||||
>
|
||||
Ipsum voluptate pariatur <Link href="#123">testlink</Link> anim officia
|
||||
minim ut mollit voluptate exercitation nulla mollit.
|
||||
@@ -46,7 +46,7 @@ export const All = () => {
|
||||
onChange={() => setChecked(!checked)}
|
||||
label="Checkbox label text"
|
||||
error="Ex cupidatat do do do"
|
||||
size="s"
|
||||
size="small"
|
||||
>
|
||||
Ipsum voluptate pariatur <Link href="#123">testlink</Link> anim officia
|
||||
minim ut mollit voluptate exercitation nulla mollit.
|
||||
|
||||
@@ -1,75 +0,0 @@
|
||||
import React, { useState } from "react";
|
||||
import { Fieldset } from "../index";
|
||||
import { Meta } from "@storybook/react/types-6-0";
|
||||
import { Button, Checkbox, CheckboxGroup } from "../../index";
|
||||
export default {
|
||||
title: "ds-react/form/uu-demo",
|
||||
component: Fieldset,
|
||||
} as Meta;
|
||||
|
||||
export const Demo1 = () => {
|
||||
const [error, setError] = useState(undefined);
|
||||
const [fieldsetError, setFieldsetError] = useState(undefined);
|
||||
const [groupError, setGroupError] = useState(undefined);
|
||||
const [propagation, setPropagation] = useState(true);
|
||||
return (
|
||||
<div>
|
||||
<h1>Nested-erros + aria-describedby</h1>
|
||||
<div>
|
||||
<Button
|
||||
style={{ marginBottom: "2rem" }}
|
||||
onClick={() => {
|
||||
!!fieldsetError
|
||||
? setFieldsetError(undefined)
|
||||
: setFieldsetError("Fieldset error message");
|
||||
}}
|
||||
>
|
||||
Toggle fieldset-error
|
||||
</Button>
|
||||
<Button
|
||||
style={{ marginBottom: "2rem" }}
|
||||
onClick={() => {
|
||||
!!groupError
|
||||
? setGroupError(undefined)
|
||||
: setGroupError("CheckboxGroup error message");
|
||||
}}
|
||||
>
|
||||
Toggle checkboxgroup-error
|
||||
</Button>
|
||||
<Button
|
||||
style={{ marginBottom: "2rem" }}
|
||||
onClick={() => {
|
||||
!!error ? setError(undefined) : setError("Textfield error message");
|
||||
}}
|
||||
>
|
||||
Toggle checkbox-error
|
||||
</Button>
|
||||
<Button
|
||||
style={{ marginBottom: "2rem" }}
|
||||
onClick={() => setPropagation(!propagation)}
|
||||
>
|
||||
Toggle errorPropagation
|
||||
</Button>
|
||||
</div>
|
||||
<Fieldset
|
||||
errorId="FIELDSET-ERROR"
|
||||
legend="Mollit eiusmod"
|
||||
error={fieldsetError}
|
||||
>
|
||||
<CheckboxGroup
|
||||
errorId="GROUP-ERROR"
|
||||
errorPropagation={propagation}
|
||||
error={groupError}
|
||||
legend="checkboxgroup"
|
||||
hideLegend
|
||||
>
|
||||
<Checkbox>Checkbox nr 1</Checkbox>
|
||||
<Checkbox errorId="CHECKBOX-ERROR" error={error}>
|
||||
Checkbox nr 2
|
||||
</Checkbox>
|
||||
<Checkbox>Checkbox nr 3</Checkbox>
|
||||
</CheckboxGroup>
|
||||
</Fieldset>
|
||||
</div>
|
||||
);
|
||||
};
|
||||
@@ -84,14 +84,14 @@ Fieldset justerer automatisk sizing på skjema-elementene. Man kan overstyre det
|
||||
`TextField` i eks dette eksemplet
|
||||
|
||||
```jsx
|
||||
<Fieldset size="s" legend="Mollit eiusmod">
|
||||
<Fieldset size="small" legend="Mollit eiusmod">
|
||||
<TextField label="Textfield label" hideLabel />
|
||||
<TextField label="Textfield label" hideLabel />
|
||||
</Fieldset>
|
||||
```
|
||||
|
||||
<Canvas>
|
||||
<Fieldset size="s" legend="Mollit eiusmod" description="Dolore minim">
|
||||
<Fieldset size="small" legend="Mollit eiusmod" description="Dolore minim">
|
||||
<TextField label="Textfield label" hideLabel />
|
||||
<TextField label="Textfield label" hideLabel />
|
||||
</Fieldset>
|
||||
|
||||
@@ -47,7 +47,7 @@ export const All = () => {
|
||||
|
||||
<h2>Sizing</h2>
|
||||
|
||||
<Fieldset size="s" legend="Mollit eiusmod" description="Dolore minim">
|
||||
<Fieldset size="small" legend="Mollit eiusmod" description="Dolore minim">
|
||||
<TextField label="Textfield label" hideLabel />
|
||||
<TextField label="Textfield label" hideLabel />
|
||||
</Fieldset>
|
||||
|
||||
@@ -3,10 +3,10 @@ import { ConfirmationPanel } from "..";
|
||||
import { Link } from "../..";
|
||||
|
||||
export const ConfirmationPanelExample = ({
|
||||
size = "m",
|
||||
size = "medium",
|
||||
error,
|
||||
}: {
|
||||
size: "m" | "s";
|
||||
size: "medium" | "small";
|
||||
error?: string;
|
||||
}) => {
|
||||
const [checked, setChecked] = useState(false);
|
||||
|
||||
Loaded 100 of 195 files, more files were not shown because too many files have changed in this diff.
Show more
Reference in new issue
Block a user