From 5482398e79ec20f93363db3b048f8b09dde01e97 Mon Sep 17 00:00:00 2001 From: Riad Benguella Date: Mon, 19 Aug 2019 17:35:41 +0100 Subject: [PATCH] Add a help panel to the inserter available in all blocks (#16813) --- packages/block-editor/README.md | 1 + .../src/components/block-card/index.js | 18 ++ .../src/components/block-card/style.scss | 34 +++ .../src/components/block-inspector/index.js | 10 +- .../src/components/block-inspector/style.scss | 38 ---- .../src/components/block-preview/index.js | 18 +- .../src/components/block-preview/style.scss | 41 +--- .../components/inserter-list-item/style.scss | 4 +- .../src/components/inserter/menu.js | 215 +++++++++++------- .../src/components/inserter/style.scss | 79 ++++++- packages/block-editor/src/store/defaults.js | 2 + packages/block-editor/src/style.scss | 1 + packages/components/src/index.js | 1 + packages/components/src/style.scss | 1 + packages/components/src/tip/index.js | 17 ++ packages/components/src/tip/style.scss | 15 ++ packages/e2e-tests/specs/editor-modes.test.js | 2 +- .../src/components/options-modal/index.js | 2 + .../options-modal/options/enable-feature.js | 24 ++ .../components/options-modal/options/index.js | 1 + .../test/__snapshots__/index.js.snap | 4 + packages/edit-post/src/editor.js | 5 + packages/edit-post/src/store/defaults.js | 1 + .../editor/src/components/provider/index.js | 1 + 24 files changed, 345 insertions(+), 190 deletions(-) create mode 100644 packages/block-editor/src/components/block-card/index.js create mode 100644 packages/block-editor/src/components/block-card/style.scss create mode 100644 packages/components/src/tip/index.js create mode 100644 packages/components/src/tip/style.scss create mode 100644 packages/edit-post/src/components/options-modal/options/enable-feature.js diff --git a/packages/block-editor/README.md b/packages/block-editor/README.md index 1d230d45fc3a2..a5a5ed24f0014 100644 --- a/packages/block-editor/README.md +++ b/packages/block-editor/README.md @@ -387,6 +387,7 @@ The default editor settings bodyPlaceholder string Empty post placeholder titlePlaceholder string Empty title placeholder codeEditingEnabled string Whether or not the user can switch to the code editor + showInserterHelpPanel boolean Whether or not the inserter help panel is shown **experimentalCanUserUseUnfilteredHTML string Whether the user should be able to use unfiltered HTML or the HTML should be filtered e.g., to remove elements considered insecure like iframes. **experimentalEnableLegacyWidgetBlock boolean Whether the user has enabled the Legacy Widget Block \_\_experimentalEnableMenuBlock boolean Whether the user has enabled the Menu Block diff --git a/packages/block-editor/src/components/block-card/index.js b/packages/block-editor/src/components/block-card/index.js new file mode 100644 index 0000000000000..f060612622804 --- /dev/null +++ b/packages/block-editor/src/components/block-card/index.js @@ -0,0 +1,18 @@ +/** + * Internal dependencies + */ +import BlockIcon from '../block-icon'; + +function BlockCard( { blockType } ) { + return ( +
+ +
+
{ blockType.title }
+
{ blockType.description }
+
+
+ ); +} + +export default BlockCard; diff --git a/packages/block-editor/src/components/block-card/style.scss b/packages/block-editor/src/components/block-card/style.scss new file mode 100644 index 0000000000000..6ac54020dd80a --- /dev/null +++ b/packages/block-editor/src/components/block-card/style.scss @@ -0,0 +1,34 @@ + +.block-editor-block-card { + display: flex; + align-items: flex-start; +} + +.block-editor-block-card__icon { + border: $border-width solid $light-gray-700; + padding: 7px; + margin-right: 10px; + height: 36px; + width: 36px; +} + +.block-editor-block-card__content { + flex-grow: 1; +} + +.block-editor-block-card__title { + font-weight: 500; + margin-bottom: 5px; +} + +.block-editor-block-card__description { + font-size: $default-font-size; +} + +.block-editor-block-card .block-editor-block-icon { + margin-left: -2px; + margin-right: 10px; + padding: 0 3px; + width: $icon-button-size; + height: $icon-button-size-small; +} diff --git a/packages/block-editor/src/components/block-inspector/index.js b/packages/block-editor/src/components/block-inspector/index.js index e04dbcbd932be..ea18d7838cca4 100644 --- a/packages/block-editor/src/components/block-inspector/index.js +++ b/packages/block-editor/src/components/block-inspector/index.js @@ -15,7 +15,7 @@ import { withSelect } from '@wordpress/data'; * Internal dependencies */ import SkipToSelectedBlock from '../skip-to-selected-block'; -import BlockIcon from '../block-icon'; +import BlockCard from '../block-card'; import InspectorControls from '../inspector-controls'; import InspectorAdvancedControls from '../inspector-advanced-controls'; import BlockStyles from '../block-styles'; @@ -51,13 +51,7 @@ const BlockInspector = ( { return ( <> -
- -
-
{ blockType.title }
-
{ blockType.description }
-
-
+ { hasBlockStyles && (
scaledElementRect.height * scale ) ? ( containerElementRect.height - ( scaledElementRect.height * scale ) ) / 2 : 0; - setIsTallPreview( scaledElementRect.height * scale > containerElementRect.height ); setPreviewScale( scale ); setPosition( { x: offsetX * scale, y: offsetY } ); @@ -60,7 +58,6 @@ function ScaledBlockPreview( { blocks, viewportWidth } ) { } else { const containerElementRect = containerElement.getBoundingClientRect(); setPreviewScale( containerElementRect.width / viewportWidth ); - setIsTallPreview( true ); } setIsReady( true ); @@ -86,14 +83,15 @@ function ScaledBlockPreview( { blocks, viewportWidth } ) { width: viewportWidth, }; - const contentClassNames = classnames( 'block-editor-block-preview__content editor-styles-wrapper', { - 'is-tall-preview': isTallPreview, - 'is-ready': isReady, - } ); - return ( -
- +
+
diff --git a/packages/block-editor/src/components/block-preview/style.scss b/packages/block-editor/src/components/block-preview/style.scss index 76c2f4ccaf10a..2316de61a8355 100644 --- a/packages/block-editor/src/components/block-preview/style.scss +++ b/packages/block-editor/src/components/block-preview/style.scss @@ -1,35 +1,3 @@ -// This is the preview that shows up to the right of the thumbnail when hovering. -.block-editor-block-switcher__preview { - padding: $block-padding; - font-family: $editor-font; - overflow: hidden; - width: 100%; - pointer-events: none; - display: none; - - @include break-medium { - display: block; - } - - .block-editor-block-preview__content { - font-family: $editor-font; - - > div { - font-family: $editor-font; - } - - &:not(.is-tall-preview) { - // Vertical alignment. - margin-top: 50%; - } - } - - .block-editor-block-preview__title { - margin-bottom: 10px; - color: $dark-gray-300; - } -} - // These rules ensure the preview scales smoothly regardless of the container size. .block-editor-block-preview__container { // In the component, a top padding is provided as an inline style to provid an aspect-ratio. @@ -39,6 +7,11 @@ // The preview component measures the pixel width of this item, so as to calculate the scale factor. // But without this baseline width, it collapses to 0. width: 100%; + + overflow: hidden; + &.is-ready { + overflow: visible; + } } .block-editor-block-preview__content { @@ -74,10 +47,6 @@ height: auto; } - &.is-tall-preview { - top: 4px; - } - .block-editor-block-list__insertion-point, .block-editor-block-drop-zone, .reusable-block-indicator, diff --git a/packages/block-editor/src/components/inserter-list-item/style.scss b/packages/block-editor/src/components/inserter-list-item/style.scss index d99f818f6f0a4..8dc8b8084ad4f 100644 --- a/packages/block-editor/src/components/inserter-list-item/style.scss +++ b/packages/block-editor/src/components/inserter-list-item/style.scss @@ -1,7 +1,7 @@ .block-editor-block-types-list__list-item { display: block; width: 33.33%; - padding: 0 4px; + padding: 0; margin: 0 0 12px; } @@ -11,7 +11,7 @@ width: 100%; font-size: $default-font-size; color: $dark-gray-700; - padding: 0; + padding: 0 4px; align-items: stretch; justify-content: center; cursor: pointer; diff --git a/packages/block-editor/src/components/inserter/menu.js b/packages/block-editor/src/components/inserter/menu.js index 0b5f47c68af25..6714a27f6c69d 100644 --- a/packages/block-editor/src/components/inserter/menu.js +++ b/packages/block-editor/src/components/inserter/menu.js @@ -16,18 +16,24 @@ import { deburr, } from 'lodash'; import scrollIntoView from 'dom-scroll-into-view'; +import classnames from 'classnames'; /** * WordPress dependencies */ import { __, _n, _x, sprintf } from '@wordpress/i18n'; import { Component, createRef } from '@wordpress/element'; -import { withSpokenMessages, PanelBody } from '@wordpress/components'; +import { + PanelBody, + withSpokenMessages, + Tip, +} from '@wordpress/components'; import { getCategories, isReusableBlock, createBlock, isUnmodifiedDefaultBlock, + getBlockType, } from '@wordpress/blocks'; import { withDispatch, withSelect } from '@wordpress/data'; import { withInstanceId, compose, withSafeTimeout } from '@wordpress/compose'; @@ -39,6 +45,7 @@ import { addQueryArgs } from '@wordpress/url'; */ import BlockPreview from '../block-preview'; import BlockTypesList from '../block-types-list'; +import BlockCard from '../block-card'; import ChildBlocks from './child-blocks'; const MAX_SUGGESTED_ITEMS = 9; @@ -246,7 +253,7 @@ export class InserterMenu extends Component { } render() { - const { instanceId, onSelect, rootClientId } = this.props; + const { instanceId, onSelect, rootClientId, showInserterHelpPanel } = this.props; const { childItems, hoveredItem, @@ -265,99 +272,139 @@ export class InserterMenu extends Component { /* eslint-disable jsx-a11y/no-autofocus, jsx-a11y/no-static-element-interactions */ return (
- - - -
- - + + - { !! suggestedItems.length && - - - - } - - { map( getCategories(), ( category ) => { - const categoryItems = itemsPerCategory[ category.slug ]; - if ( ! categoryItems || ! categoryItems.length ) { - return null; - } - return ( +
+ + + + { !! suggestedItems.length && - + - ); - } ) } - - { !! reusableItems.length && ( - - - { + const categoryItems = itemsPerCategory[ category.slug ]; + if ( ! categoryItems || ! categoryItems.length ) { + return null; + } + return ( + + + + ); + } ) } + + { !! reusableItems.length && ( + - { __( 'Manage All Reusable Blocks' ) } - - - ) } - { isEmpty( suggestedItems ) && isEmpty( reusableItems ) && isEmpty( itemsPerCategory ) && ( -

{ __( 'No blocks found.' ) }

- ) } + + + { __( 'Manage All Reusable Blocks' ) } + + + ) } + { isEmpty( suggestedItems ) && isEmpty( reusableItems ) && isEmpty( itemsPerCategory ) && ( +

{ __( 'No blocks found.' ) }

+ ) } +
- { hoveredItem && isReusableBlock( hoveredItem ) && -
-
{ __( 'Preview' ) }
- + { showInserterHelpPanel && ( +
+ { hoveredItem && ( + <> + + { isReusableBlock( hoveredItem ) && ( +
+
{ __( 'Preview' ) }
+ +
+ ) } + + ) } + { ! hoveredItem && ( +
+
+
Content Blocks
+

+ { __( + 'Welcome to the wonderful world of blocks! Blocks are the basis of all content within the editor. ' + ) } +

+

+ { __( + 'There are blocks available for all kinds of content: insert text, headings, images, lists, videos, tables, and lots more.' + ) } +

+

+ { __( + 'Browse through the library to learn more about what each block does.' + ) } +

+
+ + { __( + 'While writing, you can press "/" to quickly insert new blocks.' + ) } + +
+ ) }
- } + ) }
); /* eslint-enable jsx-a11y/no-autofocus, jsx-a11y/no-static-element-interactions */ @@ -371,6 +418,7 @@ export default compose( getBlockName, getBlockRootClientId, getBlockSelectionEnd, + getSettings, } = select( 'core/block-editor' ); const { getChildBlockNames, @@ -388,6 +436,7 @@ export default compose( return { rootChildBlocks: getChildBlockNames( destinationRootBlockName ), items: getInserterItems( destinationRootClientId ), + showInserterHelpPanel: getSettings().showInserterHelpPanel, destinationRootClientId, }; } ), diff --git a/packages/block-editor/src/components/inserter/style.scss b/packages/block-editor/src/components/inserter/style.scss index 4cc764ed0861a..a415e13ccb547 100644 --- a/packages/block-editor/src/components/inserter/style.scss +++ b/packages/block-editor/src/components/inserter/style.scss @@ -36,6 +36,21 @@ $block-inserter-search-height: 38px; } .block-editor-inserter__menu { + height: 100%; + display: flex; + width: auto; + + @include break-medium { + width: 400px; + position: relative; + + &.has-help-panel { + width: 700px; + } + } +} + +.block-editor-inserter__main-area { width: auto; display: flex; flex-direction: column; @@ -130,25 +145,65 @@ $block-inserter-search-height: 38px; } } -.block-editor-inserter__preview { - border: $border-width solid $light-gray-500; - box-shadow: $shadow-popover; - background: $white; - position: absolute; - left: 100%; - top: -1px; - bottom: -1px; - width: 300px; - height: auto; - padding: 10px; +.block-editor-inserter__menu-help-panel { display: none; + border-left: $border-width solid $light-gray-500; + width: 300px; + height: 100%; + padding: 20px; + overflow-y: auto; @include break-medium { display: block; } + + .block-editor-block-card { + padding-bottom: 20px; + margin-bottom: 10px; + border-bottom: $border-width solid $light-gray-500; + @include edit-post__fade-in-animation(); + } } .block-editor-inserter__preview-title { margin-bottom: 10px; - color: $dark-gray-300; +} + +.block-editor-inserter__menu-help-panel-no-block { + display: flex; + height: 100%; + flex-direction: column; + @include edit-post__fade-in-animation(); + + .block-editor-inserter__menu-help-panel-no-block-text { + flex-grow: 1; + + h4 { + font-size: $big-font-size; + } + } + + .components-notice { + margin: 0; + } + + h4 { + margin-top: 0; + } +} + +.block-editor-inserter__menu-help-panel-hover-area { + flex-grow: 1; + margin-top: 20px; + padding: 20px; + border: 1px dotted $light-gray-500; + display: flex; + align-items: center; + text-align: center; +} + +.block-editor-inserter__menu-help-panel-title { + font-size: $big-font-size; + font-weight: 600; + margin-bottom: 20px; } diff --git a/packages/block-editor/src/store/defaults.js b/packages/block-editor/src/store/defaults.js index 885a8b79f7fb0..2e7cb1f59cb78 100644 --- a/packages/block-editor/src/store/defaults.js +++ b/packages/block-editor/src/store/defaults.js @@ -27,6 +27,7 @@ export const PREFERENCES_DEFAULTS = { * bodyPlaceholder string Empty post placeholder * titlePlaceholder string Empty title placeholder * codeEditingEnabled string Whether or not the user can switch to the code editor + * showInserterHelpPanel boolean Whether or not the inserter help panel is shown * __experimentalCanUserUseUnfilteredHTML string Whether the user should be able to use unfiltered HTML or the HTML should be filtered e.g., to remove elements considered insecure like iframes. * __experimentalEnableLegacyWidgetBlock boolean Whether the user has enabled the Legacy Widget Block * __experimentalEnableMenuBlock boolean Whether the user has enabled the Menu Block @@ -145,6 +146,7 @@ export const SETTINGS_DEFAULTS = { availableLegacyWidgets: {}, hasPermissionsToManageWidgets: false, + showInserterHelpPanel: true, __experimentalCanUserUseUnfilteredHTML: false, __experimentalEnableLegacyWidgetBlock: false, __experimentalEnableMenuBlock: false, diff --git a/packages/block-editor/src/style.scss b/packages/block-editor/src/style.scss index 8083cf0cbc6bf..644083ea80a81 100644 --- a/packages/block-editor/src/style.scss +++ b/packages/block-editor/src/style.scss @@ -3,6 +3,7 @@ @import "./components/block-inspector/style.scss"; @import "./components/block-list/style.scss"; @import "./components/block-list-appender/style.scss"; +@import "./components/block-card/style.scss"; @import "./components/block-compare/style.scss"; @import "./components/block-mover/style.scss"; @import "./components/block-navigation/style.scss"; diff --git a/packages/components/src/index.js b/packages/components/src/index.js index 3ab485312f848..5ce67b968084e 100644 --- a/packages/components/src/index.js +++ b/packages/components/src/index.js @@ -55,6 +55,7 @@ export { default as Spinner } from './spinner'; export { default as TabPanel } from './tab-panel'; export { default as TextControl } from './text-control'; export { default as TextareaControl } from './textarea-control'; +export { default as Tip } from './tip'; export { default as ToggleControl } from './toggle-control'; export { default as Toolbar } from './toolbar'; export { default as ToolbarButton } from './toolbar-button'; diff --git a/packages/components/src/style.scss b/packages/components/src/style.scss index 39c566be5ad52..39b026111065d 100644 --- a/packages/components/src/style.scss +++ b/packages/components/src/style.scss @@ -39,6 +39,7 @@ @import "./spinner/style.scss"; @import "./text-control/style.scss"; @import "./textarea-control/style.scss"; +@import "./tip/style.scss"; @import "./toggle-control/style.scss"; @import "./toolbar/style.scss"; @import "./toolbar-button/style.scss"; diff --git a/packages/components/src/tip/index.js b/packages/components/src/tip/index.js new file mode 100644 index 0000000000000..1672283d426f6 --- /dev/null +++ b/packages/components/src/tip/index.js @@ -0,0 +1,17 @@ +/** + * Internal dependencies + */ +import { SVG, Path } from '../'; + +function Tip( props ) { + return ( +
+ + + +

{ props.children }

+
+ ); +} + +export default Tip; diff --git a/packages/components/src/tip/style.scss b/packages/components/src/tip/style.scss new file mode 100644 index 0000000000000..d02afb1bdf8d0 --- /dev/null +++ b/packages/components/src/tip/style.scss @@ -0,0 +1,15 @@ +.components-tip { + display: flex; + color: $dark-gray-500; + + svg { + align-self: center; + fill: $alert-yellow; + flex-shrink: 0; + margin-right: $grid-size-large; + } + + p { + margin: 0; + } +} diff --git a/packages/e2e-tests/specs/editor-modes.test.js b/packages/e2e-tests/specs/editor-modes.test.js index 9fa866e893e9f..6cb49238db01d 100644 --- a/packages/e2e-tests/specs/editor-modes.test.js +++ b/packages/e2e-tests/specs/editor-modes.test.js @@ -88,7 +88,7 @@ describe( 'Editing modes (visual/HTML)', () => { it( 'the code editor should unselect blocks and disable the inserter', async () => { // The paragraph block should be selected const title = await page.$eval( - '.block-editor-block-inspector__card-title', + '.block-editor-block-card__title', ( element ) => element.innerText ); expect( title ).toBe( 'Paragraph' ); diff --git a/packages/edit-post/src/components/options-modal/index.js b/packages/edit-post/src/components/options-modal/index.js index bb3f613539062..1cfe832632755 100644 --- a/packages/edit-post/src/components/options-modal/index.js +++ b/packages/edit-post/src/components/options-modal/index.js @@ -27,6 +27,7 @@ import { EnablePublishSidebarOption, EnableTipsOption, EnablePanelOption, + EnableFeature, } from './options'; import MetaBoxesSection from './meta-boxes-section'; @@ -47,6 +48,7 @@ export function OptionsModal( { isModalActive, isViewable, closeModal } ) {
+
diff --git a/packages/edit-post/src/components/options-modal/options/enable-feature.js b/packages/edit-post/src/components/options-modal/options/enable-feature.js new file mode 100644 index 0000000000000..a0b79eddef3a5 --- /dev/null +++ b/packages/edit-post/src/components/options-modal/options/enable-feature.js @@ -0,0 +1,24 @@ +/** + * WordPress dependencies + */ +import { compose } from '@wordpress/compose'; +import { withSelect, withDispatch } from '@wordpress/data'; + +/** + * Internal dependencies + */ +import BaseOption from './base'; + +export default compose( + withSelect( ( select, { feature } ) => ( { + isChecked: select( 'core/edit-post' ).isFeatureActive( feature ), + } ) ), + withDispatch( ( dispatch, { feature } ) => { + const { toggleFeature } = dispatch( 'core/edit-post' ); + return { + onChange() { + toggleFeature( feature ); + }, + }; + } ) +)( BaseOption ); diff --git a/packages/edit-post/src/components/options-modal/options/index.js b/packages/edit-post/src/components/options-modal/options/index.js index e1263f9f68474..8684b68037705 100644 --- a/packages/edit-post/src/components/options-modal/options/index.js +++ b/packages/edit-post/src/components/options-modal/options/index.js @@ -3,3 +3,4 @@ export { default as EnablePanelOption } from './enable-panel'; export { default as EnablePluginDocumentSettingPanelOption } from './enable-plugin-document-setting-panel'; export { default as EnablePublishSidebarOption } from './enable-publish-sidebar'; export { default as EnableTipsOption } from './enable-tips'; +export { default as EnableFeature } from './enable-feature'; diff --git a/packages/edit-post/src/components/options-modal/test/__snapshots__/index.js.snap b/packages/edit-post/src/components/options-modal/test/__snapshots__/index.js.snap index c2907a26e3001..7a89493c76eea 100644 --- a/packages/edit-post/src/components/options-modal/test/__snapshots__/index.js.snap +++ b/packages/edit-post/src/components/options-modal/test/__snapshots__/index.js.snap @@ -15,6 +15,10 @@ exports[`OptionsModal should match snapshot when the modal is active 1`] = ` +