-
Notifications
You must be signed in to change notification settings - Fork 4.2k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Refactor heading block to share more code with web version. #20745
Changes from 9 commits
a17a5c6
b4e84f9
28350f5
d8fb1e8
bebc055
2f21f8b
733f4f6
d6aedfa
3ec775c
2d57fe2
0988634
5050d3d
3d7e007
507f972
bc3ca73
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,10 @@ | ||
const TextColor = ( props ) => <>{ props.children }</>; | ||
|
||
const InspectorControlsColorPanel = () => null; | ||
|
||
export default function __experimentalUseColors() { | ||
return { | ||
TextColor, | ||
InspectorControlsColorPanel, | ||
}; | ||
} |
This file was deleted.
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,5 +1,173 @@ | ||
function DropdownMenu() { | ||
return null; | ||
/** | ||
* External dependencies | ||
*/ | ||
import classnames from 'classnames'; | ||
import { flatMap, isEmpty, isFunction } from 'lodash'; | ||
/** | ||
* WordPress dependencies | ||
*/ | ||
import { DOWN } from '@wordpress/keycodes'; | ||
import deprecated from '@wordpress/deprecated'; | ||
import { BottomSheet, PanelBody } from '@wordpress/components'; | ||
import { withPreferredColorScheme } from '@wordpress/compose'; | ||
|
||
/** | ||
* Internal dependencies | ||
*/ | ||
import Button from '../button'; | ||
import Dropdown from '../dropdown'; | ||
|
||
function mergeProps( defaultProps = {}, props = {} ) { | ||
const mergedProps = { | ||
...defaultProps, | ||
...props, | ||
}; | ||
|
||
if ( props.className && defaultProps.className ) { | ||
mergedProps.className = classnames( | ||
props.className, | ||
defaultProps.className | ||
); | ||
} | ||
|
||
return mergedProps; | ||
} | ||
|
||
function DropdownMenu( { | ||
children, | ||
className, | ||
controls, | ||
icon = 'menu', | ||
label, | ||
popoverProps, | ||
toggleProps, | ||
// The following props exist for backward compatibility. | ||
menuLabel, | ||
position, | ||
} ) { | ||
if ( menuLabel ) { | ||
deprecated( '`menuLabel` prop in `DropdownComponent`', { | ||
alternative: '`menuProps` object and its `aria-label` property', | ||
plugin: 'Gutenberg', | ||
} ); | ||
} | ||
|
||
if ( position ) { | ||
deprecated( '`position` prop in `DropdownComponent`', { | ||
alternative: '`popoverProps` object and its `position` property', | ||
plugin: 'Gutenberg', | ||
} ); | ||
} | ||
|
||
if ( isEmpty( controls ) && ! isFunction( children ) ) { | ||
return null; | ||
} | ||
|
||
// Normalize controls to nested array of objects (sets of controls) | ||
let controlSets; | ||
if ( ! isEmpty( controls ) ) { | ||
controlSets = controls; | ||
if ( ! Array.isArray( controlSets[ 0 ] ) ) { | ||
controlSets = [ controlSets ]; | ||
} | ||
} | ||
const mergedPopoverProps = mergeProps( | ||
{ | ||
className: 'components-dropdown-menu__popover', | ||
position, | ||
}, | ||
popoverProps | ||
); | ||
|
||
return ( | ||
<Dropdown | ||
className={ classnames( 'components-dropdown-menu', className ) } | ||
popoverProps={ mergedPopoverProps } | ||
renderToggle={ ( { isOpen, onToggle } ) => { | ||
const openOnArrowDown = ( event ) => { | ||
if ( ! isOpen && event.keyCode === DOWN ) { | ||
event.preventDefault(); | ||
event.stopPropagation(); | ||
onToggle(); | ||
} | ||
}; | ||
const mergedToggleProps = mergeProps( | ||
{ | ||
className: classnames( | ||
'components-dropdown-menu__toggle', | ||
{ | ||
'is-opened': isOpen, | ||
} | ||
), | ||
}, | ||
toggleProps | ||
); | ||
|
||
return ( | ||
<Button | ||
{ ...mergedToggleProps } | ||
icon={ icon } | ||
onClick={ ( event ) => { | ||
onToggle( event ); | ||
if ( mergedToggleProps.onClick ) { | ||
mergedToggleProps.onClick( event ); | ||
} | ||
} } | ||
onKeyDown={ ( event ) => { | ||
openOnArrowDown( event ); | ||
if ( mergedToggleProps.onKeyDown ) { | ||
mergedToggleProps.onKeyDown( event ); | ||
} | ||
} } | ||
aria-haspopup="true" | ||
aria-expanded={ isOpen } | ||
label={ label } | ||
showTooltip | ||
> | ||
{ mergedToggleProps.children } | ||
</Button> | ||
); | ||
} } | ||
renderContent={ ( { isOpen, onClose, ...props } ) => { | ||
return ( | ||
SergioEstevao marked this conversation as resolved.
Show resolved
Hide resolved
|
||
<BottomSheet | ||
hideHeader={ true } | ||
isVisible={ isOpen } | ||
onClose={ onClose } | ||
> | ||
{ isFunction( children ) ? children( props ) : null } | ||
<PanelBody title={ label }> | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Could we use the Picker component to reuse functionality? (packages/components/src/mobile/picker/) There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. The Picker is using an ActionSheet in iOS that doesn't translate to the interface we want here. There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Oh, I thought we wanted the ActionSheet on iOS based on @iamthomasbishop 's comment. Still, as this layout is already in place somewhere else, maybe we could add a prop to the picker component, something like |
||
{ flatMap( | ||
controlSets, | ||
( controlSet, indexOfSet ) => | ||
controlSet.map( | ||
( control, indexOfControl ) => ( | ||
<BottomSheet.Cell | ||
key={ [ | ||
indexOfSet, | ||
indexOfControl, | ||
].join() } | ||
label={ control.title } | ||
onPress={ () => { | ||
onClose(); | ||
if ( control.onClick ) { | ||
control.onClick(); | ||
} | ||
} } | ||
editable={ false } | ||
icon={ control.icon } | ||
leftAlign={ true } | ||
isSelected={ control.isActive } | ||
/> | ||
) | ||
) | ||
) } | ||
</PanelBody> | ||
</BottomSheet> | ||
); | ||
} } | ||
/> | ||
); | ||
} | ||
|
||
export default DropdownMenu; | ||
export default withPreferredColorScheme( DropdownMenu ); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This is the only thing that's bothering me, in this PR. It's redundunt with the style prop in the web and it can easily get removed since it's not used at all in the web version.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This is a recurrent issue we have on the mobile implementations. We don't have access to CSS so we end up recurring to extra props or container classes to do the work that CSS does. I'm all open to suggestions on how can we avoid these issues.
@mtias told me there is some approach being discussed about Global Styling approach using props for the components that could be a way to make the implementation less dependent of CSS styling.