Skip to content
This repository has been archived by the owner on Mar 4, 2020. It is now read-only.

Commit

Permalink
feat(dropdown): align, position, offset props + automatic position (#…
Browse files Browse the repository at this point in the history
…1312)

* feat(dropdown): align, position, offset props + automatic position

* changelog

* addresed part of PR comments

* - fixed dropdown toggle indicator icon direction;
- implemented knobs for dropdown and popup examples for position

* changelog

* - refactored Positioner to include updating logic;
- removed UpdatableComponent

* removed redundant prop

* addressed PR comments

* several fixes and improved perf

* add offset to proptypes for Popup and Dropdown

* reimplement Popper from react-popper with our custom component

* fix positioning

* fix Popper custom implementation and integrate in Popup and Dropdown

* feat(popper): custom react wrapper

* feat(popper): custom react wrapper

* changelog

* addressed comments

* aligned with latest Popper API

* changelog

* fix type

* reverted popup example file

* fix bad merge

* removed default padding from popper

* improved dropdown positioning and removed dead styles

* Update docs/src/examples/components/Popup/Variations/PopupExamplePosition.shorthand.tsx

Co-Authored-By: Oleksandr Fediashov <alexander.mcgarret@gmail.com>

* removed toggle icon logic

* addressed final comments

* new changelog entry

* addressed final comments

* final touches in examples and mentions prototype
  • Loading branch information
Alexandru Buliga authored May 29, 2019
1 parent c69313c commit 727e9c2
Show file tree
Hide file tree
Showing 13 changed files with 261 additions and 127 deletions.
2 changes: 2 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -19,6 +19,7 @@ This project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.htm

### BREAKING CHANGES
- Remove convoluted conditions from component's element type calculations @kuzhelov ([#1396](https://github.com/stardust-ui/react/pull/1396))
- Replace `Dropdown` variables: `borderRadius` with `containerBorderRadius`, `openBorderRadius` with `openAboveContainerBorderRadius` and `openBelowContainerBorderRadius`, `listBorderRadius` with `aboveListBorderRadius` and `belowListBorderRadius` @Bugaa92 ([#1312](https://github.com/stardust-ui/react/pull/1312))

### Fixes
- ESC key pressed on a trigger element should propagate event if `Popup` is closed @sophieH29 ([#1373](https://github.com/stardust-ui/react/pull/1373))
Expand All @@ -32,6 +33,7 @@ This project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.htm
- Export `message-seen`, `presence-available`, `presence-stroke`, `open-outside` and `eye-friendlier` icons to Teams theme @joheredi ([#1390](https://github.com/stardust-ui/react/pull/1390))
- Add 'lightning' icon @notandrew ([#1385](https://github.com/stardust-ui/react/pull/1385))
- Add automatic positioning inside viewport for `Menu` with submenus @Bugaa92 ([#1384](https://github.com/stardust-ui/react/pull/1384))
- Add `align`, `position`, `offset` props for `Dropdown` component @Bugaa92 ([#1312](https://github.com/stardust-ui/react/pull/1312))

### Documentation
- Accessibility: improve introduction section @jurokapsiar ([#1368](https://github.com/stardust-ui/react/pull/1368))
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
import * as React from 'react'
import { Grid, Dropdown } from '@stardust-ui/react'

const inputItems = ['Bruce Wayne', 'Natasha Romanoff', 'Steven Strange', 'Alfred Pennyworth']

const DropdownExamplePosition = () => (
<Grid columns="1" variables={{ padding: '30px' }} styles={{ justifyItems: 'center' }}>
<Dropdown items={inputItems} placeholder="Select your hero" offset="-50%p" />
</Grid>
)

export default DropdownExamplePosition
Original file line number Diff line number Diff line change
@@ -0,0 +1,41 @@
import * as React from 'react'
import * as _ from 'lodash'
import { Dropdown, Grid, Alignment, Position } from '@stardust-ui/react'
import { useSelectKnob, useBooleanKnob } from '@stardust-ui/docs-components'

const inputItems = ['Bruce Wayne', 'Natasha Romanoff', 'Steven Strange']

const DropdownExamplePosition = () => {
const [open] = useBooleanKnob({ name: 'open', initialValue: true })

const [positionAndAlign] = useSelectKnob({
name: 'position-align',
initialValue: 'below',
values: positionAndAlignValues,
})

const [position, align] = _.split(positionAndAlign, '-') as [Position, Alignment]

return (
<Grid columns="1" variables={{ padding: '140px 0' }} styles={{ justifyItems: 'center' }}>
<Dropdown
open={open}
items={inputItems}
placeholder={`Opens ${position} trigger${align ? ` aligned to ${align}` : ''}.`}
align={align}
position={position}
/>
</Grid>
)
}

export default DropdownExamplePosition

const positionAndAlignValues = [
'above',
'below',
'before-top',
'before-bottom',
'after-top',
'after-bottom',
]
10 changes: 10 additions & 0 deletions docs/src/examples/components/Dropdown/Variations/index.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -19,6 +19,16 @@ const Variations = () => (
description="A multiple search dropdown that uses French to provide information and accessibility."
examplePath="components/Dropdown/Variations/DropdownExampleSearchMultipleFrenchLanguage"
/>
<ComponentExample
title="Alignment and Position"
description="A dropdown can be positioned around its trigger and aligned relative to the trigger's margins. Click on a button to open a dropdown on a specific position and alignment."
examplePath="components/Dropdown/Variations/DropdownExamplePosition"
/>
<ComponentExample
title="Offset"
description="Dropdown position could be further customized by providing offset value. Note that percentage values of both trigger and dropdown elements' lengths are supported."
examplePath="components/Dropdown/Variations/DropdownExampleOffset"
/>
</ExampleSection>
)

Expand Down
Original file line number Diff line number Diff line change
@@ -1,54 +1,76 @@
import * as React from 'react'
import { Button, Grid, Popup } from '@stardust-ui/react'
import * as _ from 'lodash'
import { Button, Grid, Popup, Alignment, Position } from '@stardust-ui/react'
import { useBooleanKnob, useSelectKnob } from '@stardust-ui/docs-components'

const PopupWithButton = props => {
const { position, align, icon, padding } = props
const PopupExamplePosition = () => {
const [open] = useBooleanKnob({ name: 'open-s', initialValue: true })

const [positionAndAlign] = useSelectKnob({
name: 'position-align-s',
initialValue: 'above-start',
values: positionAndAlignValues,
})

const [position, align] = _.split(positionAndAlign, '-') as [Position, Alignment]
const buttonStyles = { padding: paddings[positionAndAlign], height: '38px', minWidth: '64px' }

return (
<Popup
align={align}
position={position}
trigger={<Button icon={icon} styles={{ padding, height: '38px', minWidth: '64px' }} />}
content={{
content: (
<p>
The popup is rendered {position} the trigger
<br />
aligned to the {align}.
</p>
),
}}
/>
<Grid columns="1" variables={{ padding: '100px 0' }} styles={{ justifyItems: 'center' }}>
<Popup
open={open || undefined}
align={align}
position={position}
trigger={<Button icon={icons[position]} styles={buttonStyles} />}
content={{
content: (
<p>
The popup is rendered {position} the trigger
<br />
aligned to the {align}.
</p>
),
}}
/>
</Grid>
)
}

const triggers = [
{ position: 'above', align: 'start', icon: 'arrow circle up', padding: '5px 42px 18px 5px' },
{ position: 'above', align: 'center', icon: 'arrow circle up', padding: '5px 5px 18px 5px' },
{ position: 'above', align: 'end', icon: 'arrow circle up', padding: '5px 5px 18px 42px' },
{ position: 'below', align: 'start', icon: 'arrow circle down', padding: '18px 42px 5px 5px' },
{ position: 'below', align: 'center', icon: 'arrow circle down', padding: '18px 5px 5px 5px' },
{ position: 'below', align: 'end', icon: 'arrow circle down', padding: '18px 5px 5px 42px' },
{ position: 'before', align: 'top', icon: 'arrow circle left', padding: '5px 42px 18px 5px' },
{ position: 'before', align: 'center', icon: 'arrow circle left', padding: '5px 42px 5px 5px' },
{ position: 'before', align: 'bottom', icon: 'arrow circle left', padding: '18px 42px 5px 5px' },
{ position: 'after', align: 'top', icon: 'arrow circle right', padding: '5px 5px 18px 42px' },
{ position: 'after', align: 'center', icon: 'arrow circle right', padding: '5px 5px 5px 42px' },
{ position: 'after', align: 'bottom', icon: 'arrow circle right', padding: '18px 5px 5px 42px' },
export default PopupExamplePosition

const positionAndAlignValues = [
'above-start',
'above-center',
'above-end',
'below-start',
'below-center',
'below-end',
'before-top',
'before-center',
'before-bottom',
'after-top',
'after-center',
'after-bottom',
]

const PopupExamplePosition = () => (
<Grid columns="repeat(3, 30px)" variables={{ padding: '30px', gridGap: '80px' }}>
{triggers.map(({ position, align, icon, padding }) => (
<PopupWithButton
position={position}
align={align}
icon={icon}
padding={padding}
key={`${position}-${align}`}
/>
))}
</Grid>
)
const icons: Record<Position, string> = {
above: 'arrow circle up',
below: 'arrow circle down',
before: 'arrow circle left',
after: 'arrow circle right',
}

export default PopupExamplePosition
const paddings: Record<string, React.CSSProperties['padding']> = {
'above-start': '5px 42px 18px 5px',
'above-center': '5px 5px 18px 5px',
'above-end': '5px 5px 18px 42px',
'below-start': '18px 42px 5px 5px',
'below-center': '18px 5px 5px 5px',
'below-end': '18px 5px 5px 42px',
'before-top': '5px 42px 18px 5px',
'before-center': '5px 42px 5px 5px',
'before-bottom': '18px 42px 5px 5px',
'after-top': '5px 5px 18px 42px',
'after-center': '5px 5px 5px 42px',
'after-bottom': '18px 5px 5px 42px',
}
112 changes: 66 additions & 46 deletions docs/src/examples/components/Popup/Variations/PopupExamplePosition.tsx
Original file line number Diff line number Diff line change
@@ -1,57 +1,77 @@
import * as React from 'react'
import { Button, Grid, Popup } from '@stardust-ui/react'
import * as _ from 'lodash'
import { Button, Grid, Popup, Alignment, Position } from '@stardust-ui/react'
import { useBooleanKnob, useSelectKnob } from '@stardust-ui/docs-components'

const PopupArrowExample = props => {
const { position, align, icon, padding } = props
const PopupExamplePosition = () => {
const [open] = useBooleanKnob({ name: 'open-c', initialValue: true })

const buttonStyles = { padding, height: '38px', minWidth: '64px' }
const [positionAndAlign] = useSelectKnob({
name: 'position-align-c',
initialValue: 'above-start',
values: positionAndAlignValues,
})

const [position, align] = _.split(positionAndAlign, '-') as [Position, Alignment]
const buttonStyles = { padding: paddings[positionAndAlign], height: '38px', minWidth: '64px' }

return (
<Popup
align={align}
position={position}
content={{
content: (
<p>
The popup is rendered {position} the trigger
<br />
aligned to the {align}.
</p>
),
}}
>
<Button icon={icon} styles={buttonStyles} />
</Popup>
<Grid columns="1" variables={{ padding: '100px 0' }} styles={{ justifyItems: 'center' }}>
<Popup
open={open || undefined}
align={align}
position={position}
content={{
content: (
<p>
The popup is rendered {position} the trigger
<br />
aligned to the {align}.
</p>
),
}}
>
<Button icon={icons[position]} styles={buttonStyles} />
</Popup>
</Grid>
)
}

const triggers = [
{ position: 'above', align: 'start', icon: 'arrow circle up', padding: '5px 42px 18px 5px' },
{ position: 'above', align: 'center', icon: 'arrow circle up', padding: '5px 5px 18px 5px' },
{ position: 'above', align: 'end', icon: 'arrow circle up', padding: '5px 5px 18px 42px' },
{ position: 'below', align: 'start', icon: 'arrow circle down', padding: '18px 42px 5px 5px' },
{ position: 'below', align: 'center', icon: 'arrow circle down', padding: '18px 5px 5px 5px' },
{ position: 'below', align: 'end', icon: 'arrow circle down', padding: '18px 5px 5px 42px' },
{ position: 'before', align: 'top', icon: 'arrow circle left', padding: '5px 42px 18px 5px' },
{ position: 'before', align: 'center', icon: 'arrow circle left', padding: '5px 42px 5px 5px' },
{ position: 'before', align: 'bottom', icon: 'arrow circle left', padding: '18px 42px 5px 5px' },
{ position: 'after', align: 'top', icon: 'arrow circle right', padding: '5px 5px 18px 42px' },
{ position: 'after', align: 'center', icon: 'arrow circle right', padding: '5px 5px 5px 42px' },
{ position: 'after', align: 'bottom', icon: 'arrow circle right', padding: '18px 5px 5px 42px' },
export default PopupExamplePosition

const positionAndAlignValues = [
'above-start',
'above-center',
'above-end',
'below-start',
'below-center',
'below-end',
'before-top',
'before-center',
'before-bottom',
'after-top',
'after-center',
'after-bottom',
]

const PopupExamplePosition = () => (
<Grid columns="repeat(3, 30px)" variables={{ padding: '30px', gridGap: '80px' }}>
{triggers.map(({ position, align, icon, padding }) => (
<PopupArrowExample
position={position}
align={align}
icon={icon}
padding={padding}
key={`${position}-${align}`}
/>
))}
</Grid>
)
const icons: Record<Position, string> = {
above: 'arrow circle up',
below: 'arrow circle down',
before: 'arrow circle left',
after: 'arrow circle right',
}

export default PopupExamplePosition
const paddings: Record<string, React.CSSProperties['padding']> = {
'above-start': '5px 42px 18px 5px',
'above-center': '5px 5px 18px 5px',
'above-end': '5px 5px 18px 42px',
'below-start': '18px 42px 5px 5px',
'below-center': '18px 5px 5px 5px',
'below-end': '18px 5px 5px 42px',
'before-top': '5px 42px 18px 5px',
'before-center': '5px 42px 5px 5px',
'before-bottom': '18px 42px 5px 5px',
'after-top': '5px 5px 18px 42px',
'after-center': '5px 5px 5px 42px',
'after-bottom': '18px 5px 5px 42px',
}
3 changes: 2 additions & 1 deletion docs/src/prototypes/mentions/MentionsDropdown.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -22,9 +22,10 @@ const MentionsDropdown: React.FunctionComponent<MentionsContainerProps> = props
<Provider.Consumer
render={({ siteVariables: siteVars }) => (
<Dropdown
defaultOpen={true}
defaultOpen
inline
search
position="above"
items={items}
renderItem={
searchQuery
Expand Down
Loading

0 comments on commit 727e9c2

Please sign in to comment.