@plone/volto 18.0.0-alpha.47 → 18.0.0-alpha.48
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +21 -0
- package/locales/ca/LC_MESSAGES/volto.po +1 -2
- package/locales/de/LC_MESSAGES/volto.po +1 -2
- package/locales/en/LC_MESSAGES/volto.po +1 -2
- package/locales/es/LC_MESSAGES/volto.po +1 -2
- package/locales/eu/LC_MESSAGES/volto.po +1 -2
- package/locales/fi/LC_MESSAGES/volto.po +1 -2
- package/locales/fr/LC_MESSAGES/volto.po +1 -2
- package/locales/hi/LC_MESSAGES/volto.po +1 -2
- package/locales/it/LC_MESSAGES/volto.po +1 -2
- package/locales/ja/LC_MESSAGES/volto.po +1 -2
- package/locales/nl/LC_MESSAGES/volto.po +1 -2
- package/locales/pt/LC_MESSAGES/volto.po +1 -2
- package/locales/pt_BR/LC_MESSAGES/volto.po +1 -2
- package/locales/ro/LC_MESSAGES/volto.po +1 -2
- package/locales/volto.pot +1 -2
- package/locales/zh_CN/LC_MESSAGES/volto.po +1 -2
- package/package.json +4 -4
- package/src/components/manage/Blocks/Block/Edit.jsx +1 -2
- package/src/components/manage/Blocks/Block/EditBlockWrapper.jsx +5 -2
- package/src/components/manage/Blocks/Block/StyleWrapper.jsx +1 -1
- package/src/components/manage/Blocks/Listing/getAsyncData.js +8 -0
- package/src/components/manage/Blocks/ToC/View.jsx +18 -7
- package/src/components/manage/Blocks/ToC/variations/DefaultTocRenderer.jsx +2 -20
- package/src/components/manage/Blocks/ToC/variations/HorizontalMenu.jsx +2 -19
- package/src/components/manage/Widgets/IdWidget.jsx +6 -7
- package/src/components/theme/App/App.jsx +2 -0
- package/src/components/theme/App/App.test.jsx +4 -3
- package/src/components/theme/RouteAnnouncer/RouteAnnouncer.jsx +64 -0
- package/src/helpers/Blocks/Blocks.js +73 -33
- package/src/helpers/Blocks/Blocks.test.js +204 -27
- package/types/components/manage/Blocks/ToC/View.d.ts +1 -4
- package/types/components/manage/Blocks/ToC/variations/DefaultTocRenderer.d.ts +10 -5
- package/types/components/manage/Blocks/ToC/variations/HorizontalMenu.d.ts +10 -5
- package/types/components/manage/Blocks/ToC/variations/index.d.ts +16 -4
- package/types/components/theme/RouteAnnouncer/RouteAnnouncer.d.ts +2 -0
- package/types/helpers/Blocks/Blocks.d.ts +10 -1
package/CHANGELOG.md
CHANGED
|
@@ -17,6 +17,27 @@ myst:
|
|
|
17
17
|
|
|
18
18
|
<!-- towncrier release notes start -->
|
|
19
19
|
|
|
20
|
+
## 18.0.0-alpha.48 (2024-10-30)
|
|
21
|
+
|
|
22
|
+
### Breaking
|
|
23
|
+
|
|
24
|
+
- Wrap Table of Contents block in a `nav` tag, instead of a `div` tag, for better representation improving the block accessibility. @Tishasoumya-02 @ichim-david [#6082](https://github.com/plone/volto/issues/6082)
|
|
25
|
+
|
|
26
|
+
### Feature
|
|
27
|
+
|
|
28
|
+
- Enhance the `buildStyleObjectFromData` helper. @sneridagh [#6445](https://github.com/plone/volto/issues/6445)
|
|
29
|
+
|
|
30
|
+
### Bugfix
|
|
31
|
+
|
|
32
|
+
- Fix error "Exception: No query supplied" in the listing block, when there is no criteria selected. @tedw87 [#3839](https://github.com/plone/volto/issues/3839)
|
|
33
|
+
- Fixed page changes not being announced to screen reader users. @JeffersonBledsoe [#5288](https://github.com/plone/volto/issues/5288)
|
|
34
|
+
- Fix useSelector is returned a different result when called with the same parameters in IdWidget. @iFlameing [#6449](https://github.com/plone/volto/issues/6449)
|
|
35
|
+
- Moved `applyBlockDefaults` one component up so the style is computed correctly. @sneridagh [#6451](https://github.com/plone/volto/issues/6451)
|
|
36
|
+
|
|
37
|
+
### Documentation
|
|
38
|
+
|
|
39
|
+
- Added upgrade guide fix for HMR. @sneridagh [#6446](https://github.com/plone/volto/issues/6446)
|
|
40
|
+
|
|
20
41
|
## 18.0.0-alpha.47 (2024-10-27)
|
|
21
42
|
|
|
22
43
|
### Breaking
|
|
@@ -3622,8 +3622,7 @@ msgid "Table"
|
|
|
3622
3622
|
msgstr "Taula"
|
|
3623
3623
|
|
|
3624
3624
|
#. Default: "Table of Contents"
|
|
3625
|
-
#: components/manage/Blocks/ToC/
|
|
3626
|
-
#: components/manage/Blocks/ToC/variations/HorizontalMenu
|
|
3625
|
+
#: components/manage/Blocks/ToC/View
|
|
3627
3626
|
msgid "Table of Contents"
|
|
3628
3627
|
msgstr "Taula de continguts"
|
|
3629
3628
|
|
|
@@ -3621,8 +3621,7 @@ msgid "Table"
|
|
|
3621
3621
|
msgstr "Tabelle"
|
|
3622
3622
|
|
|
3623
3623
|
#. Default: "Table of Contents"
|
|
3624
|
-
#: components/manage/Blocks/ToC/
|
|
3625
|
-
#: components/manage/Blocks/ToC/variations/HorizontalMenu
|
|
3624
|
+
#: components/manage/Blocks/ToC/View
|
|
3626
3625
|
msgid "Table of Contents"
|
|
3627
3626
|
msgstr "Inhaltsverzeichnis"
|
|
3628
3627
|
|
|
@@ -3616,8 +3616,7 @@ msgid "Table"
|
|
|
3616
3616
|
msgstr ""
|
|
3617
3617
|
|
|
3618
3618
|
#. Default: "Table of Contents"
|
|
3619
|
-
#: components/manage/Blocks/ToC/
|
|
3620
|
-
#: components/manage/Blocks/ToC/variations/HorizontalMenu
|
|
3619
|
+
#: components/manage/Blocks/ToC/View
|
|
3621
3620
|
msgid "Table of Contents"
|
|
3622
3621
|
msgstr ""
|
|
3623
3622
|
|
|
@@ -3623,8 +3623,7 @@ msgid "Table"
|
|
|
3623
3623
|
msgstr "Tabla"
|
|
3624
3624
|
|
|
3625
3625
|
#. Default: "Table of Contents"
|
|
3626
|
-
#: components/manage/Blocks/ToC/
|
|
3627
|
-
#: components/manage/Blocks/ToC/variations/HorizontalMenu
|
|
3626
|
+
#: components/manage/Blocks/ToC/View
|
|
3628
3627
|
msgid "Table of Contents"
|
|
3629
3628
|
msgstr "Tabla de contenidos"
|
|
3630
3629
|
|
|
@@ -3623,8 +3623,7 @@ msgid "Table"
|
|
|
3623
3623
|
msgstr "Taula"
|
|
3624
3624
|
|
|
3625
3625
|
#. Default: "Table of Contents"
|
|
3626
|
-
#: components/manage/Blocks/ToC/
|
|
3627
|
-
#: components/manage/Blocks/ToC/variations/HorizontalMenu
|
|
3626
|
+
#: components/manage/Blocks/ToC/View
|
|
3628
3627
|
msgid "Table of Contents"
|
|
3629
3628
|
msgstr "Edukien taula"
|
|
3630
3629
|
|
|
@@ -3621,8 +3621,7 @@ msgid "Table"
|
|
|
3621
3621
|
msgstr "Taulukkoa"
|
|
3622
3622
|
|
|
3623
3623
|
#. Default: "Table of Contents"
|
|
3624
|
-
#: components/manage/Blocks/ToC/
|
|
3625
|
-
#: components/manage/Blocks/ToC/variations/HorizontalMenu
|
|
3624
|
+
#: components/manage/Blocks/ToC/View
|
|
3626
3625
|
msgid "Table of Contents"
|
|
3627
3626
|
msgstr "Sisällys"
|
|
3628
3627
|
|
|
@@ -3623,8 +3623,7 @@ msgid "Table"
|
|
|
3623
3623
|
msgstr "Table"
|
|
3624
3624
|
|
|
3625
3625
|
#. Default: "Table of Contents"
|
|
3626
|
-
#: components/manage/Blocks/ToC/
|
|
3627
|
-
#: components/manage/Blocks/ToC/variations/HorizontalMenu
|
|
3626
|
+
#: components/manage/Blocks/ToC/View
|
|
3628
3627
|
msgid "Table of Contents"
|
|
3629
3628
|
msgstr "Table des matières"
|
|
3630
3629
|
|
|
@@ -3616,8 +3616,7 @@ msgid "Table"
|
|
|
3616
3616
|
msgstr "तालिका"
|
|
3617
3617
|
|
|
3618
3618
|
#. Default: "Table of Contents"
|
|
3619
|
-
#: components/manage/Blocks/ToC/
|
|
3620
|
-
#: components/manage/Blocks/ToC/variations/HorizontalMenu
|
|
3619
|
+
#: components/manage/Blocks/ToC/View
|
|
3621
3620
|
msgid "Table of Contents"
|
|
3622
3621
|
msgstr "सारांश की तालिका"
|
|
3623
3622
|
|
|
@@ -3616,8 +3616,7 @@ msgid "Table"
|
|
|
3616
3616
|
msgstr "Tabella"
|
|
3617
3617
|
|
|
3618
3618
|
#. Default: "Table of Contents"
|
|
3619
|
-
#: components/manage/Blocks/ToC/
|
|
3620
|
-
#: components/manage/Blocks/ToC/variations/HorizontalMenu
|
|
3619
|
+
#: components/manage/Blocks/ToC/View
|
|
3621
3620
|
msgid "Table of Contents"
|
|
3622
3621
|
msgstr "Indice dei contenuti"
|
|
3623
3622
|
|
|
@@ -3621,8 +3621,7 @@ msgid "Table"
|
|
|
3621
3621
|
msgstr "テーブル"
|
|
3622
3622
|
|
|
3623
3623
|
#. Default: "Table of Contents"
|
|
3624
|
-
#: components/manage/Blocks/ToC/
|
|
3625
|
-
#: components/manage/Blocks/ToC/variations/HorizontalMenu
|
|
3624
|
+
#: components/manage/Blocks/ToC/View
|
|
3626
3625
|
msgid "Table of Contents"
|
|
3627
3626
|
msgstr "目次"
|
|
3628
3627
|
|
|
@@ -3620,8 +3620,7 @@ msgid "Table"
|
|
|
3620
3620
|
msgstr ""
|
|
3621
3621
|
|
|
3622
3622
|
#. Default: "Table of Contents"
|
|
3623
|
-
#: components/manage/Blocks/ToC/
|
|
3624
|
-
#: components/manage/Blocks/ToC/variations/HorizontalMenu
|
|
3623
|
+
#: components/manage/Blocks/ToC/View
|
|
3625
3624
|
msgid "Table of Contents"
|
|
3626
3625
|
msgstr ""
|
|
3627
3626
|
|
|
@@ -3621,8 +3621,7 @@ msgid "Table"
|
|
|
3621
3621
|
msgstr "Tabela"
|
|
3622
3622
|
|
|
3623
3623
|
#. Default: "Table of Contents"
|
|
3624
|
-
#: components/manage/Blocks/ToC/
|
|
3625
|
-
#: components/manage/Blocks/ToC/variations/HorizontalMenu
|
|
3624
|
+
#: components/manage/Blocks/ToC/View
|
|
3626
3625
|
msgid "Table of Contents"
|
|
3627
3626
|
msgstr ""
|
|
3628
3627
|
|
|
@@ -3622,8 +3622,7 @@ msgid "Table"
|
|
|
3622
3622
|
msgstr "Tabela"
|
|
3623
3623
|
|
|
3624
3624
|
#. Default: "Table of Contents"
|
|
3625
|
-
#: components/manage/Blocks/ToC/
|
|
3626
|
-
#: components/manage/Blocks/ToC/variations/HorizontalMenu
|
|
3625
|
+
#: components/manage/Blocks/ToC/View
|
|
3627
3626
|
msgid "Table of Contents"
|
|
3628
3627
|
msgstr "Tabela de conteúdos"
|
|
3629
3628
|
|
|
@@ -3616,8 +3616,7 @@ msgid "Table"
|
|
|
3616
3616
|
msgstr "Tabel"
|
|
3617
3617
|
|
|
3618
3618
|
#. Default: "Table of Contents"
|
|
3619
|
-
#: components/manage/Blocks/ToC/
|
|
3620
|
-
#: components/manage/Blocks/ToC/variations/HorizontalMenu
|
|
3619
|
+
#: components/manage/Blocks/ToC/View
|
|
3621
3620
|
msgid "Table of Contents"
|
|
3622
3621
|
msgstr "Cuprins"
|
|
3623
3622
|
|
package/locales/volto.pot
CHANGED
|
@@ -3618,8 +3618,7 @@ msgid "Table"
|
|
|
3618
3618
|
msgstr ""
|
|
3619
3619
|
|
|
3620
3620
|
#. Default: "Table of Contents"
|
|
3621
|
-
#: components/manage/Blocks/ToC/
|
|
3622
|
-
#: components/manage/Blocks/ToC/variations/HorizontalMenu
|
|
3621
|
+
#: components/manage/Blocks/ToC/View
|
|
3623
3622
|
msgid "Table of Contents"
|
|
3624
3623
|
msgstr ""
|
|
3625
3624
|
|
|
@@ -3622,8 +3622,7 @@ msgid "Table"
|
|
|
3622
3622
|
msgstr "表格"
|
|
3623
3623
|
|
|
3624
3624
|
#. Default: "Table of Contents"
|
|
3625
|
-
#: components/manage/Blocks/ToC/
|
|
3626
|
-
#: components/manage/Blocks/ToC/variations/HorizontalMenu
|
|
3625
|
+
#: components/manage/Blocks/ToC/View
|
|
3627
3626
|
msgid "Table of Contents"
|
|
3628
3627
|
msgstr "表格内容"
|
|
3629
3628
|
|
package/package.json
CHANGED
|
@@ -9,7 +9,7 @@
|
|
|
9
9
|
}
|
|
10
10
|
],
|
|
11
11
|
"license": "MIT",
|
|
12
|
-
"version": "18.0.0-alpha.
|
|
12
|
+
"version": "18.0.0-alpha.48",
|
|
13
13
|
"repository": {
|
|
14
14
|
"type": "git",
|
|
15
15
|
"url": "git@github.com:plone/volto.git"
|
|
@@ -239,7 +239,7 @@
|
|
|
239
239
|
"uuid": "^8.3.2",
|
|
240
240
|
"@plone/registry": "2.0.0-alpha.0",
|
|
241
241
|
"@plone/scripts": "3.7.0",
|
|
242
|
-
"@plone/volto-slate": "18.0.0-alpha.
|
|
242
|
+
"@plone/volto-slate": "18.0.0-alpha.20"
|
|
243
243
|
},
|
|
244
244
|
"devDependencies": {
|
|
245
245
|
"@babel/core": "^7.0.0",
|
|
@@ -359,8 +359,8 @@
|
|
|
359
359
|
"webpack-dev-server": "4.11.1",
|
|
360
360
|
"webpack-node-externals": "3.0.0",
|
|
361
361
|
"why": "0.6.2",
|
|
362
|
-
"@plone/
|
|
363
|
-
"@plone/
|
|
362
|
+
"@plone/types": "1.0.0-alpha.22",
|
|
363
|
+
"@plone/volto-coresandbox": "1.0.0"
|
|
364
364
|
},
|
|
365
365
|
"volta": {
|
|
366
366
|
"node": "20.9.0"
|
|
@@ -12,7 +12,6 @@ import cx from 'classnames';
|
|
|
12
12
|
import { setSidebarTab, setUIState } from '@plone/volto/actions';
|
|
13
13
|
import config from '@plone/volto/registry';
|
|
14
14
|
import withObjectBrowser from '@plone/volto/components/manage/Sidebar/ObjectBrowser';
|
|
15
|
-
import { applyBlockDefaults } from '@plone/volto/helpers';
|
|
16
15
|
import { ViewDefaultBlock, EditDefaultBlock } from '@plone/volto/components';
|
|
17
16
|
|
|
18
17
|
import {
|
|
@@ -199,7 +198,7 @@ export class Edit extends Component {
|
|
|
199
198
|
<Block
|
|
200
199
|
{...this.props}
|
|
201
200
|
blockNode={this.blockNode}
|
|
202
|
-
data={
|
|
201
|
+
data={this.props.data}
|
|
203
202
|
/>
|
|
204
203
|
{this.props.manage && (
|
|
205
204
|
<SidebarPortal
|
|
@@ -1,6 +1,7 @@
|
|
|
1
1
|
import React from 'react';
|
|
2
2
|
import { Icon } from '@plone/volto/components';
|
|
3
3
|
import {
|
|
4
|
+
applyBlockDefaults,
|
|
4
5
|
applyBlockInitialValue,
|
|
5
6
|
getBlocksFieldname,
|
|
6
7
|
blockHasValue,
|
|
@@ -48,7 +49,7 @@ const EditBlockWrapper = (props) => {
|
|
|
48
49
|
onInsertBlock,
|
|
49
50
|
onSelectBlock,
|
|
50
51
|
onMutateBlock,
|
|
51
|
-
data,
|
|
52
|
+
data: originalData,
|
|
52
53
|
editable,
|
|
53
54
|
properties,
|
|
54
55
|
showBlockChooser,
|
|
@@ -56,6 +57,8 @@ const EditBlockWrapper = (props) => {
|
|
|
56
57
|
contentType,
|
|
57
58
|
} = blockProps;
|
|
58
59
|
|
|
60
|
+
const data = applyBlockDefaults({ data: originalData, ...blockProps, intl });
|
|
61
|
+
|
|
59
62
|
const visible = selected && !hideHandler(data);
|
|
60
63
|
|
|
61
64
|
const required = isBoolean(data.required)
|
|
@@ -69,7 +72,7 @@ const EditBlockWrapper = (props) => {
|
|
|
69
72
|
data,
|
|
70
73
|
classNames,
|
|
71
74
|
});
|
|
72
|
-
const style = buildStyleObjectFromData(data
|
|
75
|
+
const style = buildStyleObjectFromData(data);
|
|
73
76
|
|
|
74
77
|
// We need to merge the StyleWrapper styles with the draggable props from b-D&D
|
|
75
78
|
const styleMergedWithDragProps = {
|
|
@@ -19,7 +19,7 @@ const StyleWrapper = (props) => {
|
|
|
19
19
|
classNames,
|
|
20
20
|
});
|
|
21
21
|
|
|
22
|
-
style = buildStyleObjectFromData(data
|
|
22
|
+
style = buildStyleObjectFromData(data);
|
|
23
23
|
|
|
24
24
|
const rewrittenChildren = React.Children.map(children, (child) => {
|
|
25
25
|
if (React.isValidElement(child)) {
|
|
@@ -24,6 +24,14 @@ export default function getListingBlockAsyncData(props) {
|
|
|
24
24
|
const subrequestID = content?.UID ? `${content?.UID}-${id}` : id;
|
|
25
25
|
const currentPage = getCurrentPage(location, id);
|
|
26
26
|
|
|
27
|
+
if (!data.querystring) {
|
|
28
|
+
return [
|
|
29
|
+
async () => {
|
|
30
|
+
return null;
|
|
31
|
+
},
|
|
32
|
+
];
|
|
33
|
+
}
|
|
34
|
+
|
|
27
35
|
return [
|
|
28
36
|
dispatch(
|
|
29
37
|
getQueryStringResults(
|
|
@@ -2,10 +2,9 @@
|
|
|
2
2
|
* View toc block.
|
|
3
3
|
* @module components/manage/Blocks/ToC/View
|
|
4
4
|
*/
|
|
5
|
-
|
|
6
5
|
import React from 'react';
|
|
7
6
|
import PropTypes from 'prop-types';
|
|
8
|
-
import {
|
|
7
|
+
import { FormattedMessage } from 'react-intl';
|
|
9
8
|
import cx from 'classnames';
|
|
10
9
|
import { Message } from 'semantic-ui-react';
|
|
11
10
|
import config from '@plone/volto/registry';
|
|
@@ -86,6 +85,8 @@ export const getBlocksTocEntries = (properties, tocData) => {
|
|
|
86
85
|
*/
|
|
87
86
|
const View = (props) => {
|
|
88
87
|
const { data } = props;
|
|
88
|
+
|
|
89
|
+
const title = data.title ? data.title : '';
|
|
89
90
|
const { variation } = props;
|
|
90
91
|
const metadata = props.metadata || props.properties;
|
|
91
92
|
const blocksFieldname = getBlocksFieldname(metadata);
|
|
@@ -165,9 +166,19 @@ const View = (props) => {
|
|
|
165
166
|
|
|
166
167
|
const Renderer = variation?.view;
|
|
167
168
|
return (
|
|
168
|
-
<
|
|
169
|
-
{
|
|
170
|
-
|
|
169
|
+
<nav
|
|
170
|
+
aria-label={title && !data.hide_title ? title : ''}
|
|
171
|
+
className={cx('table-of-contents', variation?.id)}
|
|
172
|
+
>
|
|
173
|
+
{props.mode === 'edit' && !title && !tocEntries.length && (
|
|
174
|
+
<Message>
|
|
175
|
+
{
|
|
176
|
+
<FormattedMessage
|
|
177
|
+
id="Table of Contents"
|
|
178
|
+
defaultMessage="Table of Contents"
|
|
179
|
+
/>
|
|
180
|
+
}
|
|
181
|
+
</Message>
|
|
171
182
|
)}
|
|
172
183
|
|
|
173
184
|
{Renderer ? (
|
|
@@ -175,7 +186,7 @@ const View = (props) => {
|
|
|
175
186
|
) : (
|
|
176
187
|
<div>View extension not found</div>
|
|
177
188
|
)}
|
|
178
|
-
</
|
|
189
|
+
</nav>
|
|
179
190
|
);
|
|
180
191
|
};
|
|
181
192
|
|
|
@@ -188,4 +199,4 @@ View.propTypes = {
|
|
|
188
199
|
properties: PropTypes.objectOf(PropTypes.any).isRequired,
|
|
189
200
|
};
|
|
190
201
|
|
|
191
|
-
export default
|
|
202
|
+
export default withBlockExtensions(View);
|
|
@@ -3,11 +3,9 @@
|
|
|
3
3
|
* @module components/manage/Blocks/ToC/View
|
|
4
4
|
*/
|
|
5
5
|
|
|
6
|
-
import React from 'react';
|
|
7
6
|
import PropTypes from 'prop-types';
|
|
8
7
|
import { map } from 'lodash';
|
|
9
8
|
import { List } from 'semantic-ui-react';
|
|
10
|
-
import { FormattedMessage, injectIntl } from 'react-intl';
|
|
11
9
|
import Slugger from 'github-slugger';
|
|
12
10
|
import { UniversalLink } from '@plone/volto/components';
|
|
13
11
|
import { normalizeString } from '@plone/volto/helpers';
|
|
@@ -37,26 +35,10 @@ const RenderListItems = ({ items, data }) => {
|
|
|
37
35
|
});
|
|
38
36
|
};
|
|
39
37
|
|
|
40
|
-
/**
|
|
41
|
-
* View toc block class.
|
|
42
|
-
* @class View
|
|
43
|
-
* @extends Component
|
|
44
|
-
*/
|
|
45
38
|
const View = ({ data, tocEntries }) => {
|
|
46
39
|
return (
|
|
47
40
|
<>
|
|
48
|
-
{data.title && !data.hide_title ?
|
|
49
|
-
<h2>
|
|
50
|
-
{data.title || (
|
|
51
|
-
<FormattedMessage
|
|
52
|
-
id="Table of Contents"
|
|
53
|
-
defaultMessage="Table of Contents"
|
|
54
|
-
/>
|
|
55
|
-
)}
|
|
56
|
-
</h2>
|
|
57
|
-
) : (
|
|
58
|
-
''
|
|
59
|
-
)}
|
|
41
|
+
{data.title && !data.hide_title ? <h2>{data.title}</h2> : ''}
|
|
60
42
|
<List
|
|
61
43
|
ordered={data.ordered}
|
|
62
44
|
bulleted={!data.ordered}
|
|
@@ -77,4 +59,4 @@ View.propTypes = {
|
|
|
77
59
|
properties: PropTypes.objectOf(PropTypes.any).isRequired,
|
|
78
60
|
};
|
|
79
61
|
|
|
80
|
-
export default
|
|
62
|
+
export default View;
|
|
@@ -2,7 +2,6 @@ import React, { useEffect, useState } from 'react';
|
|
|
2
2
|
import PropTypes from 'prop-types';
|
|
3
3
|
import { map } from 'lodash';
|
|
4
4
|
import { Menu, Dropdown } from 'semantic-ui-react';
|
|
5
|
-
import { FormattedMessage, injectIntl } from 'react-intl';
|
|
6
5
|
import AnchorLink from 'react-anchor-link-smooth-scroll';
|
|
7
6
|
import Slugger from 'github-slugger';
|
|
8
7
|
import { normalizeString } from '@plone/volto/helpers';
|
|
@@ -26,11 +25,6 @@ const RenderMenuItems = ({ items }) => {
|
|
|
26
25
|
});
|
|
27
26
|
};
|
|
28
27
|
|
|
29
|
-
/**
|
|
30
|
-
* View toc block class.
|
|
31
|
-
* @class View
|
|
32
|
-
* @extends Component
|
|
33
|
-
*/
|
|
34
28
|
const View = ({ data, tocEntries }) => {
|
|
35
29
|
const [isDropdownOpen, setIsDropdownOpen] = useState(false);
|
|
36
30
|
// When the page is resized to prevent items from the TOC from going out of the viewport,
|
|
@@ -159,18 +153,7 @@ const View = ({ data, tocEntries }) => {
|
|
|
159
153
|
|
|
160
154
|
return (
|
|
161
155
|
<>
|
|
162
|
-
{data.title && !data.hide_title ?
|
|
163
|
-
<h2>
|
|
164
|
-
{data.title || (
|
|
165
|
-
<FormattedMessage
|
|
166
|
-
id="Table of Contents"
|
|
167
|
-
defaultMessage="Table of Contents"
|
|
168
|
-
/>
|
|
169
|
-
)}
|
|
170
|
-
</h2>
|
|
171
|
-
) : (
|
|
172
|
-
''
|
|
173
|
-
)}
|
|
156
|
+
{data.title && !data.hide_title ? <h2>{data.title}</h2> : ''}
|
|
174
157
|
<Menu className="responsive-menu">
|
|
175
158
|
<RenderMenuItems items={tocEntries} />
|
|
176
159
|
<Dropdown
|
|
@@ -201,4 +184,4 @@ View.propTypes = {
|
|
|
201
184
|
properties: PropTypes.objectOf(PropTypes.any).isRequired,
|
|
202
185
|
};
|
|
203
186
|
|
|
204
|
-
export default
|
|
187
|
+
export default View;
|
|
@@ -7,7 +7,7 @@ import { useState, useEffect, useRef } from 'react';
|
|
|
7
7
|
import PropTypes from 'prop-types';
|
|
8
8
|
import { useSelector, useDispatch } from 'react-redux';
|
|
9
9
|
import { Input } from 'semantic-ui-react';
|
|
10
|
-
import { compact, concat,
|
|
10
|
+
import { compact, concat, map, union, uniq } from 'lodash';
|
|
11
11
|
|
|
12
12
|
import { defineMessages, useIntl } from 'react-intl';
|
|
13
13
|
import { Icon } from '@plone/volto/components';
|
|
@@ -46,8 +46,7 @@ const IdWidget = (props) => {
|
|
|
46
46
|
const intl = useIntl();
|
|
47
47
|
const dispatch = useDispatch();
|
|
48
48
|
const ref = useRef();
|
|
49
|
-
|
|
50
|
-
const indexes = useSelector((state) => keys(state.querystring.indexes));
|
|
49
|
+
const indexes = useSelector((state) => state.querystring.indexes);
|
|
51
50
|
|
|
52
51
|
const [errors, setError] = useState([]);
|
|
53
52
|
const [reservedIds] = useState(
|
|
@@ -62,11 +61,11 @@ const IdWidget = (props) => {
|
|
|
62
61
|
),
|
|
63
62
|
),
|
|
64
63
|
);
|
|
65
|
-
const fieldValidation = (
|
|
64
|
+
const fieldValidation = (value) => {
|
|
66
65
|
const error = [];
|
|
67
66
|
|
|
68
67
|
// Check reserved id's
|
|
69
|
-
if (reservedIds.indexOf(
|
|
68
|
+
if (reservedIds.indexOf(value) !== -1) {
|
|
70
69
|
error.push(intl.formatMessage(messages.reservedId));
|
|
71
70
|
}
|
|
72
71
|
|
|
@@ -74,14 +73,14 @@ const IdWidget = (props) => {
|
|
|
74
73
|
if (
|
|
75
74
|
// eslint-disable-next-line no-control-regex
|
|
76
75
|
!/^(?!.*\\)(?!\+\+)(?!@@)(?!.*request)(?!.*contributors)(?!aq_)(?!.*__)(?!_)(?!((^|\/)\.\.?($|\/)|^"\s*"$))(?!.*[A-Z])(?:(?![\r\n<>/?&#\x00-\x1F\x7F])['\x00-\x7F\u0080-\uFFFF. _])*$/.test(
|
|
77
|
-
|
|
76
|
+
value,
|
|
78
77
|
)
|
|
79
78
|
) {
|
|
80
79
|
error.push(intl.formatMessage(messages.invalidCharacters));
|
|
81
80
|
}
|
|
82
81
|
|
|
83
82
|
// Check indexes
|
|
84
|
-
if (
|
|
83
|
+
if (value in indexes) {
|
|
85
84
|
error.push(intl.formatMessage(messages.reservedId));
|
|
86
85
|
}
|
|
87
86
|
|
|
@@ -51,6 +51,7 @@ import clearSVG from '@plone/volto/icons/clear.svg';
|
|
|
51
51
|
import MultilingualRedirector from '@plone/volto/components/theme/MultilingualRedirector/MultilingualRedirector';
|
|
52
52
|
import WorkingCopyToastsFactory from '@plone/volto/components/manage/WorkingCopyToastsFactory/WorkingCopyToastsFactory';
|
|
53
53
|
import LockingToastsFactory from '@plone/volto/components/manage/LockingToastsFactory/LockingToastsFactory';
|
|
54
|
+
import RouteAnnouncer from '@plone/volto/components/theme/RouteAnnouncer/RouteAnnouncer';
|
|
54
55
|
|
|
55
56
|
/**
|
|
56
57
|
* @export
|
|
@@ -191,6 +192,7 @@ export class App extends Component {
|
|
|
191
192
|
</main>
|
|
192
193
|
</Segment>
|
|
193
194
|
</MultilingualRedirector>
|
|
195
|
+
<RouteAnnouncer />
|
|
194
196
|
<Footer />
|
|
195
197
|
<LockingToastsFactory
|
|
196
198
|
content={this.props.content}
|
|
@@ -1,9 +1,9 @@
|
|
|
1
|
+
import config from '@plone/volto/registry';
|
|
1
2
|
import React from 'react';
|
|
2
|
-
import renderer from 'react-test-renderer';
|
|
3
|
-
import configureStore from 'redux-mock-store';
|
|
4
3
|
import { Provider } from 'react-intl-redux';
|
|
5
4
|
import { MemoryRouter } from 'react-router-dom';
|
|
6
|
-
import
|
|
5
|
+
import renderer from 'react-test-renderer';
|
|
6
|
+
import configureStore from 'redux-mock-store';
|
|
7
7
|
|
|
8
8
|
import { __test__ as App } from './App';
|
|
9
9
|
|
|
@@ -64,5 +64,6 @@ describe('App', () => {
|
|
|
64
64
|
);
|
|
65
65
|
const json = component.toJSON();
|
|
66
66
|
expect(json).toMatchSnapshot();
|
|
67
|
+
component.unmount();
|
|
67
68
|
});
|
|
68
69
|
});
|
|
@@ -0,0 +1,64 @@
|
|
|
1
|
+
import { useEffect, useState } from 'react';
|
|
2
|
+
|
|
3
|
+
function RouteAnnouncer() {
|
|
4
|
+
const [pageTitle, setPageTitle] = useState('');
|
|
5
|
+
|
|
6
|
+
useEffect(() => {
|
|
7
|
+
function updatePage(title) {
|
|
8
|
+
setPageTitle(title);
|
|
9
|
+
document.activeElement.blur();
|
|
10
|
+
}
|
|
11
|
+
function handlePop(event) {
|
|
12
|
+
const pageTitle = event.target.document.title;
|
|
13
|
+
updatePage(pageTitle);
|
|
14
|
+
}
|
|
15
|
+
|
|
16
|
+
const observer = new MutationObserver((mutationList) => {
|
|
17
|
+
for (const mutation of mutationList) {
|
|
18
|
+
if (mutation.type === 'childList') {
|
|
19
|
+
for (const node of mutation.addedNodes) {
|
|
20
|
+
if (node.nodeType === Node.TEXT_NODE && node.textContent) {
|
|
21
|
+
updatePage(node.textContent);
|
|
22
|
+
}
|
|
23
|
+
}
|
|
24
|
+
}
|
|
25
|
+
}
|
|
26
|
+
});
|
|
27
|
+
observer.observe(document.querySelector('title'), {
|
|
28
|
+
characterData: true,
|
|
29
|
+
attributes: true,
|
|
30
|
+
childList: true,
|
|
31
|
+
subtree: true,
|
|
32
|
+
});
|
|
33
|
+
window.addEventListener('popstate', handlePop);
|
|
34
|
+
|
|
35
|
+
return () => {
|
|
36
|
+
observer.disconnect();
|
|
37
|
+
window.removeEventListener('popstate', handlePop);
|
|
38
|
+
};
|
|
39
|
+
}, []);
|
|
40
|
+
|
|
41
|
+
return (
|
|
42
|
+
<p
|
|
43
|
+
id="route-announcer"
|
|
44
|
+
role="alert"
|
|
45
|
+
// Off-screen element with 'best' browser support
|
|
46
|
+
style={{
|
|
47
|
+
border: 0,
|
|
48
|
+
clip: 'rect(1px 1px 1px 1px)', // IE-style CSS for compatibility
|
|
49
|
+
height: '1px',
|
|
50
|
+
margin: '-1px',
|
|
51
|
+
overflow: 'hidden',
|
|
52
|
+
padding: 0,
|
|
53
|
+
position: 'absolute',
|
|
54
|
+
width: '1px',
|
|
55
|
+
whiteSpace: 'nowrap',
|
|
56
|
+
wordWrap: 'normal',
|
|
57
|
+
}}
|
|
58
|
+
>
|
|
59
|
+
{pageTitle}
|
|
60
|
+
</p>
|
|
61
|
+
);
|
|
62
|
+
}
|
|
63
|
+
|
|
64
|
+
export default RouteAnnouncer;
|
|
@@ -629,11 +629,11 @@ export const styleDataToStyleObject = (key, value, prefix = '') => {
|
|
|
629
629
|
* Generate styles object from data
|
|
630
630
|
*
|
|
631
631
|
* @function buildStyleObjectFromData
|
|
632
|
-
* @param {Object}
|
|
632
|
+
* @param {Object} data A block data object
|
|
633
633
|
* @param {string} prefix The prefix (could be dragged from a recursive call, initially empty)
|
|
634
634
|
* @return {Object} The style object ready to be passed as prop
|
|
635
635
|
*/
|
|
636
|
-
export const buildStyleObjectFromData = (
|
|
636
|
+
export const buildStyleObjectFromData = (data = {}, prefix = '') => {
|
|
637
637
|
// style wrapper object has the form:
|
|
638
638
|
// const styles = {
|
|
639
639
|
// color: 'red',
|
|
@@ -641,39 +641,79 @@ export const buildStyleObjectFromData = (obj = {}, prefix = '') => {
|
|
|
641
641
|
// }
|
|
642
642
|
// Returns: {'--background-color: '#AABBCC'}
|
|
643
643
|
|
|
644
|
-
|
|
645
|
-
Object.
|
|
646
|
-
.
|
|
647
|
-
|
|
648
|
-
(
|
|
649
|
-
|
|
650
|
-
|
|
651
|
-
|
|
652
|
-
|
|
653
|
-
|
|
654
|
-
|
|
655
|
-
|
|
656
|
-
|
|
657
|
-
|
|
658
|
-
|
|
659
|
-
|
|
660
|
-
|
|
661
|
-
|
|
662
|
-
|
|
663
|
-
|
|
664
|
-
|
|
665
|
-
|
|
666
|
-
|
|
667
|
-
|
|
668
|
-
|
|
669
|
-
|
|
670
|
-
|
|
671
|
-
|
|
672
|
-
|
|
673
|
-
|
|
674
|
-
|
|
644
|
+
function recursiveBuildStyleObjectFromData(obj, prefix) {
|
|
645
|
+
return Object.fromEntries(
|
|
646
|
+
Object.entries(obj)
|
|
647
|
+
.filter(([k, v]) => k.startsWith('--') || isObject(v))
|
|
648
|
+
.reduce(
|
|
649
|
+
(acc, [k, v]) => [
|
|
650
|
+
...acc,
|
|
651
|
+
// Kept for easy debugging
|
|
652
|
+
// ...(() => {
|
|
653
|
+
// if (isObject(v)) {
|
|
654
|
+
// return Object.entries(
|
|
655
|
+
// buildStyleObjectFromData(
|
|
656
|
+
// v,
|
|
657
|
+
// `${k.endsWith(':noprefix') ? '' : `${prefix}${k}--`}`,
|
|
658
|
+
// ),
|
|
659
|
+
// );
|
|
660
|
+
// }
|
|
661
|
+
// return [styleDataToStyleObject(k, v, prefix)];
|
|
662
|
+
// })(),
|
|
663
|
+
...(isObject(v)
|
|
664
|
+
? Object.entries(
|
|
665
|
+
recursiveBuildStyleObjectFromData(
|
|
666
|
+
v,
|
|
667
|
+
`${k.endsWith(':noprefix') ? '' : `${prefix}${k}--`}`, // We don't add a prefix if the key ends with the marker suffix
|
|
668
|
+
),
|
|
669
|
+
)
|
|
670
|
+
: [styleDataToStyleObject(k, v, prefix)]),
|
|
671
|
+
],
|
|
672
|
+
[],
|
|
673
|
+
)
|
|
674
|
+
.filter((v) => !!v),
|
|
675
|
+
);
|
|
676
|
+
}
|
|
677
|
+
|
|
678
|
+
// If the block has a `@type`, it's a full data block object
|
|
679
|
+
// Then apply the style enhancers
|
|
680
|
+
if (data['@type']) {
|
|
681
|
+
const styleObj = data.styles || {};
|
|
682
|
+
const stylesFromCSSproperties = recursiveBuildStyleObjectFromData(
|
|
683
|
+
styleObj,
|
|
684
|
+
prefix,
|
|
685
|
+
);
|
|
686
|
+
|
|
687
|
+
let stylesFromObjectStyleEnhancers = {};
|
|
688
|
+
const enhancers = config.getUtilities({
|
|
689
|
+
type: 'styleWrapperStyleObjectEnhancer',
|
|
690
|
+
});
|
|
691
|
+
|
|
692
|
+
enhancers.forEach(({ method }) => {
|
|
693
|
+
stylesFromObjectStyleEnhancers = {
|
|
694
|
+
...stylesFromObjectStyleEnhancers,
|
|
695
|
+
...method(data),
|
|
696
|
+
};
|
|
697
|
+
});
|
|
698
|
+
|
|
699
|
+
return { ...stylesFromCSSproperties, ...stylesFromObjectStyleEnhancers };
|
|
700
|
+
} else {
|
|
701
|
+
return recursiveBuildStyleObjectFromData(data, prefix);
|
|
702
|
+
}
|
|
675
703
|
};
|
|
676
704
|
|
|
705
|
+
/**
|
|
706
|
+
* Find a matching style by name given a style definition
|
|
707
|
+
*
|
|
708
|
+
* @function findStyleByName
|
|
709
|
+
* @param {Object} styleDefinitions An object with the style definitions
|
|
710
|
+
* @param {string} name The name of the style to find
|
|
711
|
+
* @return {Object} The style object of the matching name
|
|
712
|
+
*/
|
|
713
|
+
export function findStyleByName(styleDefinitions, name) {
|
|
714
|
+
return styleDefinitions.find((color) => color.name === name)?.style;
|
|
715
|
+
}
|
|
716
|
+
|
|
677
717
|
/**
|
|
678
718
|
* Return previous/next blocks given the content object and the current block id
|
|
679
719
|
*
|
|
@@ -24,6 +24,7 @@ import {
|
|
|
24
24
|
findBlocks,
|
|
25
25
|
findContainer,
|
|
26
26
|
isBlockContainer,
|
|
27
|
+
findStyleByName,
|
|
27
28
|
} from './Blocks';
|
|
28
29
|
|
|
29
30
|
import config from '@plone/volto/registry';
|
|
@@ -1103,38 +1104,68 @@ describe('Blocks', () => {
|
|
|
1103
1104
|
});
|
|
1104
1105
|
|
|
1105
1106
|
describe('buildStyleObjectFromData', () => {
|
|
1107
|
+
beforeEach(() => {
|
|
1108
|
+
function blockThemesEnhancer(data) {
|
|
1109
|
+
const blockConfig = config.blocks.blocksConfig[data['@type']];
|
|
1110
|
+
const blockStyleDefinitions =
|
|
1111
|
+
// We look up for the blockThemes in the block's data, then in the global config
|
|
1112
|
+
// We keep data.colors for BBB, but data.themes should be used
|
|
1113
|
+
blockConfig.themes ||
|
|
1114
|
+
blockConfig.colors ||
|
|
1115
|
+
config.blocks.themes ||
|
|
1116
|
+
[];
|
|
1117
|
+
return data.theme
|
|
1118
|
+
? findStyleByName(blockStyleDefinitions, data.theme)
|
|
1119
|
+
: {};
|
|
1120
|
+
}
|
|
1121
|
+
config.registerUtility({
|
|
1122
|
+
name: 'blockThemesEnhancer',
|
|
1123
|
+
type: 'styleWrapperStyleObjectEnhancer',
|
|
1124
|
+
method: blockThemesEnhancer,
|
|
1125
|
+
});
|
|
1126
|
+
});
|
|
1127
|
+
|
|
1106
1128
|
it('Understands style converter for style values, no styles found', () => {
|
|
1107
|
-
const
|
|
1108
|
-
|
|
1109
|
-
|
|
1129
|
+
const data = {
|
|
1130
|
+
'@type': 'text',
|
|
1131
|
+
styles: {
|
|
1132
|
+
color: 'red',
|
|
1133
|
+
backgroundColor: '#FFF',
|
|
1134
|
+
},
|
|
1110
1135
|
};
|
|
1111
|
-
expect(buildStyleObjectFromData(
|
|
1136
|
+
expect(buildStyleObjectFromData(data)).toEqual({});
|
|
1112
1137
|
});
|
|
1113
1138
|
|
|
1114
1139
|
it('Understands style converter for style values', () => {
|
|
1115
|
-
const
|
|
1116
|
-
|
|
1117
|
-
|
|
1140
|
+
const data = {
|
|
1141
|
+
'@type': 'text',
|
|
1142
|
+
styles: {
|
|
1143
|
+
color: 'red',
|
|
1144
|
+
'--background-color': '#FFF',
|
|
1145
|
+
},
|
|
1118
1146
|
};
|
|
1119
|
-
expect(buildStyleObjectFromData(
|
|
1147
|
+
expect(buildStyleObjectFromData(data)).toEqual({
|
|
1120
1148
|
'--background-color': '#FFF',
|
|
1121
1149
|
});
|
|
1122
1150
|
});
|
|
1123
1151
|
|
|
1124
1152
|
it('Supports multiple nested levels', () => {
|
|
1125
|
-
const
|
|
1126
|
-
'
|
|
1127
|
-
|
|
1128
|
-
|
|
1129
|
-
|
|
1130
|
-
|
|
1131
|
-
|
|
1132
|
-
'--foo': '
|
|
1133
|
-
|
|
1153
|
+
const data = {
|
|
1154
|
+
'@type': 'text',
|
|
1155
|
+
styles: {
|
|
1156
|
+
'--color': 'red',
|
|
1157
|
+
backgroundColor: '#AABBCC',
|
|
1158
|
+
nested: {
|
|
1159
|
+
l1: 'white',
|
|
1160
|
+
'--foo': 'white',
|
|
1161
|
+
level2: {
|
|
1162
|
+
'--foo': '#fff',
|
|
1163
|
+
bar: '#000',
|
|
1164
|
+
},
|
|
1134
1165
|
},
|
|
1135
1166
|
},
|
|
1136
1167
|
};
|
|
1137
|
-
expect(buildStyleObjectFromData(
|
|
1168
|
+
expect(buildStyleObjectFromData(data)).toEqual({
|
|
1138
1169
|
'--color': 'red',
|
|
1139
1170
|
'--nested--foo': 'white',
|
|
1140
1171
|
'--nested--level2--foo': '#fff',
|
|
@@ -1142,22 +1173,168 @@ describe('Blocks', () => {
|
|
|
1142
1173
|
});
|
|
1143
1174
|
|
|
1144
1175
|
it('Supports multiple nested levels and optional inclusion of the name of the level', () => {
|
|
1145
|
-
const
|
|
1176
|
+
const data = {
|
|
1177
|
+
'@type': 'text',
|
|
1178
|
+
styles: {
|
|
1179
|
+
'--color': 'red',
|
|
1180
|
+
backgroundColor: '#AABBCC',
|
|
1181
|
+
'nested:noprefix': {
|
|
1182
|
+
l1: 'white',
|
|
1183
|
+
'--foo': 'white',
|
|
1184
|
+
level2: {
|
|
1185
|
+
'--foo': '#fff',
|
|
1186
|
+
bar: '#000',
|
|
1187
|
+
},
|
|
1188
|
+
},
|
|
1189
|
+
},
|
|
1190
|
+
};
|
|
1191
|
+
expect(buildStyleObjectFromData(data)).toEqual({
|
|
1146
1192
|
'--color': 'red',
|
|
1147
|
-
|
|
1148
|
-
'
|
|
1149
|
-
|
|
1150
|
-
|
|
1151
|
-
|
|
1152
|
-
|
|
1153
|
-
|
|
1193
|
+
'--foo': 'white',
|
|
1194
|
+
'--level2--foo': '#fff',
|
|
1195
|
+
});
|
|
1196
|
+
});
|
|
1197
|
+
|
|
1198
|
+
it('Supports named theme block - with global config', () => {
|
|
1199
|
+
config.blocks.themes = [
|
|
1200
|
+
{
|
|
1201
|
+
style: {
|
|
1202
|
+
'--primary-color': '#fff',
|
|
1203
|
+
'--primary-foreground-color': '#ecebeb',
|
|
1204
|
+
},
|
|
1205
|
+
name: 'default',
|
|
1206
|
+
label: 'Default',
|
|
1207
|
+
},
|
|
1208
|
+
{
|
|
1209
|
+
style: {
|
|
1210
|
+
'--primary-color': '#000',
|
|
1211
|
+
'--primary-foreground-color': '#fff',
|
|
1212
|
+
},
|
|
1213
|
+
name: 'primary',
|
|
1214
|
+
label: 'Primary',
|
|
1215
|
+
},
|
|
1216
|
+
];
|
|
1217
|
+
const data = {
|
|
1218
|
+
'@type': 'text',
|
|
1219
|
+
theme: 'primary',
|
|
1220
|
+
};
|
|
1221
|
+
expect(buildStyleObjectFromData(data)).toEqual({
|
|
1222
|
+
'--primary-color': '#000',
|
|
1223
|
+
'--primary-foreground-color': '#fff',
|
|
1224
|
+
});
|
|
1225
|
+
});
|
|
1226
|
+
|
|
1227
|
+
it('Supports named theme block - with local block themes config', () => {
|
|
1228
|
+
config.blocks.themes = [
|
|
1229
|
+
{
|
|
1230
|
+
style: {
|
|
1231
|
+
'--primary-color': '#fff',
|
|
1232
|
+
'--primary-foreground-color': '#ecebeb',
|
|
1233
|
+
},
|
|
1234
|
+
name: 'default',
|
|
1235
|
+
label: 'Default',
|
|
1236
|
+
},
|
|
1237
|
+
{
|
|
1238
|
+
style: {
|
|
1239
|
+
'--primary-color': '#000',
|
|
1240
|
+
'--primary-foreground-color': '#fff',
|
|
1241
|
+
},
|
|
1242
|
+
name: 'primary',
|
|
1243
|
+
label: 'Primary',
|
|
1244
|
+
},
|
|
1245
|
+
];
|
|
1246
|
+
const themes = [
|
|
1247
|
+
{
|
|
1248
|
+
style: {
|
|
1249
|
+
'--primary-color': '#fff',
|
|
1250
|
+
'--primary-foreground-color': '#ecebeb',
|
|
1251
|
+
},
|
|
1252
|
+
name: 'default',
|
|
1253
|
+
label: 'Default',
|
|
1254
|
+
},
|
|
1255
|
+
{
|
|
1256
|
+
style: {
|
|
1257
|
+
'--secondary-color': '#bbb',
|
|
1258
|
+
'--secondary-foreground-color': '#ddd',
|
|
1154
1259
|
},
|
|
1260
|
+
name: 'secondary',
|
|
1261
|
+
label: 'Secondary',
|
|
1155
1262
|
},
|
|
1263
|
+
];
|
|
1264
|
+
config.blocks.blocksConfig.text.themes = themes;
|
|
1265
|
+
const data = {
|
|
1266
|
+
'@type': 'text',
|
|
1267
|
+
theme: 'secondary',
|
|
1156
1268
|
};
|
|
1157
|
-
|
|
1269
|
+
|
|
1270
|
+
expect(buildStyleObjectFromData(data)).toEqual({
|
|
1271
|
+
'--secondary-color': '#bbb',
|
|
1272
|
+
'--secondary-foreground-color': '#ddd',
|
|
1273
|
+
});
|
|
1274
|
+
});
|
|
1275
|
+
|
|
1276
|
+
it('All together now - named theme block - with local block themes config', () => {
|
|
1277
|
+
config.blocks.blocksThemes = [
|
|
1278
|
+
{
|
|
1279
|
+
style: {
|
|
1280
|
+
'--primary-color': '#fff',
|
|
1281
|
+
'--primary-foreground-color': '#ecebeb',
|
|
1282
|
+
},
|
|
1283
|
+
name: 'default',
|
|
1284
|
+
label: 'Default',
|
|
1285
|
+
},
|
|
1286
|
+
{
|
|
1287
|
+
style: {
|
|
1288
|
+
'--primary-color': '#000',
|
|
1289
|
+
'--primary-foreground-color': '#fff',
|
|
1290
|
+
},
|
|
1291
|
+
name: 'primary',
|
|
1292
|
+
label: 'Primary',
|
|
1293
|
+
},
|
|
1294
|
+
];
|
|
1295
|
+
const themes = [
|
|
1296
|
+
{
|
|
1297
|
+
style: {
|
|
1298
|
+
'--primary-color': '#fff',
|
|
1299
|
+
'--primary-foreground-color': '#ecebeb',
|
|
1300
|
+
},
|
|
1301
|
+
name: 'default',
|
|
1302
|
+
label: 'Default',
|
|
1303
|
+
},
|
|
1304
|
+
{
|
|
1305
|
+
style: {
|
|
1306
|
+
'--secondary-color': '#bbb',
|
|
1307
|
+
'--secondary-foreground-color': '#ddd',
|
|
1308
|
+
},
|
|
1309
|
+
name: 'secondary',
|
|
1310
|
+
label: 'Secondary',
|
|
1311
|
+
},
|
|
1312
|
+
];
|
|
1313
|
+
|
|
1314
|
+
const data = {
|
|
1315
|
+
'@type': 'text',
|
|
1316
|
+
styles: {
|
|
1317
|
+
'--color': 'red',
|
|
1318
|
+
backgroundColor: '#AABBCC',
|
|
1319
|
+
'nested:noprefix': {
|
|
1320
|
+
l1: 'white',
|
|
1321
|
+
'--foo': 'white',
|
|
1322
|
+
level2: {
|
|
1323
|
+
'--foo': '#fff',
|
|
1324
|
+
bar: '#000',
|
|
1325
|
+
},
|
|
1326
|
+
},
|
|
1327
|
+
},
|
|
1328
|
+
theme: 'secondary',
|
|
1329
|
+
themes,
|
|
1330
|
+
};
|
|
1331
|
+
|
|
1332
|
+
expect(buildStyleObjectFromData(data)).toEqual({
|
|
1158
1333
|
'--color': 'red',
|
|
1159
1334
|
'--foo': 'white',
|
|
1160
1335
|
'--level2--foo': '#fff',
|
|
1336
|
+
'--secondary-color': '#bbb',
|
|
1337
|
+
'--secondary-foreground-color': '#ddd',
|
|
1161
1338
|
});
|
|
1162
1339
|
});
|
|
1163
1340
|
});
|
|
@@ -4,8 +4,5 @@ export function getBlocksTocEntries(properties: any, tocData: any): {
|
|
|
4
4
|
tocEntries: {};
|
|
5
5
|
tocEntriesLayout: any[];
|
|
6
6
|
};
|
|
7
|
-
declare const _default:
|
|
8
|
-
WrappedComponent: React.ComponentType<any>;
|
|
9
|
-
};
|
|
7
|
+
declare const _default: (props: any) => import("react/jsx-runtime").JSX.Element;
|
|
10
8
|
export default _default;
|
|
11
|
-
import React from 'react';
|
|
@@ -1,5 +1,10 @@
|
|
|
1
|
-
|
|
2
|
-
|
|
3
|
-
|
|
4
|
-
|
|
5
|
-
import
|
|
1
|
+
export default View;
|
|
2
|
+
declare function View({ data, tocEntries }: {
|
|
3
|
+
data: any;
|
|
4
|
+
tocEntries: any;
|
|
5
|
+
}): import("react/jsx-runtime").JSX.Element;
|
|
6
|
+
declare namespace View {
|
|
7
|
+
namespace propTypes {
|
|
8
|
+
let properties: any;
|
|
9
|
+
}
|
|
10
|
+
}
|
|
@@ -1,5 +1,10 @@
|
|
|
1
|
-
|
|
2
|
-
|
|
3
|
-
|
|
4
|
-
|
|
5
|
-
import
|
|
1
|
+
export default View;
|
|
2
|
+
declare function View({ data, tocEntries }: {
|
|
3
|
+
data: any;
|
|
4
|
+
tocEntries: any;
|
|
5
|
+
}): import("react/jsx-runtime").JSX.Element;
|
|
6
|
+
declare namespace View {
|
|
7
|
+
namespace propTypes {
|
|
8
|
+
let properties: any;
|
|
9
|
+
}
|
|
10
|
+
}
|
|
@@ -2,15 +2,27 @@ export default ToCVariations;
|
|
|
2
2
|
declare const ToCVariations: ({
|
|
3
3
|
id: string;
|
|
4
4
|
title: string;
|
|
5
|
-
view:
|
|
6
|
-
|
|
5
|
+
view: {
|
|
6
|
+
({ data, tocEntries }: {
|
|
7
|
+
data: any;
|
|
8
|
+
tocEntries: any;
|
|
9
|
+
}): import("react/jsx-runtime").JSX.Element;
|
|
10
|
+
propTypes: {
|
|
11
|
+
properties: any;
|
|
12
|
+
};
|
|
7
13
|
};
|
|
8
14
|
isDefault: boolean;
|
|
9
15
|
} | {
|
|
10
16
|
id: string;
|
|
11
17
|
title: string;
|
|
12
|
-
view:
|
|
13
|
-
|
|
18
|
+
view: {
|
|
19
|
+
({ data, tocEntries }: {
|
|
20
|
+
data: any;
|
|
21
|
+
tocEntries: any;
|
|
22
|
+
}): import("react/jsx-runtime").JSX.Element;
|
|
23
|
+
propTypes: {
|
|
24
|
+
properties: any;
|
|
25
|
+
};
|
|
14
26
|
};
|
|
15
27
|
isDefault?: undefined;
|
|
16
28
|
})[];
|
|
@@ -134,6 +134,15 @@ export function applySchemaDefaults({ data, schema, intl }: {
|
|
|
134
134
|
* @return {Object} Derived data, with the defaults extracted from the schema
|
|
135
135
|
*/
|
|
136
136
|
export function applyBlockDefaults({ data, intl, navRoot, contentType, ...rest }: any, blocksConfig: any): any;
|
|
137
|
+
/**
|
|
138
|
+
* Find a matching style by name given a style definition
|
|
139
|
+
*
|
|
140
|
+
* @function findStyleByName
|
|
141
|
+
* @param {Object} styleDefinitions An object with the style definitions
|
|
142
|
+
* @param {string} name The name of the style to find
|
|
143
|
+
* @return {Object} The style object of the matching name
|
|
144
|
+
*/
|
|
145
|
+
export function findStyleByName(styleDefinitions: any, name: string): any;
|
|
137
146
|
/**
|
|
138
147
|
* Check if a block is a container block
|
|
139
148
|
* check blocks from data as well since some add-ons use that
|
|
@@ -168,7 +177,7 @@ export function styleToClassName(key: any, value: any, prefix?: string): any;
|
|
|
168
177
|
export function buildStyleClassNamesFromData(obj?: {}, prefix?: string): any;
|
|
169
178
|
export function buildStyleClassNamesExtenders({ block, content, data, classNames, }: any): any[];
|
|
170
179
|
export function styleDataToStyleObject(key: any, value: any, prefix?: string): any[];
|
|
171
|
-
export function buildStyleObjectFromData(
|
|
180
|
+
export function buildStyleObjectFromData(data?: any, prefix?: string): any;
|
|
172
181
|
export function getPreviousNextBlock({ content, block }: any): any[];
|
|
173
182
|
export function getBlocksHierarchy(properties: any): any;
|
|
174
183
|
export function findContainer(formData: object, { containerId }: {
|