Skip to content

Commit 804e44b

Browse files
ntsekourasoandregaljameskosterfcoveramyouknowriad
authored
DataViews: Add insert left/right in table column header (#72929)
Co-authored-by: ntsekouras <[email protected]> Co-authored-by: oandregal <[email protected]> Co-authored-by: jameskoster <[email protected]> Co-authored-by: fcoveram <[email protected]> Co-authored-by: youknowriad <[email protected]>
1 parent a244310 commit 804e44b

File tree

5 files changed

+115
-16
lines changed

5 files changed

+115
-16
lines changed

packages/dataviews/CHANGELOG.md

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,7 @@
66

77
- Simplify field normalization and types. [#73387](https://github.com/WordPress/gutenberg/pull/73387)
88
- DataViews table layout: make checkboxes permanently visible when bulk actions are available. [#73245](https://github.com/WordPress/gutenberg/pull/73245)
9+
- DataViews: Add insert left/right in table column header. [#72929](https://github.com/WordPress/gutenberg/pull/72929)
910
- DataViews: Make sticky elements (table headers, footer, actions column) inherit background colors from parent container. This allows DataViews instances to seamlessly adapt to containers with custom background colors. [#73240](https://github.com/WordPress/gutenberg/pull/73240)
1011
- DataViews table layout: only apply hover styles when bulk actions are available. [#73248](https://github.com/WordPress/gutenberg/pull/73248)
1112
- DataViews: add support for activity layout. [#72780](https://github.com/WordPress/gutenberg/pull/72780)

packages/dataviews/src/components/dataviews-view-config/properties-section.tsx

Lines changed: 2 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -18,6 +18,7 @@ import { check } from '@wordpress/icons';
1818
*/
1919
import type { NormalizedField } from '../../types';
2020
import DataViewsContext from '../dataviews-context';
21+
import getHideableFields from '../../utils/get-hideable-fields';
2122

2223
function FieldItem( {
2324
field,
@@ -53,19 +54,8 @@ export function PropertiesSection( {
5354
} ) {
5455
const { view, fields, onChangeView } = useContext( DataViewsContext );
5556

56-
const togglableFields = [
57-
view?.titleField,
58-
view?.mediaField,
59-
view?.descriptionField,
60-
].filter( Boolean );
61-
6257
// Get all regular fields (non-locked) in their original order from fields prop
63-
const regularFields = fields.filter(
64-
( f ) =>
65-
! togglableFields.includes( f.id ) &&
66-
f.type !== 'media' &&
67-
f.enableHiding !== false
68-
);
58+
const regularFields = getHideableFields( view, fields );
6959

7060
if ( ! regularFields?.length ) {
7161
return null;

packages/dataviews/src/dataviews-layouts/table/column-header-menu.tsx

Lines changed: 82 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -28,6 +28,7 @@ import type {
2828
Operator,
2929
} from '../../types';
3030
import DataViewsContext from '../../components/dataviews-context';
31+
import getHideableFields from '../../utils/get-hideable-fields';
3132

3233
const { Menu } = unlock( componentsPrivateApis );
3334

@@ -39,6 +40,8 @@ interface HeaderMenuProps< Item > {
3940
onHide: ( field: NormalizedField< Item > ) => void;
4041
setOpenedFilter: ( fieldId: string ) => void;
4142
canMove?: boolean;
43+
canInsertLeft?: boolean;
44+
canInsertRight?: boolean;
4245
}
4346

4447
function WithMenuSeparators( { children }: { children: ReactNode } ) {
@@ -61,6 +64,8 @@ const _HeaderMenu = forwardRef( function HeaderMenu< Item >(
6164
onHide,
6265
setOpenedFilter,
6366
canMove = true,
67+
canInsertLeft = true,
68+
canInsertRight = true,
6469
}: HeaderMenuProps< Item >,
6570
ref: Ref< HTMLButtonElement >
6671
) {
@@ -102,6 +107,12 @@ const _HeaderMenu = forwardRef( function HeaderMenu< Item >(
102107
return header;
103108
}
104109

110+
const hiddenFields = getHideableFields( view, fields ).filter(
111+
( f ) => ! visibleFieldIds.includes( f.id )
112+
);
113+
const canInsert =
114+
( canInsertLeft || canInsertRight ) && !! hiddenFields.length;
115+
105116
return (
106117
<Menu>
107118
<Menu.TriggerButton
@@ -192,7 +203,7 @@ const _HeaderMenu = forwardRef( function HeaderMenu< Item >(
192203
</Menu.Item>
193204
</Menu.Group>
194205
) }
195-
{ ( canMove || isHidable ) && field && (
206+
{ ( canMove || isHidable || canInsert ) && field && (
196207
<Menu.Group>
197208
{ canMove && (
198209
<Menu.Item
@@ -248,6 +259,76 @@ const _HeaderMenu = forwardRef( function HeaderMenu< Item >(
248259
</Menu.ItemLabel>
249260
</Menu.Item>
250261
) }
262+
{ canInsertLeft && !! hiddenFields.length && (
263+
<Menu>
264+
<Menu.SubmenuTriggerItem>
265+
<Menu.ItemLabel>
266+
{ __( 'Insert left' ) }
267+
</Menu.ItemLabel>
268+
</Menu.SubmenuTriggerItem>
269+
<Menu.Popover>
270+
{ hiddenFields.map( ( hiddenField ) => (
271+
<Menu.Item
272+
key={ hiddenField.id }
273+
onClick={ () => {
274+
onChangeView( {
275+
...view,
276+
fields: [
277+
...visibleFieldIds.slice(
278+
0,
279+
index
280+
),
281+
hiddenField.id,
282+
...visibleFieldIds.slice(
283+
index
284+
),
285+
],
286+
} );
287+
} }
288+
>
289+
<Menu.ItemLabel>
290+
{ hiddenField.label }
291+
</Menu.ItemLabel>
292+
</Menu.Item>
293+
) ) }
294+
</Menu.Popover>
295+
</Menu>
296+
) }
297+
{ canInsertRight && !! hiddenFields.length && (
298+
<Menu>
299+
<Menu.SubmenuTriggerItem>
300+
<Menu.ItemLabel>
301+
{ __( 'Insert right' ) }
302+
</Menu.ItemLabel>
303+
</Menu.SubmenuTriggerItem>
304+
<Menu.Popover>
305+
{ hiddenFields.map( ( hiddenField ) => (
306+
<Menu.Item
307+
key={ hiddenField.id }
308+
onClick={ () => {
309+
onChangeView( {
310+
...view,
311+
fields: [
312+
...visibleFieldIds.slice(
313+
0,
314+
index + 1
315+
),
316+
hiddenField.id,
317+
...visibleFieldIds.slice(
318+
index + 1
319+
),
320+
],
321+
} );
322+
} }
323+
>
324+
<Menu.ItemLabel>
325+
{ hiddenField.label }
326+
</Menu.ItemLabel>
327+
</Menu.Item>
328+
) ) }
329+
</Menu.Popover>
330+
</Menu>
331+
) }
251332
{ isHidable && field && (
252333
<Menu.Item
253334
prefix={ <Icon icon={ unseen } /> }

packages/dataviews/src/dataviews-layouts/table/index.tsx

Lines changed: 9 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -458,6 +458,10 @@ function ViewTable< Item >( {
458458
onHide={ onHide }
459459
setOpenedFilter={ setOpenedFilter }
460460
canMove={ false }
461+
canInsertLeft={ false }
462+
canInsertRight={
463+
view.layout?.enableMoving ?? true
464+
}
461465
/>
462466
) }
463467
</th>
@@ -466,6 +470,8 @@ function ViewTable< Item >( {
466470
// Explicit picks the supported styles.
467471
const { width, maxWidth, minWidth, align } =
468472
view.layout?.styles?.[ column ] ?? {};
473+
const canInsertOrMove =
474+
view.layout?.enableMoving ?? true;
469475
return (
470476
<th
471477
key={ column }
@@ -491,9 +497,9 @@ function ViewTable< Item >( {
491497
onChangeView={ onChangeView }
492498
onHide={ onHide }
493499
setOpenedFilter={ setOpenedFilter }
494-
canMove={
495-
view.layout?.enableMoving ?? true
496-
}
500+
canMove={ canInsertOrMove }
501+
canInsertLeft={ canInsertOrMove }
502+
canInsertRight={ canInsertOrMove }
497503
/>
498504
</th>
499505
);
Lines changed: 21 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,21 @@
1+
/**
2+
* Internal dependencies
3+
*/
4+
import type { NormalizedField, View } from '../types';
5+
6+
export default function getHideableFields< Item >(
7+
view: View,
8+
fields: NormalizedField< Item >[]
9+
): NormalizedField< Item >[] {
10+
const togglableFields = [
11+
view?.titleField,
12+
view?.mediaField,
13+
view?.descriptionField,
14+
].filter( Boolean );
15+
return fields.filter(
16+
( f ) =>
17+
! togglableFields.includes( f.id ) &&
18+
f.type !== 'media' &&
19+
f.enableHiding !== false
20+
);
21+
}

0 commit comments

Comments
 (0)