diff --git a/package.json b/package.json index fa0250f..5a61096 100644 --- a/package.json +++ b/package.json @@ -1,6 +1,6 @@ { "name": "@eeacms/volto-group-block", - "version": "6.0.0", + "version": "6.1.0", "description": "volto-group-block: Volto block to be used to group other blocks", "main": "src/index.js", "author": "European Environment Agency: IDM2 A-Team", diff --git a/src/components/manage/Blocks/Group/Edit.jsx b/src/components/manage/Blocks/Group/Edit.jsx index f8baf3f..36f9b60 100644 --- a/src/components/manage/Blocks/Group/Edit.jsx +++ b/src/components/manage/Blocks/Group/Edit.jsx @@ -1,5 +1,6 @@ import React, { useState } from 'react'; import { isEmpty, without } from 'lodash'; +import config from '@plone/volto/registry'; import { BlocksForm, SidebarPortal, @@ -32,6 +33,44 @@ const Edit = (props) => { manage, formDescription, } = props; + const metadata = props.metadata || props.properties; + const [multiSelected, setMultiSelected] = useState([]); + const data_blocks = data?.data?.blocks; + const properties = isEmpty(data_blocks) ? emptyBlocksForm() : data.data; + + const [selectedBlock, setSelectedBlock] = useState( + properties.blocks_layout.items[0], + ); + + const blockState = {}; + let charCount = 0; + + const handleKeyDown = ( + e, + index, + block, + node, + { + disableEnter = false, + disableArrowUp = false, + disableArrowDown = false, + } = {}, + ) => { + const hasblockActive = !!selectedBlock; + if (e.key === 'ArrowUp' && !disableArrowUp && !hasblockActive) { + props.onFocusPreviousBlock(block, node); + e.preventDefault(); + } + if (e.key === 'ArrowDown' && !disableArrowDown && !hasblockActive) { + props.onFocusNextBlock(block, node); + e.preventDefault(); + } + if (e.key === 'Enter' && !disableEnter && !hasblockActive) { + props.onAddBlock(config.settings.defaultBlockType, index + 1); + e.preventDefault(); + } + }; + const onSelectBlock = (id, isMultipleSelection, event, activeBlock) => { let newMultiSelected = []; let selected = id; @@ -67,14 +106,7 @@ const Edit = (props) => { setSelectedBlock(selected); setMultiSelected(newMultiSelected); }; - const metadata = props.metadata || props.properties; - const [multiSelected, setMultiSelected] = useState([]); - const data_blocks = data?.data?.blocks; - const properties = isEmpty(data_blocks) ? emptyBlocksForm() : data.data; - const [selectedBlock, setSelectedBlock] = useState( - properties.blocks_layout.items[0], - ); const changeBlockData = (newBlockData) => { let pastedBlocks = newBlockData.blocks_layout.items.filter((blockID) => { if (data?.data?.blocks_layout.items.find((x) => x === blockID)) @@ -98,6 +130,7 @@ const Edit = (props) => { }, }); }; + React.useEffect(() => { if ( isEmpty(data_blocks) && @@ -111,9 +144,6 @@ const Edit = (props) => { } }, [onChangeBlock, properties, selectedBlock, block, data, data_blocks]); - const blockState = {}; - let charCount = 0; - /** * Count the number of characters that are anything except using Regex * @param {string} paragraph @@ -216,7 +246,16 @@ const Edit = (props) => { } return ( -
+
{ + handleKeyDown(e, props.index, props.block, props.blockNode.current); + }} + // The tabIndex is required for the keyboard navigation + /* eslint-disable jsx-a11y/no-noninteractive-tabindex */ + tabIndex={-1} + > { setSelectedBlock(); diff --git a/src/components/manage/Blocks/Group/EditBlockWrapper.jsx b/src/components/manage/Blocks/Group/EditBlockWrapper.jsx index ead9c87..ca3f5d7 100644 --- a/src/components/manage/Blocks/Group/EditBlockWrapper.jsx +++ b/src/components/manage/Blocks/Group/EditBlockWrapper.jsx @@ -1,13 +1,16 @@ import React from 'react'; import { Icon, BlockChooser } from '@plone/volto/components'; -import { blockHasValue } from '@plone/volto/helpers'; -import config from '@plone/volto/registry'; +import { + blockHasValue, + buildStyleClassNamesFromData, +} from '@plone/volto/helpers'; import { Button } from 'semantic-ui-react'; import includes from 'lodash/includes'; import isBoolean from 'lodash/isBoolean'; import { defineMessages, injectIntl } from 'react-intl'; -import { doesNodeContainClick } from 'semantic-ui-react/dist/commonjs/lib'; import cx from 'classnames'; +import config from '@plone/volto/registry'; +import { doesNodeContainClick } from 'semantic-ui-react/dist/commonjs/lib'; import dragSVG from '@plone/volto/icons/drag.svg'; import addSVG from '@plone/volto/icons/circle-plus.svg'; @@ -86,6 +89,8 @@ class EditBlockWrapper extends React.Component { ? data.required : includes(config.blocks.requiredBlocks, type); + const styles = buildStyleClassNamesFromData(data.styles); + // Get editing instructions from block settings or props let instructions = data?.instructions?.data || data?.instructions; if (!instructions || instructions === '


') { @@ -97,7 +102,9 @@ class EditBlockWrapper extends React.Component {
{(!selected || !visible || disabled) && (
{ restricted: false, mostUsed: false, blockHasOwnFocusManagement: true, - sidebarTab: 0, + sidebarTab: 1, security: { addPermission: [], view: [],