Skip to content
Merged
Original file line number Diff line number Diff line change
Expand Up @@ -16,8 +16,17 @@ export default function useNavigateToEntityRecord() {

const onNavigateToEntityRecord = useCallback(
( params ) => {
const { focusMode = true, ...navigationParams } = params;
const queryParams = [ 'canvas=edit' ];

if ( focusMode ) {
queryParams.push( 'focusMode=true' );
}

history.navigate(
`/${ params.postType }/${ params.postId }?canvas=edit&focusMode=true`
`/${ navigationParams.postType }/${
navigationParams.postId
}?${ queryParams.join( '&' ) }`
);
},
[ history ]
Expand Down
1 change: 1 addition & 0 deletions packages/editor/src/hooks/index.js
Original file line number Diff line number Diff line change
Expand Up @@ -5,3 +5,4 @@ import './custom-sources-backwards-compatibility';
import './default-autocompleters';
import './media-upload';
import './pattern-overrides';
import './navigation-link-view-button';
87 changes: 87 additions & 0 deletions packages/editor/src/hooks/navigation-link-view-button.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,87 @@
/**
* WordPress dependencies
*/
import { addFilter } from '@wordpress/hooks';
import { createHigherOrderComponent } from '@wordpress/compose';
import { useCallback } from '@wordpress/element';
import { __ } from '@wordpress/i18n';
import {
__unstableBlockToolbarLastItem as BlockToolbarLastItem,
store as blockEditorStore,
} from '@wordpress/block-editor';
import { ToolbarButton, ToolbarGroup } from '@wordpress/components';
import { useSelect } from '@wordpress/data';

// Target blocks that should have the View button
const SUPPORTED_BLOCKS = [ 'core/navigation-link', 'core/navigation-submenu' ];

/**
* Component that renders the View button for navigation blocks
*
* @param {Object} props Component props.
* @param {Object} props.attributes Block attributes.
*/
function NavigationViewButton( { attributes } ) {
const { kind, id, type } = attributes;

const onNavigateToEntityRecord = useSelect(
( select ) =>
select( blockEditorStore ).getSettings().onNavigateToEntityRecord,
[]
);

const onViewPage = useCallback( () => {
if ( kind === 'post-type' && type === 'page' && id ) {
onNavigateToEntityRecord( {
postId: id,
postType: type,
focusMode: false,
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

While switching focusMode to false is good for ensuring we land in the editor with the page extending to the edges of the canvas, this appears to remove the Back button in the DocumentBar. It would usually show here:

image

I think it'd be great if we can (somehow) preserve that so that it's easy for users to get back to the template they were editing.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I wasn't sure whether we'd want that border around the content which is why I added the ability to conditionalise focusMode. I think it's worth considering but I'd say this is a call for @richtabor.

Rich using @andrewserong's screen grab as a guide would you be happy for clicking View to take you to the page in that mode (i.e. with a back button and the border around the content)? Or would you prefer the experience currently in this PR (i.e. no back button and no border)?

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I wasn't sure whether we'd want that border around the content which is why I added the ability to conditionalise focusMode.

I think avoiding the border we get from focusMode was the right call, so I don't mind it being set to false here. The main question I have (and this is also my naivety as to how the Back button works) is whether we can also somehow get the Back button working while not in focusMode 🤔

Not necessarily a blocker to figure out, either, if folks are happy with how this PR is behaving — we could always look into how to add in the Back button behaviour separately if it proves tricky.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The main question I have (and this is also my naivety as to how the Back button works) is whether we can also somehow get the Back button working while not in focusMode 🤔

Here is where Back is set

const isFocusMode =
location.query.focusMode ||
( location?.params?.postId &&
FOCUSABLE_ENTITIES.includes( location?.params?.postType ) );
const didComeFromEditorCanvas =
previousLocation?.query.canvas === 'edit';
const showBackButton = isFocusMode && didComeFromEditorCanvas;

The Back button appears in focus mode when you've navigated from the main editor canvas (canvas=edit) to a focused entity. It's controlled by URL parameters and browser history.

I think the Back button is pretty important so I'm going to remove the changes I made and allow it to land with the border.

However, we'll probably want to invent some new mechanic that allows for the Back button to appear in non-focus contexts.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

However, we'll probably want to invent some new mechanic that allows for the Back button to appear in non-focus contexts.

Agreed — currently if you're viewing a page within focus mode there's a couple of other peculiarities, for example if you select to "Show template" from within focus mode while iewing a page, then the Back button in the DocumentBar will overlap with the template icon. But that's something to fix in the DocumentBar component, I believe:

image

It'd be nice to have a param we can set that enables navigating back without the focus mode border, so we'll wind up needing to fix that DocumentBar issue anyway.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

For fixing up the DocumentBar and overlapping Back button, I've opened up: #71183

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Tiny update: I've merged #71183, so the DocumentBar will be fixed once this is either rebased or merged.

} );
}
}, [ kind, id, type, onNavigateToEntityRecord ] );

// Only show for page-type links
if ( kind !== 'post-type' || type !== 'page' || ! id ) {
return null;
}

return (
<BlockToolbarLastItem>
<ToolbarGroup>
<ToolbarButton
name="view"
title={ __( 'View' ) }
onClick={ onViewPage }
>
{ __( 'View' ) }
</ToolbarButton>
</ToolbarGroup>
</BlockToolbarLastItem>
);
}

/**
* Higher-order component that adds the View button to navigation blocks
*/
const withNavigationViewButton = createHigherOrderComponent(
( BlockEdit ) => ( props ) => {
const isSupportedBlock = SUPPORTED_BLOCKS.includes( props.name );

return (
<>
<BlockEdit key="edit" { ...props } />
{ props.isSelected && isSupportedBlock && (
<NavigationViewButton { ...props } />
) }
</>
);
},
'withNavigationViewButton'
);

// Register the filter
addFilter(
'editor.BlockEdit',
'core/editor/with-navigation-view-button',
withNavigationViewButton
);
Loading