Skip to content

Demos

Default dropdown

No value is defined, but a title is given.

Code Editor
const data = [
  // Every data item can, beside "content" - contain what ever
  {
    // (optional) can be what ever
    selected_key: 'key_0',
    // (optional) is show instead of "content", once selected
    selected_value: 'Item 1 Value',
    // Item content as a string or array
    content: 'Item 1 Content',
  },
  {
    selected_key: 'key_1',
    content: ['Item 2 Value', 'Item 2 Content'],
  },
  {
    selected_value: (
      <NumberFormat always_selectall ban>
        11345678962
      </NumberFormat>
    ),
    content: [
      <NumberFormat key="ban" always_selectall ban>
        11345678962
      </NumberFormat>,
      'Bank account number',
    ],
  },
  {
    selected_key: 'key_2',
    selected_value: 'Item 3 Value',
    content: ['Item 3 Content A', 'Item 3 Content B'],
  },
  {
    selected_key: 'key_3',
    selected_value: 'Item 4 Value',
    content: ['Item 4 Content A', <>Custom Component</>],
  },
]
render(
  <Dropdown
    data={data}
    label="Label"
    title="Please select a value"
    on_change={({ data }) => {
      console.log('on_change', data)
    }}
  />,
)

Dropdown with different item content directions

Code Editor
<Dropdown
  label="Label"
  data={[
    ['Vertical', 'alignment'],
    <>
      <P modifier="medium">Vertical</P>
      <P>alignment</P>
    </>,
    <Dropdown.HorizontalItem key="item-1">
      <P modifier="medium" right="x-small">
        Horizontal
      </P>
      <P>alignment</P>
    </Dropdown.HorizontalItem>,
  ]}
/>

Icon on left side

Code Editor
<Dropdown
  label="Label"
  icon_position="left"
  data={data}
  value={3}
  skip_portal={true}
  on_change={({ data: selectedDataItem }) => {
    console.log('on_change', selectedDataItem)
  }}
  on_show={() => {
    console.log('on_show')
  }}
/>

ActionMenu

The ActionMenu will change its characteristics in mobile view. It will hide the title, and the DrawerList will be placed on the bottom of the page.

Code Editor
<Dropdown
  title="ActionMenu"
  action_menu={true}
  align_dropdown="left"
  data={() => ({
    trash: (
      <>
        <Icon icon={trash} right />
        Move to trash
      </>
    ),
    download: (
      <>
        <Icon icon={download} right />
        Download
      </>
    ),
  })}
  on_change={({ value }) => console.log('action:', value)}
/>

MoreMenu

No lasting selection will be made.

Code Editor
<Dropdown
  more_menu={true}
  size="small"
  title="Choose an item"
  data={() => [
    <Link href="/" key="item-1">
      Go to this Link
    </Link>,
    'Or press on me',
    <>Custom component</>,
  ]}
  right="small"
/>
<Dropdown
  prevent_selection={true}
  align_dropdown="right"
  size="small"
  title={null}
  aria-label="Choose an item"
  data={() => ({
    first: (
      <Link href="/" key="item-1">
        Go to this Link
      </Link>
    ),
    second: 'Or press on me',
    third: <>Custom component</>,
  })}
  right="small"
/>
<Dropdown
  more_menu={true}
  title="Choose an item"
  data={[
    <Link href="/" key="item-1">
      Go to this Link
    </Link>,
    'Or press on me',
    <>Custom component</>,
  ]}
  right="small"
/>
<Dropdown
  prevent_selection={true}
  align_dropdown="right"
  title={null}
  aria-label="Choose an item"
  data={() => ({
    first: (
      <Link href="/" key="item-1">
        Go to this Link
      </Link>
    ),
    second: 'Or press on me',
    third: <>Custom component</>,
  })}
  on_change={({ value }) => {
    console.log('on_change', value)
  }}
  on_select={({ active_item }) => {
    console.log('on_select', active_item)
  }}
/>

Dropdown as tertiary variant

Code Editor
<Dropdown
  variant="tertiary"
  direction="bottom"
  independent_width={true}
  icon_position="left"
  align_dropdown="left"
  data={data}
/>

Custom item events

Code Editor
const CustomComponent = () => (
  <CustomComponentInner
    onTouchStart={preventDefault}
    onClick={(e) => {
      console.log('Do something different')
      preventDefault(e)
    }}
  >
    Custom event handler
  </CustomComponentInner>
)
const CustomComponentInner = styled.span`
  display: block;
  width: 100%;
  margin: -1rem -2rem -1rem -1rem;
  padding: 1rem 2rem 1rem 1rem;
`
const preventDefault = (e) => {
  e.stopPropagation()
  e.preventDefault()
}
render(
  <Dropdown
    action_menu
    right
    label="Label"
    title="Choose an item"
    data={() => ({
      first: (
        <Link href="/" key="item-1">
          Go to this Link
        </Link>
      ),
      second: 'Or press on me',
      third: <CustomComponent key="item-2" />,
    })}
    on_change={({ value }) => {
      console.log('More menu:', value)
    }}
    suffix={<HelpButton title="Modal Title">Modal content</HelpButton>}
  />,
)

Dropdown in different sizes

Four sizes are available: small, default, medium and large

Code Editor
<Flex.Vertical>
  <Dropdown label="Label" size="default" data={() => data} />
  <Dropdown label="Label" size="medium" data={() => data} />
  <Dropdown label="Label" size="large" data={() => data} />
</Flex.Vertical>

Custom width

Code Editor
const CustomWidthOne = styled(Dropdown)`
  .dnb-dropdown__shell {
    width: 10rem;
  }
`
const CustomWidthTwo = styled(Dropdown)`
  &.dnb-dropdown--is-popup .dnb-drawer-list__root {
    width: 12rem;
  }
`
const CustomWidthThree = styled(Dropdown)`
  /** Change the "__shell" width */
  .dnb-dropdown__shell {
    width: 10rem;
  }

  /** Change the "__list" width */
  .dnb-drawer-list__root {
    width: 20rem;
  }
`
const CustomWidthFour = styled(Dropdown)`
  width: 60%;
  min-width: 224px; /** 14rem (please use pixels on min-width!) */
  max-width: 25rem;

  /** In case we have a label */
  .dnb-form-label + .dnb-dropdown__inner {
    width: 100%;
  }
`
render(
  <Flex.Vertical>
    <CustomWidthOne
      label="Label"
      size="default"
      icon_position="left"
      data={data}
    />
    <CustomWidthTwo label="Label" size="small" more_menu data={data} />
    <CustomWidthThree
      label="Label"
      size="large"
      align_dropdown="right"
      data={data}
    />
    <CustomWidthFour
      title="Min and max width"
      stretch={true}
      data={data}
    />
  </Flex.Vertical>,
)

Dropdown with status

And vertical label layout.

Message to the user
Code Editor
<Dropdown
  data={data}
  label="Label"
  label_direction="vertical"
  status="Message to the user"
/>

Findable list

With long list to make it scrollable and searchable

Code Editor
const scrollableData = [
  {
    content: 'A',
  },
  {
    content: 'B',
  },
  {
    selected_value: (
      <NumberFormat always_selectall ban>
        11345678962
      </NumberFormat>
    ),
    content: [
      <NumberFormat key="ban-1" always_selectall ban>
        11345678962
      </NumberFormat>,
      'C',
    ],
  },
  {
    selected_value: (
      <NumberFormat always_selectall ban>
        15349648901
      </NumberFormat>
    ),
    content: [
      <NumberFormat key="ban-2" always_selectall ban>
        15349648901
      </NumberFormat>,
      'D',
    ],
  },
  {
    content: 'E',
  },
  {
    selected_key: 'key_1',
    selected_value: 'Find me by keypress',
    content: ['F', 'F', 'F', 'F'],
  },
  {
    content: 'G',
  },
  {
    content: 'H',
  },
]
render(
  <Dropdown
    data={scrollableData}
    value="key_1" // use either index (5) or selected_key: 'key_1'
    label="Label"
  />,
)

Disabled dropdown

Code Editor
<Dropdown disabled data={['Disabled Dropdown']} label="Label" />

Individual options can also be disabled.

Code Editor
<Dropdown
  data={[
    {
      content: 'Item 1 Content',
    },
    {
      content: 'Item 2 Content',
      disabled: true,
    },
    {
      content: 'Item 3 Content',
      disabled: true,
    },
    {
      content: 'Item 4 Content A',
    },
  ]}
  label="Label"
/>

Disabled tertiary dropdown

Code Editor
<Dropdown
  disabled
  variant="tertiary"
  data={['Disabled Dropdown']}
  label="Disabled tertiary dropdown"
/>

Customized Dropdown

An example of how you can customize the look of your Dropdown

Code Editor
const styles = {
  customTrigger: {
    backgroundColor: '#d4ecc5',
    color: '#14555a',
    border: 'none',
    borderRadius: '8px',
    padding: '8px 16px',
    fontWeight: 600,
  },
  customMenuItem: {
    display: 'flex',
    flexFlow: 'row nowrap',
    justifyContent: 'space-between',
    alignItems: 'center',
  },
  customMenuItemTitle: {
    display: 'flex',
    flexFlow: 'column',
    gap: '0.5rem',
  },
}
const MenuItem = ({ title, content, key }) => (
  <span style={styles.customMenuItem} key="item-1">
    <span style={styles.customMenuItemTitle}>
      {title}
      <span>{content}</span>
    </span>
    <Icon icon={chevron_right} />
  </span>
)
const data = {
  accounts: (
    <MenuItem key="item-1" title="Accounts" content={'Bills, Savings'} />
  ),
  loans: <MenuItem key="item-2" title="Loans" content={'Mortgage, Car'} />,
  cards: (
    <MenuItem key="item-3" title="Cards" content={'Visa, Mastercard'} />
  ),
  stocks: (
    <MenuItem key="item-4" title="Stocks" content={'Nvidia, Apple'} />
  ),
}
render(
  <Dropdown
    data={data}
    action_menu
    trigger_element={(props) => (
      <button {...props} style={styles.customTrigger}>
        <Icon icon={newspaper} /> Custom trigger{' '}
        <Icon icon={chevron_down} />
      </button>
    )}
  />,
)

DrawerList opened

Only to visualize and used for visual testing

  • Brukskonto - Kari Nordmann
  • Sparekonto - Ole Nordmann
  • Feriekonto - Kari Nordmann med et kjempelangt etternavnsen
  • Oppussing - Ole Nordmann