@eeacms/volto-hero-block 0.1.0 → 0.1.3

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 CHANGED
@@ -1,5 +1,40 @@
1
- # Changelog
1
+ ### Changelog
2
2
 
3
- ## 0.1.0
3
+ All notable changes to this project will be documented in this file. Dates are displayed in UTC.
4
4
 
5
- - Initial release
5
+ Generated by [`auto-changelog`](https://github.com/CookPete/auto-changelog).
6
+
7
+ #### [0.1.3](https://github.com/eea/volto-hero-block/compare/0.1.2...0.1.3)
8
+
9
+ - Cleanup themeing options [`1832d55`](https://github.com/eea/volto-hero-block/commit/1832d551c96f02dd1905e8acc1b1c31c09caf38d)
10
+
11
+ #### [0.1.2](https://github.com/eea/volto-hero-block/compare/0.1.1...0.1.2)
12
+
13
+ > 16 June 2022
14
+
15
+ - Release [`#3`](https://github.com/eea/volto-hero-block/pull/3)
16
+ - change(hero): wrap hero-block-image within a wrapper class [`2802c41`](https://github.com/eea/volto-hero-block/commit/2802c41ee8eba4c34bf6d4b4766ebafb24056602)
17
+ - change(hero): added spaced and inverted options to the main schema [`b6865cd`](https://github.com/eea/volto-hero-block/commit/b6865cdc6dfae0d486f43fccfb31fa555af3a536)
18
+ - change(hero): output h2 from slate instead of p tag [`0b2a4c5`](https://github.com/eea/volto-hero-block/commit/0b2a4c5070cc2bf97f31ff4cf74ade0e27434d91)
19
+
20
+ #### [0.1.1](https://github.com/eea/volto-hero-block/compare/0.1.0...0.1.1)
21
+
22
+ > 13 June 2022
23
+
24
+ - Add hero block [`#2`](https://github.com/eea/volto-hero-block/pull/2)
25
+ - change(hero): added image overlay option [`647ef2c`](https://github.com/eea/volto-hero-block/commit/647ef2ce68848ac38b71977485021b17e8c2f540)
26
+ - Fix Hero image type [`fb2188a`](https://github.com/eea/volto-hero-block/commit/fb2188ac604cfc57ba26ea482e799ca867a412ad)
27
+ - Fix external vs internal image [`5e447e9`](https://github.com/eea/volto-hero-block/commit/5e447e9a4e35229d9a29b74ad230a2e1e659bbea)
28
+ - Fix block title [`db8de23`](https://github.com/eea/volto-hero-block/commit/db8de237f523e8cb9b96c2702818b529805fd36e)
29
+ - Support external images [`196902a`](https://github.com/eea/volto-hero-block/commit/196902ac0214cefb8a4bdc643f0424bc7c318282)
30
+ - Update slate footnote support [`c1522b4`](https://github.com/eea/volto-hero-block/commit/c1522b4164dbe6de01771d211d7e0bf3009f44d4)
31
+ - Use justify content for text and button as well [`08599cc`](https://github.com/eea/volto-hero-block/commit/08599cc45546d9b349128c4f8ce9c01318385811)
32
+ - Add dependencies [`30e2881`](https://github.com/eea/volto-hero-block/commit/30e2881a2a97a899e7f4cc614a0405c300ac6fee)
33
+
34
+ #### 0.1.0
35
+
36
+ > 10 June 2022
37
+
38
+ - Empty release [`#1`](https://github.com/eea/volto-hero-block/pull/1)
39
+ - Initial commit [`799ed92`](https://github.com/eea/volto-hero-block/commit/799ed92e506b9b0faded334c019f4a8ffc4b8d43)
40
+ - Initial commit [`b21bcfd`](https://github.com/eea/volto-hero-block/commit/b21bcfd42c775acc84179272fac0d6ecaad71430)
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@eeacms/volto-hero-block",
3
- "version": "0.1.0",
3
+ "version": "0.1.3",
4
4
  "description": "@eeacms/volto-hero-block: Volto add-on",
5
5
  "main": "src/index.js",
6
6
  "author": "European Environment Agency: IDM2 A-Team",
@@ -16,10 +16,16 @@
16
16
  "type": "git",
17
17
  "url": "git@github.com:eea/volto-hero-block.git"
18
18
  },
19
+ "addons": [
20
+ "@eeacms/volto-object-widget",
21
+ "volto-slate"
22
+ ],
19
23
  "dependencies": {
20
- "@plone/scripts": "*"
24
+ "volto-slate": "*",
25
+ "@eeacms/volto-object-widget": "*"
21
26
  },
22
27
  "devDependencies": {
28
+ "@plone/scripts": "*",
23
29
  "@cypress/code-coverage": "^3.9.5",
24
30
  "babel-plugin-transform-class-properties": "^6.24.1"
25
31
  },
@@ -0,0 +1,124 @@
1
+ import React from 'react';
2
+ import cx from 'classnames';
3
+ import { connect } from 'react-redux';
4
+ import config from '@plone/volto/registry';
5
+ import {
6
+ BlockDataForm,
7
+ SidebarPortal,
8
+ UniversalLink,
9
+ } from '@plone/volto/components';
10
+ import SlateEditor from 'volto-slate/editor/SlateEditor';
11
+ import { handleKey } from 'volto-slate/blocks/Text/keyboard';
12
+ import { uploadContent, saveSlateBlockSelection } from 'volto-slate/actions';
13
+
14
+ import { createSlateHeader } from '@eeacms/volto-hero-block/helpers';
15
+
16
+ import Hero from './Hero';
17
+ import getSchema from './schema';
18
+
19
+ const Metadata = ({ buttonLabel, buttonLink, inverted, styles }) => {
20
+ const { buttonVariant } = styles || {};
21
+
22
+ return buttonLabel ? (
23
+ <UniversalLink
24
+ className={cx('ui button', buttonVariant, { inverted })}
25
+ href={buttonLink || ''}
26
+ >
27
+ {buttonLabel}
28
+ </UniversalLink>
29
+ ) : (
30
+ ''
31
+ );
32
+ };
33
+
34
+ const Edit = (props) => {
35
+ const { slate } = config.settings;
36
+ const {
37
+ data = {},
38
+ block = null,
39
+ selected = false,
40
+ index,
41
+ properties,
42
+ onChangeBlock,
43
+ onSelectBlock,
44
+ } = props;
45
+ const { text } = data;
46
+ const schema = React.useMemo(() => getSchema(props), [props]);
47
+
48
+ const withBlockProperties = React.useCallback(
49
+ (editor) => {
50
+ editor.getBlockProps = () => props;
51
+ return editor;
52
+ },
53
+ [props],
54
+ );
55
+
56
+ const handleFocus = React.useCallback(() => {
57
+ if (!selected) {
58
+ onSelectBlock(block);
59
+ }
60
+ }, [onSelectBlock, selected, block]);
61
+
62
+ return (
63
+ <>
64
+ <Hero {...data}>
65
+ <Hero.Text {...data}>
66
+ <SlateEditor
67
+ index={index}
68
+ properties={properties}
69
+ extensions={slate.textblockExtensions}
70
+ renderExtensions={[withBlockProperties]}
71
+ value={createSlateHeader(text)}
72
+ onChange={(text) => {
73
+ onChangeBlock(block, {
74
+ ...data,
75
+ text,
76
+ });
77
+ }}
78
+ block={block}
79
+ onFocus={handleFocus}
80
+ onKeyDown={handleKey}
81
+ selected={selected}
82
+ placeholder="Add text..."
83
+ slateSettings={slate}
84
+ />
85
+ </Hero.Text>
86
+ <Hero.Meta {...data}>
87
+ <Metadata {...data} />
88
+ </Hero.Meta>
89
+ </Hero>
90
+
91
+ <SidebarPortal selected={selected}>
92
+ <BlockDataForm
93
+ block={block}
94
+ schema={schema}
95
+ title={schema.title}
96
+ onChangeField={(id, value) => {
97
+ onChangeBlock(block, {
98
+ ...data,
99
+ [id]: value,
100
+ });
101
+ }}
102
+ formData={data}
103
+ />
104
+ </SidebarPortal>
105
+ </>
106
+ );
107
+ };
108
+
109
+ export default connect(
110
+ (state, props) => {
111
+ const blockId = props.block;
112
+ return {
113
+ defaultSelection: blockId
114
+ ? state.slate_block_selections?.[blockId]
115
+ : null,
116
+ uploadRequest: state.upload_content?.[props.block]?.upload || {},
117
+ uploadedContent: state.upload_content?.[props.block]?.data || {},
118
+ };
119
+ },
120
+ {
121
+ uploadContent,
122
+ saveSlateBlockSelection, // needed as editor blockProps
123
+ },
124
+ )(Edit);
@@ -0,0 +1,102 @@
1
+ import React from 'react';
2
+ import cx from 'classnames';
3
+ import PropTypes from 'prop-types';
4
+ import { isInternalURL } from '@plone/volto/helpers/Url/Url';
5
+
6
+ Hero.propTypes = {
7
+ image: PropTypes.string,
8
+ fullWidth: PropTypes.bool,
9
+ fullHeight: PropTypes.bool,
10
+ alignContent: PropTypes.string,
11
+ justifyContent: PropTypes.string,
12
+ backgroundVariant: PropTypes.string,
13
+ quoted: PropTypes.bool,
14
+ spaced: PropTypes.bool,
15
+ inverted: PropTypes.bool,
16
+ textVariant: PropTypes.string,
17
+ };
18
+
19
+ function Hero({
20
+ image,
21
+ overlay = true,
22
+ fullWidth = true,
23
+ fullHeight = true,
24
+ children,
25
+ spaced = false,
26
+ inverted = true,
27
+ styles,
28
+ }) {
29
+ const isExternal = !isInternalURL(image);
30
+ const { alignContent = 'center', backgroundVariant = 'primary' } =
31
+ styles || {};
32
+ return (
33
+ <div
34
+ className={cx(
35
+ 'eea hero-block',
36
+ { spaced },
37
+ { inverted },
38
+ !image && backgroundVariant && `color-bg-${backgroundVariant}`,
39
+ {
40
+ 'full-height': fullHeight,
41
+ },
42
+ )}
43
+ >
44
+ <div
45
+ className={cx('hero-block-image-wrapper', {
46
+ 'full-width': fullWidth,
47
+ })}
48
+ >
49
+ <div
50
+ className={cx('hero-block-image')}
51
+ style={
52
+ image
53
+ ? {
54
+ backgroundImage: isExternal
55
+ ? `url(${image})`
56
+ : `url(${image}/@@images/image/huge)`,
57
+ }
58
+ : {}
59
+ }
60
+ />
61
+ {image && overlay && (
62
+ <div className="hero-block-image-overlay dark-overlay-4"></div>
63
+ )}
64
+ </div>
65
+ <div
66
+ className={cx(
67
+ 'hero-block-inner-wrapper d-flex ui container',
68
+ `flex-items-${alignContent}`,
69
+ )}
70
+ >
71
+ <div className="hero-block-body">{children}</div>
72
+ </div>
73
+ </div>
74
+ );
75
+ }
76
+
77
+ Hero.Text = ({ children, styles }) => {
78
+ const { textVariant = 'white', justifyContent = 'left', quoted } =
79
+ styles || {};
80
+ return (
81
+ <div
82
+ className={cx(
83
+ 'hero-block-text',
84
+ `color-fg-${textVariant}`,
85
+ `text-${justifyContent}`,
86
+ )}
87
+ >
88
+ <div className={cx({ quoted })}>{children}</div>
89
+ </div>
90
+ );
91
+ };
92
+
93
+ Hero.Meta = ({ children, styles }) => {
94
+ const { justifyContent = 'left' } = styles || {};
95
+ return (
96
+ <div className={cx('hero-block-meta', `text-${justifyContent}`)}>
97
+ {children}
98
+ </div>
99
+ );
100
+ };
101
+
102
+ export default Hero;
@@ -0,0 +1,35 @@
1
+ import React from 'react';
2
+ import cx from 'classnames';
3
+ import { UniversalLink } from '@plone/volto/components';
4
+ import Hero from './Hero';
5
+ import { serializeText } from '@eeacms/volto-hero-block/helpers';
6
+
7
+ const Metadata = ({ buttonLabel, buttonLink, inverted, styles }) => {
8
+ const { buttonVariant = 'white' } = styles || {};
9
+
10
+ return buttonLabel ? (
11
+ <UniversalLink
12
+ className={cx('ui button', buttonVariant, { inverted })}
13
+ href={buttonLink || ''}
14
+ >
15
+ {buttonLabel}
16
+ </UniversalLink>
17
+ ) : (
18
+ ''
19
+ );
20
+ };
21
+
22
+ const View = (props) => {
23
+ const { data = {} } = props;
24
+ const { text } = data;
25
+ return (
26
+ <Hero {...data}>
27
+ <Hero.Text {...data}>{serializeText(text)}</Hero.Text>
28
+ <Hero.Meta {...data}>
29
+ <Metadata {...data} />
30
+ </Hero.Meta>
31
+ </Hero>
32
+ );
33
+ };
34
+
35
+ export default View;
@@ -0,0 +1,32 @@
1
+ import codeSVG from '@plone/volto/icons/code.svg';
2
+ import HeroEdit from './Edit';
3
+ import HeroView from './View';
4
+ import { stylingSchema } from './schema';
5
+
6
+ export default (config) => {
7
+ config.blocks.blocksConfig.hero = {
8
+ id: 'hero',
9
+ title: 'Hero',
10
+ icon: codeSVG,
11
+ group: 'common',
12
+ edit: HeroEdit,
13
+ view: HeroView,
14
+ blockHasOwnFocusManagement: true,
15
+ stylesSchema: stylingSchema,
16
+ enableStyling: true,
17
+ restricted: false,
18
+ mostUsed: false,
19
+ sidebarTab: 1,
20
+ security: {
21
+ addPermission: [],
22
+ view: [],
23
+ },
24
+ };
25
+
26
+ config.settings.blocksWithFootnotesSupport = {
27
+ ...(config.settings.blocksWithFootnotesSupport || {}),
28
+ hero: ['text'],
29
+ };
30
+
31
+ return config;
32
+ };
@@ -0,0 +1,124 @@
1
+ export default ({ data }) => {
2
+ return {
3
+ title: 'Hero',
4
+ fieldsets: [
5
+ {
6
+ id: 'default',
7
+ title: 'Default',
8
+ fields: [
9
+ 'fullWidth',
10
+ 'fullHeight',
11
+ 'spaced',
12
+ 'inverted',
13
+ 'buttonLabel',
14
+ 'buttonLink',
15
+ 'overlay',
16
+ 'image',
17
+ ],
18
+ },
19
+ ],
20
+ properties: {
21
+ fullWidth: {
22
+ title: 'Full width',
23
+ type: 'boolean',
24
+ defaultValue: true,
25
+ },
26
+ fullHeight: {
27
+ title: 'Full height',
28
+ type: 'boolean',
29
+ defaultValue: true,
30
+ },
31
+ spaced: {
32
+ title: 'Spaced',
33
+ type: 'boolean',
34
+ defaultValue: false,
35
+ },
36
+ inverted: {
37
+ title: 'Inverted',
38
+ type: 'boolean',
39
+ defaultValue: true,
40
+ },
41
+ buttonLabel: {
42
+ title: 'Button label',
43
+ widget: 'textarea',
44
+ },
45
+ buttonLink: {
46
+ title: 'Button link',
47
+ widget: 'url',
48
+ },
49
+ overlay: {
50
+ title: 'Image darken overlay',
51
+ type: 'boolean',
52
+ defaultValue: true,
53
+ },
54
+ image: {
55
+ title: 'Image',
56
+ widget: 'attachedimage',
57
+ },
58
+ },
59
+ required: [],
60
+ };
61
+ };
62
+
63
+ export const stylingSchema = ({ intl }) => ({
64
+ title: 'Hero style',
65
+ block: 'hero',
66
+ fieldsets: [
67
+ {
68
+ id: 'default',
69
+ title: 'Default',
70
+ fields: [
71
+ // 'quoted',
72
+ 'alignContent',
73
+ 'justifyContent',
74
+ 'backgroundVariant',
75
+ 'textVariant',
76
+ 'buttonVariant',
77
+ ],
78
+ },
79
+ ],
80
+ properties: {
81
+ quoted: {
82
+ title: 'Quoted',
83
+ type: 'boolean',
84
+ },
85
+ alignContent: {
86
+ title: 'Align content',
87
+ choices: [
88
+ ['start', 'Top'],
89
+ ['center', 'Center'],
90
+ ['end', 'Bottom'],
91
+ ],
92
+ },
93
+ justifyContent: {
94
+ title: 'Align Text',
95
+ widget: 'align',
96
+ },
97
+ backgroundVariant: {
98
+ title: 'Background theme',
99
+ choices: [
100
+ ['primary', 'Primary'],
101
+ ['secondary', 'Secondary'],
102
+ ['tertiary', 'Tertiary'],
103
+ ['grey', 'Grey'],
104
+ ],
105
+ },
106
+ textVariant: {
107
+ title: 'Text theme',
108
+ choices: [
109
+ ['primary', 'Primary'],
110
+ ['secondary', 'Secondary'],
111
+ ['tertiary', 'Tertiary'],
112
+ ],
113
+ },
114
+ buttonVariant: {
115
+ title: 'Button theme',
116
+ choices: [
117
+ ['primary', 'Primary'],
118
+ ['secondary', 'Secondary'],
119
+ ['tertiary', 'Tertiary'],
120
+ ],
121
+ },
122
+ },
123
+ required: [],
124
+ });
package/src/helpers.js ADDED
@@ -0,0 +1,17 @@
1
+ import { isArray } from 'lodash';
2
+ import { serializeNodes } from 'volto-slate/editor/render';
3
+
4
+ const createEmptyHeader = () => {
5
+ return {
6
+ type: 'h2',
7
+ children: [{ text: '' }],
8
+ };
9
+ };
10
+
11
+ export const createSlateHeader = (text) => {
12
+ return isArray(text) ? text : [createEmptyHeader()];
13
+ };
14
+
15
+ export const serializeText = (text) => {
16
+ return isArray(text) ? serializeNodes(text) : text;
17
+ };
package/src/index.js CHANGED
@@ -1,5 +1,7 @@
1
+ import installHeroBlock from '@eeacms/volto-hero-block/components/Blocks/Hero';
2
+
1
3
  const applyConfig = (config) => {
2
- return config;
4
+ return [installHeroBlock].reduce((acc, apply) => apply(acc), config);
3
5
  };
4
6
 
5
7
  export default applyConfig;