Skip to content
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

Site Editor: Add navigation panel with placeholder content #25506

Merged
merged 18 commits into from
Sep 24, 2020
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
74 changes: 34 additions & 40 deletions packages/edit-site/src/components/editor/index.js
Original file line number Diff line number Diff line change
Expand Up @@ -17,9 +17,7 @@ import {
BlockBreadcrumb,
__unstableEditorStyles as EditorStyles,
__experimentalUseResizeCanvas as useResizeCanvas,
__experimentalLibrary as Library,
} from '@wordpress/block-editor';
import { useViewportMatch } from '@wordpress/compose';
import {
FullscreenMode,
InterfaceSkeleton,
Expand All @@ -28,7 +26,6 @@ import {
import { EntitiesSavedStates, UnsavedChangesWarning } from '@wordpress/editor';
import { __ } from '@wordpress/i18n';
import { PluginArea } from '@wordpress/plugins';
import { close } from '@wordpress/icons';

/**
* Internal dependencies
Expand All @@ -39,14 +36,14 @@ import { SidebarComplementaryAreaFills } from '../sidebar';
import BlockEditor from '../block-editor';
import KeyboardShortcuts from '../keyboard-shortcuts';
import GlobalStylesProvider from './global-styles-provider';
import LeftSidebar from '../left-sidebar';

const interfaceLabels = {
leftSidebar: __( 'Block Library' ),
};

function Editor() {
const [ isInserterOpen, setIsInserterOpen ] = useState( false );
const isMobile = useViewportMatch( 'medium', '<' );
const [ leftSidebarContent, setLeftSidebarContent ] = useState( null );

const {
isFullscreenActive,
Expand Down Expand Up @@ -156,6 +153,9 @@ function Editor() {
[ page?.context ]
);

const toggleLeftSidebarContent = ( value ) =>
setLeftSidebarContent( leftSidebarContent === value ? null : value );

return (
<>
<EditorStyles styles={ settings.styles } />
Expand Down Expand Up @@ -191,36 +191,14 @@ function Editor() {
<InterfaceSkeleton
labels={ interfaceLabels }
leftSidebar={
isInserterOpen && (
<div className="edit-site-editor__inserter-panel">
<div className="edit-site-editor__inserter-panel-header">
<Button
icon={
close
}
onClick={ () =>
setIsInserterOpen(
false
)
}
/>
</div>
<div className="edit-site-editor__inserter-panel-content">
<Library
showInserterHelpPanel
onSelect={ () => {
if (
isMobile
) {
setIsInserterOpen(
false
);
}
} }
/>
</div>
</div>
)
<LeftSidebar
content={
leftSidebarContent
}
setContent={
setLeftSidebarContent
}
/>
}
sidebar={
sidebarIsOpened && (
Expand All @@ -233,11 +211,21 @@ function Editor() {
openEntitiesSavedStates
}
isInserterOpen={
isInserterOpen
leftSidebarContent ===
'inserter'
}
onToggleInserter={ () =>
setIsInserterOpen(
! isInserterOpen
toggleLeftSidebarContent(
'inserter'
)
}
isNavigationOpen={
leftSidebarContent ===
'navigation'
}
onToggleNavigation={ () =>
toggleLeftSidebarContent(
'navigation'
)
}
/>
Expand All @@ -251,8 +239,14 @@ function Editor() {
<Popover.Slot name="block-toolbar" />
{ template && (
<BlockEditor
setIsInserterOpen={
setIsInserterOpen
setIsInserterOpen={ (
isInserterOpen
) =>
setLeftSidebarContent(
isInserterOpen
? 'inserter'
: null
)
}
/>
) }
Expand Down
26 changes: 0 additions & 26 deletions packages/edit-site/src/components/editor/style.scss
Original file line number Diff line number Diff line change
Expand Up @@ -25,29 +25,3 @@
.edit-site-visual-editor {
background-color: $white;
}

.edit-site-editor__inserter-panel {
height: 100%;
display: flex;
flex-direction: column;
}

.edit-site-editor__inserter-panel-header {
padding-top: $grid-unit-10;
padding-right: $grid-unit-10;
display: flex;
justify-content: flex-end;

@include break-medium() {
display: none;
}
}

.edit-site-editor__inserter-panel-content {
// Leave space for the close button
height: calc(100% - #{$button-size} - #{$grid-unit-10});

@include break-medium() {
height: 100%;
}
}
9 changes: 7 additions & 2 deletions packages/edit-site/src/components/header/index.js
Original file line number Diff line number Diff line change
Expand Up @@ -26,13 +26,15 @@ import TemplateSwitcher from '../template-switcher';
import SaveButton from '../save-button';
import UndoButton from './undo-redo/undo';
import RedoButton from './undo-redo/redo';
import FullscreenModeClose from './fullscreen-mode-close';
import DocumentActions from './document-actions';
import NavigationToggle from './navigation-toggle';

export default function Header( {
openEntitiesSavedStates,
isInserterOpen,
onToggleInserter,
isNavigationOpen,
onToggleNavigation,
} ) {
const {
deviceType,
Expand Down Expand Up @@ -89,7 +91,10 @@ export default function Header( {
<div className="edit-site-header">
<div className="edit-site-header_start">
<MainDashboardButton.Slot>
<FullscreenModeClose />
Copy link
Member

Choose a reason for hiding this comment

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

This button is exported from the package (experimental for now) and provides a way for 3rd plugins to customize some of its parts while retaining functionality (see docs here). Given that it will no longer represent a close action, I think that we should rename the existing FullscreenModeClose to NavigationButton or DashboardButton and place our code changes there.

Copy link
Contributor

Choose a reason for hiding this comment

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

We should also figure out how to handle the FSE Navigation when not in fullscreen mode, where we wouldn't have the WP/Site Icon back button anymore.

Copy link
Member

Choose a reason for hiding this comment

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

Good point @Copons! I don't consider it a blocker for this PR though, as it's something that we can figure out later.

<NavigationToggle
isOpen={ isNavigationOpen }
onClick={ onToggleNavigation }
/>
Copy link
Contributor

Choose a reason for hiding this comment

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

I've got a few doubts about this change.
While it's true that this button doesn't close fullscreen mode anymore, it also doesn't navigate back to the dashboard (so the "Open dashboard" label in the component is misleading) — and it's not even technically just a button 😄.

What it does now is to toggle the navigation sidebar, so I'd be more inclined in calling it NavigationPanelToggle.


I think we could also keep FullscreenModeClose.
While it would be left unused in this PR, we could update it to become (be?) the actual "dashboard button".
Consumers relying on it would not break, and we could use it inside the navigation toggle, or in the navigation itself (or wherever we see fit).

Either way, my opinion is that we should probably avoid removing existing components from an experimental PR whose purpose is to be a starting point, and not the finished product.

Copy link
Member

Choose a reason for hiding this comment

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

I agree that that name is more appropriate. Also no objections to keeping the FullscreenModeClose if we are going to repurpose it and include it in navigation.

Copy link
Contributor

@Copons Copons Sep 23, 2020

Choose a reason for hiding this comment

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

My point is also that the navigation sidebar is still in flux, and I'm not super keen on removing an established component (albeit experimental).
We might end up not using it, or heavily modifying it, but let's care about that when we'll be actually working on the back navigation. 🙂

Copy link
Member Author

Choose a reason for hiding this comment

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

  • Renamed DashboardButton to NavigationToggle
  • Reverted FullscreenModeClose component, let's keep it for now and we will iterate upon it

</MainDashboardButton.Slot>
<div className="edit-site-header__toolbar">
<Button
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,78 @@
/**
* WordPress dependencies
*/
import { useSelect } from '@wordpress/data';
import { Button, Icon } from '@wordpress/components';
import { __ } from '@wordpress/i18n';
import { wordpress } from '@wordpress/icons';

function NavigationToggle( { icon, isOpen, onClick } ) {
const {
isActive,
isRequestingSiteIcon,
siteIconUrl,
siteTitle,
} = useSelect( ( select ) => {
const { isFeatureActive } = select( 'core/edit-site' );
const { getEntityRecord } = select( 'core' );
const { isResolving } = select( 'core/data' );
const siteData =
getEntityRecord( 'root', '__unstableBase', undefined ) || {};

return {
isActive: isFeatureActive( 'fullscreenMode' ),
isRequestingSiteIcon: isResolving( 'core', 'getEntityRecord', [
'root',
'__unstableBase',
undefined,
] ),
siteIconUrl: siteData.site_icon_url,
siteTitle: siteData.name,
};
}, [] );

if ( ! isActive ) {
return null;
}

let buttonIcon = <Icon size="32px" icon={ wordpress } />;

if ( siteIconUrl ) {
buttonIcon = (
<img
alt={ __( 'Site Icon' ) }
className="edit-site-navigation-toggle__site-icon"
src={ siteIconUrl }
/>
);
} else if ( isRequestingSiteIcon ) {
buttonIcon = null;
} else if ( icon ) {
buttonIcon = <Icon size="32px" icon={ icon } />;
}

return (
<div
className={
'edit-site-navigation-toggle' + ( isOpen ? ' is-open' : '' )
}
>
<Button
className="edit-site-navigation-toggle__button has-icon"
label={ __( 'Toggle navigation' ) }
onClick={ onClick }
showTooltip
>
{ buttonIcon }
</Button>

{ isOpen && (
<div className="edit-site-navigation-toggle__site-title">
{ siteTitle }
</div>
) }
</div>
);
}

export default NavigationToggle;
Original file line number Diff line number Diff line change
@@ -0,0 +1,47 @@
.edit-site-navigation-toggle {
display: none;

@include break-medium() {
display: flex;
align-items: center;
background-color: #1e1e1e;
height: 61px;
border-radius: 0;
}
}

.edit-site-navigation-toggle.is-open {
width: 300px;
}

.edit-site-navigation-toggle__button {
color: #fff;
margin-left: 14px;
margin-right: 14px;

&:hover {
color: #ddd;
}
}

.edit-site-navigation-toggle.components-button.has-icon {
justify-content: flex-start;
padding: 0;
height: 32px;
width: 32px;
min-width: 32px;
}

.edit-site-navigation-toggle__site-title {
font-style: normal;
font-weight: 600;
font-size: 13px;
line-height: 16px;
color: #ddd;
margin-right: 14px;

display: -webkit-box;
-webkit-line-clamp: 2;
-webkit-box-orient: vertical;
overflow: hidden;
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,66 @@
/**
* External dependencies
*/
import { render } from '@testing-library/react';

/**
* WordPress dependencies
*/
import { useSelect } from '@wordpress/data';

/**
* Internal dependencies
*/
import NavigationToggle from '..';

jest.mock( '@wordpress/data/src/components/use-select', () => {
// This allows us to tweak the returned value on each test
const mock = jest.fn();
return mock;
} );

jest.mock( '@wordpress/core-data' );

describe( 'NavigationToggle', () => {
describe( 'when in full screen mode', () => {
it( 'should display a user uploaded site icon if it exists', () => {
useSelect.mockImplementation( ( cb ) => {
return cb( () => ( {
isResolving: () => false,
isFeatureActive: () => true,
getEntityRecord: () => ( {
site_icon_url: 'https://fakeUrl.com',
} ),
} ) );
} );

const { container } = render( <NavigationToggle /> );
const siteIcon = container.querySelector(
'.edit-site-navigation-toggle__site-icon'
);

expect( siteIcon ).toBeTruthy();
} );

it( 'should display a default site icon if no user uploaded site icon exists', () => {
useSelect.mockImplementation( ( cb ) => {
return cb( () => ( {
isResolving: () => false,
isFeatureActive: () => true,
getEntityRecord: () => ( {
site_icon_url: '',
} ),
} ) );
} );

const { container } = render( <NavigationToggle /> );
const siteIcon = container.querySelector(
'.edit-site-navigation-toggle__site-icon'
);
const defaultIcon = container.querySelector( 'svg' );

expect( siteIcon ).toBeFalsy();
expect( defaultIcon ).toBeTruthy();
} );
} );
} );
Loading