-
Notifications
You must be signed in to change notification settings - Fork 4.2k
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Add combined border controls components
- Loading branch information
1 parent
a719ea0
commit 7be6d5d
Showing
52 changed files
with
3,640 additions
and
24 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
152 changes: 152 additions & 0 deletions
152
packages/components/src/border-box-control/border-box-control/README.md
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,152 @@ | ||
# BorderBoxControl | ||
|
||
<div class="callout callout-alert"> | ||
This feature is still experimental. “Experimental” means this is an early implementation subject to drastic and breaking changes. | ||
</div> | ||
<br /> | ||
|
||
This component provides users with the ability to configure a single "flat" | ||
border or separate borders per side. | ||
|
||
## Development guidelines | ||
|
||
The `BorderBoxControl` effectively has two view states. The first, a "linked" | ||
view, allows configuration of a flat border via a single `BorderControl`. | ||
The second, a "split" view, contains a `BorderControl` for each side | ||
as well as a visualizer for the currently selected borders. Each view also | ||
contains a button to toggle between the two. | ||
|
||
When switching from the "split" view to "linked", if the individual side | ||
borders are not consistent, the "linked" view will display any border properties | ||
selections that are consistent while showing a mixed state for those that | ||
aren't. For example, if all borders had the same color and style but different | ||
widths, then the border dropdown in the "linked" view's `BorderControl` would | ||
show that consistent color and style but the "linked" view's width input would | ||
show "Mixed" placeholder text. | ||
|
||
## Usage | ||
|
||
```jsx | ||
import { __experimentalBorderBoxControl as BorderBoxControl } from '@wordpress/components'; | ||
import { __ } from '@wordpress/i18n'; | ||
|
||
const colors = [ | ||
{ name: 'Blue 20', color: '#72aee6' }, | ||
// ... | ||
]; | ||
|
||
const MyBorderBoxControl = () => { | ||
const defaultBorder = { | ||
color: '#72aee6', | ||
style: 'dashed', | ||
width: '1px', | ||
}; | ||
const [ borders, setBorders ] = useState( { | ||
top: defaultBorder, | ||
right: defaultBorder, | ||
bottom: defaultBorder, | ||
left: defaultBorder, | ||
} ); | ||
const onChange = ( newBorders ) => setBorders( newBorders ); | ||
|
||
return ( | ||
<BorderBoxControl | ||
colors={ colors } | ||
label={ __( 'Borders' ) } | ||
onChange={ onChange } | ||
value={ borders } | ||
/> | ||
); | ||
}; | ||
``` | ||
|
||
## Props | ||
|
||
### `colors`: `Array` | ||
|
||
An array of color definitions. This may also be a multi-dimensional array where | ||
colors are organized by multiple origins. | ||
|
||
Each color may be an object containing a `name` and `color` value. | ||
|
||
- Required: No | ||
|
||
### `disableCustomColors`: `boolean` | ||
|
||
This toggles the ability to choose custom colors. | ||
|
||
- Required: No | ||
|
||
### `enableAlpha`: `boolean` | ||
|
||
This controls whether the alpha channel will be offered when selecting | ||
custom colors. | ||
|
||
- Required: No | ||
|
||
### `hideLabelFromVision`: `boolean` | ||
|
||
Provides control over whether the label will only be visible to screen readers. | ||
|
||
- Required: No | ||
|
||
### `label`: `string` | ||
|
||
If provided, a label will be generated using this as the content. | ||
|
||
_Whether it is visible only to screen readers is controlled via | ||
`hideLabelFromVision`._ | ||
|
||
- Required: No | ||
|
||
### `onChange`: `( value: Object | undefined ) => void` | ||
|
||
A callback function invoked when any border value is changed. The value received | ||
may be a "flat" border object, one that has properties defining individual side | ||
borders, or `undefined`. | ||
|
||
_Note: The will be `undefined` if a user clears all borders._ | ||
|
||
- Required: Yes | ||
|
||
### `showStyle`: `boolean` | ||
|
||
This controls whether to support border style selections. | ||
|
||
- Required: No | ||
- Default: `true` | ||
|
||
### `value`: `Object` | ||
|
||
An object representing the current border configuration. | ||
|
||
This may be a "flat" border where the object has `color`, `style`, and `width` | ||
properties or a "split" border which defines the previous properties but for | ||
each side; `top`, `right`, `bottom`, and `left`. | ||
|
||
Examples: | ||
```js | ||
const flatBorder = { color: '#72aee6', style: 'solid', width: '1px' }; | ||
const splitBorders = { | ||
top: { color: '#72aee6', style: 'solid', width: '1px' }, | ||
right: { color: '#e65054', style: 'dashed', width: '2px' }, | ||
bottom: { color: '#68de7c', style: 'solid', width: '1px' }, | ||
left: { color: '#f2d675', style: 'dotted', width: '1em' }, | ||
}; | ||
``` | ||
|
||
- Required: No | ||
|
||
### `__experimentalHasMultipleOrigins`: `boolean` | ||
|
||
This is passed on to the color related sub-components which need to be made | ||
aware of whether the colors prop contains multiple origins. | ||
|
||
- Required: No | ||
|
||
### `__experimentalIsRenderedInSidebar`: `boolean` | ||
|
||
This is passed on to the color related sub-components so they may render more | ||
effectively when used within a sidebar. | ||
|
||
- Required: No |
116 changes: 116 additions & 0 deletions
116
packages/components/src/border-box-control/border-box-control/component.tsx
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,116 @@ | ||
/** | ||
* WordPress dependencies | ||
*/ | ||
import { __ } from '@wordpress/i18n'; | ||
|
||
/** | ||
* Internal dependencies | ||
*/ | ||
import LinkedButton from '../linked-button'; | ||
import SplitBorderControl from '../split-border-control'; | ||
import { BorderControl } from '../../border-control'; | ||
import { HStack } from '../../h-stack'; | ||
import { StyledLabel } from '../../base-control/styles/base-control-styles'; | ||
import { View } from '../../view'; | ||
import { VisuallyHidden } from '../../visually-hidden'; | ||
import { contextConnect, WordPressComponentProps } from '../../ui/context'; | ||
import { useBorderBoxControl } from './hook'; | ||
|
||
import type { BorderBoxControlProps, BorderLabelProps } from '../types'; | ||
|
||
const BorderLabel = ( props: BorderLabelProps ) => { | ||
const { label, hideLabelFromVision } = props; | ||
|
||
if ( ! label ) { | ||
return null; | ||
} | ||
|
||
return hideLabelFromVision ? ( | ||
<VisuallyHidden as="label">{ label }</VisuallyHidden> | ||
) : ( | ||
<StyledLabel>{ label }</StyledLabel> | ||
); | ||
}; | ||
|
||
const BorderBoxControl = ( | ||
props: WordPressComponentProps< BorderBoxControlProps, 'div' >, | ||
forwardedRef: React.Ref< any > | ||
) => { | ||
const { | ||
className, | ||
colors, | ||
disableCustomColors, | ||
enableAlpha, | ||
hasMixedBorders, | ||
hideLabelFromVision, | ||
isLinked, | ||
label, | ||
linkedControlClassName, | ||
linkedValue, | ||
onLinkedChange, | ||
onSplitChange, | ||
showStyle, | ||
splitValue, | ||
toggleLinked, | ||
__experimentalHasMultipleOrigins, | ||
__experimentalIsRenderedInSidebar, | ||
...otherProps | ||
} = useBorderBoxControl( props ); | ||
|
||
return ( | ||
<View className={ className } { ...otherProps } ref={ forwardedRef }> | ||
<BorderLabel | ||
label={ label } | ||
hideLabelFromVision={ hideLabelFromVision } | ||
/> | ||
<HStack alignment={ 'start' } expanded={ true } spacing={ 3 }> | ||
{ isLinked ? ( | ||
<BorderControl | ||
className={ linkedControlClassName } | ||
colors={ colors } | ||
disableCustomColors={ disableCustomColors } | ||
enableAlpha={ enableAlpha } | ||
onChange={ onLinkedChange } | ||
placeholder={ | ||
hasMixedBorders ? __( 'Mixed' ) : undefined | ||
} | ||
shouldSanitizeBorder={ false } // This component will handle that. | ||
showStyle={ showStyle } | ||
value={ linkedValue } | ||
withSlider={ true } | ||
width={ '110px' } | ||
__experimentalHasMultipleOrigins={ | ||
__experimentalHasMultipleOrigins | ||
} | ||
__experimentalIsRenderedInSidebar={ | ||
__experimentalIsRenderedInSidebar | ||
} | ||
/> | ||
) : ( | ||
<SplitBorderControl | ||
colors={ colors } | ||
disableCustomColors={ disableCustomColors } | ||
enableAlpha={ enableAlpha } | ||
onChange={ onSplitChange } | ||
showStyle={ showStyle } | ||
value={ splitValue } | ||
__experimentalHasMultipleOrigins={ | ||
__experimentalHasMultipleOrigins | ||
} | ||
__experimentalIsRenderedInSidebar={ | ||
__experimentalIsRenderedInSidebar | ||
} | ||
/> | ||
) } | ||
<LinkedButton onClick={ toggleLinked } isLinked={ isLinked } /> | ||
</HStack> | ||
</View> | ||
); | ||
}; | ||
|
||
const ConnectedBorderBoxControl = contextConnect( | ||
BorderBoxControl, | ||
'BorderBoxControl' | ||
); | ||
|
||
export default ConnectedBorderBoxControl; |
Oops, something went wrong.