@eeacms/volto-clms-theme 1.0.127 → 1.0.129

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.
Files changed (27) hide show
  1. package/CHANGELOG.md +52 -1
  2. package/package.json +1 -1
  3. package/src/components/Blocks/CclUseCaseList/CclUseCaseListEdit.jsx +2 -2
  4. package/src/components/Blocks/CclUseCaseList/CclUseCaseListView.jsx +2 -2
  5. package/src/components/Blocks/CustomTemplates/VoltoSearchBlock/FilterList.jsx +7 -6
  6. package/src/components/Blocks/CustomTemplates/VoltoSearchBlock/SearchInput.jsx +6 -4
  7. package/src/components/Blocks/CustomTemplates/VoltoTabsBlock/CclVerticalFaqTabsView.jsx +7 -3
  8. package/src/components/Blocks/CustomTemplates/VoltoTabsBlock/CclVerticalTabsView.jsx +15 -10
  9. package/src/components/Blocks/CustomTemplates/VoltoTabsBlock/RoutingHOC.jsx +24 -4
  10. package/src/components/Blocks/customBlocks.js +3 -3
  11. package/src/components/Blocks/utils.js +7 -0
  12. package/src/components/CLMSDatasetDetailView/DownloadDataSetContent.jsx +7 -7
  13. package/src/components/CLMSDownloadCartView/CLMSCartContent.jsx +3 -1
  14. package/src/components/CLMSDownloadCartView/cartUtils.js +3 -0
  15. package/src/components/CLMSMeetingView/CLMSMeetingView.jsx +70 -25
  16. package/src/components/CLMSMeetingView/utils.js +29 -0
  17. package/src/components/CLMSProfileView/CLMSDeleteProfileView.jsx +5 -1
  18. package/src/components/CclCard/cards.less +2 -0
  19. package/src/components/CclDownloadTable/CclDownloadTable.jsx +7 -3
  20. package/src/components/Widgets/DownloadableFilesTableWidget.jsx +6 -0
  21. package/src/components/Widgets/taxonomyUtils.js +13 -2
  22. package/src/customizations/volto/components/manage/UniversalLink/UniversalLink.jsx +0 -1
  23. package/src/customizations/volto/components/theme/Header/Header.jsx +28 -3
  24. package/src/customizations/volto/components/theme/Navigation/Navigation.jsx +4 -3
  25. package/theme/clms/css/header.css +7 -1
  26. package/theme/clms/css/ownstyles.less +1 -2
  27. package/theme/clms/css/styles.less +7 -2
package/CHANGELOG.md CHANGED
@@ -4,7 +4,58 @@ All notable changes to this project will be documented in this file. Dates are d
4
4
 
5
5
  Generated by [`auto-changelog`](https://github.com/CookPete/auto-changelog).
6
6
 
7
- ### [1.0.127](https://github.com/eea/volto-clms-theme/compare/1.0.126...1.0.127) - 20 September 2022
7
+ ### [1.0.129](https://github.com/eea/volto-clms-theme/compare/1.0.128...1.0.129) - 26 September 2022
8
+
9
+ #### :bug: Bug Fixes
10
+
11
+ - fix: prevent extra url data coming from search [ionlizarazu - [`210badf`](https://github.com/eea/volto-clms-theme/commit/210badfd72e3efa37db157e4f69feb475f0d5631)]
12
+ - fix: eslint [Mikel Larreategi - [`bc8f97f`](https://github.com/eea/volto-clms-theme/commit/bc8f97f957bfdc1798a6197af7a208bad0b3f991)]
13
+ - fix: add new field file, show and use it in the download cart and prepackaged files table. CLMS-1202 [Mikel Larreategi - [`4ebd4eb`](https://github.com/eea/volto-clms-theme/commit/4ebd4eb93b5fbaf4e539aba9e27c7e9525babe96)]
14
+ - fix: show meeting register status only to managers [ionlizarazu - [`aed5137`](https://github.com/eea/volto-clms-theme/commit/aed5137882b03e47cd928ba820b4974018bbdbb5)]
15
+ - fix: routing in new tab [ionlizarazu - [`cf038d5`](https://github.com/eea/volto-clms-theme/commit/cf038d5b5a4f0a85667a580709fb75b226195d8a)]
16
+ - fix: remove inexisting attribute from a tag [Mikel Larreategi - [`3160125`](https://github.com/eea/volto-clms-theme/commit/3160125a31b5509343ee8f4cc43ea5a243700181)]
17
+ - fix: global search taxonomy filters count [ionlizarazu - [`087d78e`](https://github.com/eea/volto-clms-theme/commit/087d78e190531eda4de503abf0261a98e717144a)]
18
+ - fix: match with regex current tab from the location hash and add slugify function [ionlizarazu - [`6bd11ae`](https://github.com/eea/volto-clms-theme/commit/6bd11ae040b104fa9b07887c042599f99114d250)]
19
+ - fix: vertical and verticalFAQ tabs block now uses tab title to set the hash [Unai - [`dc5375b`](https://github.com/eea/volto-clms-theme/commit/dc5375b16bed78c72a821a172fd133e22a4395ba)]
20
+
21
+ #### :hammer_and_wrench: Others
22
+
23
+ - CLMS-1405 Hide the topic in the Use case details [joewdavies - [`c907b88`](https://github.com/eea/volto-clms-theme/commit/c907b88d38a3d3b71d7652a3f42d4b7a7feffbfc)]
24
+ - ESlint fix [joewdavies - [`9c689e6`](https://github.com/eea/volto-clms-theme/commit/9c689e6026e84b6c7c8f7e915f99c803c014feea)]
25
+ - CLMS-1341 [joewdavies - [`dbdfe60`](https://github.com/eea/volto-clms-theme/commit/dbdfe60a9e2e9b26782481ce2ecc170634a997c4)]
26
+ - CLMS-1218 [joewdavies - [`f1fc506`](https://github.com/eea/volto-clms-theme/commit/f1fc506a26aa1adf7a8768c8fcc77d0081ac26e4)]
27
+ - CLMS-1346 [joewdavies - [`a402538`](https://github.com/eea/volto-clms-theme/commit/a4025384dafa0eabdd499d61e5f7c99f9bfb25ce)]
28
+ - CLMS-1344 [joewdavies - [`4e26a60`](https://github.com/eea/volto-clms-theme/commit/4e26a606e6cd57f79ce074bf86910fa09bb94133)]
29
+ - absolute path to import widgets [ionlizarazu - [`e284cb9`](https://github.com/eea/volto-clms-theme/commit/e284cb9868fb74e3628eeba7c7d3ff539610b263)]
30
+ - ESlint fix [joewdavies - [`3870362`](https://github.com/eea/volto-clms-theme/commit/3870362deaf735c35400404bfb39f84ac670177f)]
31
+ - Revert "hide View in the pa viewer button for anon" [ionlizarazu - [`05210c0`](https://github.com/eea/volto-clms-theme/commit/05210c0bb256604edfe12805b4c6ea21f76481d6)]
32
+ - Revert "disable view in the map viewer button for anon" [ionlizarazu - [`e4ff0da`](https://github.com/eea/volto-clms-theme/commit/e4ff0dac484fd1a340d13d33e934c4f8a8636ad5)]
33
+ - disable view in the map viewer button for anon [ionlizarazu - [`3e87a19`](https://github.com/eea/volto-clms-theme/commit/3e87a19cce034e3af6255c8aac9551a2f104d4d7)]
34
+ - hide View in the pa viewer button for anon [ionlizarazu - [`79bf226`](https://github.com/eea/volto-clms-theme/commit/79bf2268a30e5830e44dd93cb8a71ec26c6999aa)]
35
+ - use UniversalLink [ionlizarazu - [`1150208`](https://github.com/eea/volto-clms-theme/commit/115020873957edf27820addafad56a845bd040c9)]
36
+ - sort imports [ionlizarazu - [`6725c87`](https://github.com/eea/volto-clms-theme/commit/6725c87b6957bb20019290dc08d2f15cf51de606)]
37
+ - add agree privacy policy for register meeting [ionlizarazu - [`bc8d1ca`](https://github.com/eea/volto-clms-theme/commit/bc8d1ca21c6bc64a34a1bf8c52f86fa9c8b36bc8)]
38
+ ### [1.0.128](https://github.com/eea/volto-clms-theme/compare/1.0.127...1.0.128) - 22 September 2022
39
+
40
+ #### :bug: Bug Fixes
41
+
42
+ - fix: CLMS-1381 remove cart when deleting the user-profile [Mikel Larreategi - [`87b043d`](https://github.com/eea/volto-clms-theme/commit/87b043dee950bbaa86f1669eebbaa0938329bdc1)]
43
+ - fix: vertical and verticalFAQ tabs block now uses tab title to set the hash [Unai - [`505573c`](https://github.com/eea/volto-clms-theme/commit/505573c33d63948c4201d3b8c0038809ca479407)]
44
+
45
+ #### :hammer_and_wrench: Others
46
+
47
+ - Revert "add agree privacy policy for register meeting" [Mikel Larreategi - [`0cb5061`](https://github.com/eea/volto-clms-theme/commit/0cb5061d40d9f299c0f35c8066d76a7f23cf4b45)]
48
+ - Revert "sort imports" [Mikel Larreategi - [`1a54e00`](https://github.com/eea/volto-clms-theme/commit/1a54e006ed3486bff9687ff2318914ec30f085c9)]
49
+ - Revert "use UniversalLink" [Mikel Larreategi - [`7dedeba`](https://github.com/eea/volto-clms-theme/commit/7dedeba760099b10b0c36b7b57a4da4758a6262d)]
50
+ - Revert "hide View in the pa viewer button for anon" [Mikel Larreategi - [`57a2d1a`](https://github.com/eea/volto-clms-theme/commit/57a2d1a8e5a79adfa45b4ee297ef82c3cbf66100)]
51
+ - Revert "disable view in the map viewer button for anon" [Mikel Larreategi - [`84759e6`](https://github.com/eea/volto-clms-theme/commit/84759e66c2fde33a6e679516f2624e83bf21bdc2)]
52
+ - Revert "fix: vertical and verticalFAQ tabs block now uses tab title to set the hash" [Mikel Larreategi - [`59cc5e5`](https://github.com/eea/volto-clms-theme/commit/59cc5e5dc0e7acb92354c0f6e9e00c65fe26ce12)]
53
+ - disable view in the map viewer button for anon [ionlizarazu - [`bb1809d`](https://github.com/eea/volto-clms-theme/commit/bb1809d66b5b8c077270ceac61143f3297350be5)]
54
+ - hide View in the pa viewer button for anon [ionlizarazu - [`6f0b29e`](https://github.com/eea/volto-clms-theme/commit/6f0b29e2731564d1ac9039b99a1566b25dae2043)]
55
+ - use UniversalLink [ionlizarazu - [`489cb6d`](https://github.com/eea/volto-clms-theme/commit/489cb6d62c02565c36845ac364b71c0299aad053)]
56
+ - sort imports [ionlizarazu - [`d33d3d8`](https://github.com/eea/volto-clms-theme/commit/d33d3d8f655c82a216a93194474de44a66ef4a95)]
57
+ - add agree privacy policy for register meeting [ionlizarazu - [`0f50bcb`](https://github.com/eea/volto-clms-theme/commit/0f50bcbe0a1d77bee6ebcdada1f2a27cc02d78ca)]
58
+ ### [1.0.127](https://github.com/eea/volto-clms-theme/compare/1.0.126...1.0.127) - 21 September 2022
8
59
 
9
60
  #### :hammer_and_wrench: Others
10
61
 
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@eeacms/volto-clms-theme",
3
- "version": "1.0.127",
3
+ "version": "1.0.129",
4
4
  "description": "volto-clms-theme: Volto theme for CLMS site",
5
5
  "main": "src/index.js",
6
6
  "author": "CodeSyntax for the European Environment Agency",
@@ -89,9 +89,9 @@ const CclUseCaseListEdit = (props) => {
89
89
  {useCase.title}
90
90
  </div>
91
91
  <div className="use-case-element-description">
92
- <span>
92
+ {/* <span>
93
93
  {useCase.topics.map((topic) => topic.title)}
94
- </span>
94
+ </span> */}
95
95
  <span>{cclDateTimeFormat(useCase?.effective)}</span>
96
96
  <span>{useCase.responsibleOrganization}</span>
97
97
  </div>
@@ -81,9 +81,9 @@ const CclUseCaseListView = (props) => {
81
81
  {useCase.title}
82
82
  </div>
83
83
  <div className="use-case-element-description">
84
- <span>
84
+ {/* <span>
85
85
  {useCase.topics.map((topic) => topic.title)}
86
- </span>
86
+ </span> */}
87
87
  <span>
88
88
  {new Date(useCase?.effective).toLocaleDateString()}
89
89
  </span>
@@ -59,12 +59,13 @@ const FilterList = (props) => {
59
59
  // }
60
60
  const currentFiltersToCount = {};
61
61
  Object.keys(currentFilters).forEach((filterKey) => {
62
- currentFiltersToCount[filterKey] =
63
- typeof currentFilters[filterKey] === 'object'
64
- ? currentFilters[filterKey].filter((filter) => {
65
- return !filtersToAvoidSet.has(filter);
66
- })
67
- : null;
62
+ if (typeof currentFilters[filterKey] === 'object') {
63
+ currentFiltersToCount[filterKey] = currentFilters[filterKey].filter(
64
+ (filter) => {
65
+ return !filtersToAvoidSet.has(filter);
66
+ },
67
+ );
68
+ }
68
69
  });
69
70
  // const totalFilters = [].concat.apply([], Object.values(currentFilters))
70
71
  // .length;
@@ -1,4 +1,4 @@
1
- import React, { useEffect } from 'react';
1
+ import React from 'react';
2
2
  import { Button, Input } from 'semantic-ui-react';
3
3
  import { defineMessages, useIntl } from 'react-intl';
4
4
  import { Icon } from '@plone/volto/components';
@@ -22,9 +22,11 @@ const SearchInput = (props) => {
22
22
  } = props;
23
23
  const intl = useIntl();
24
24
 
25
- useEffect(() => {
26
- onTriggerSearch(rest.searchedText);
27
- setSearchText(rest.searchedText);
25
+ React.useEffect(() => {
26
+ if (rest.searchedText !== '') {
27
+ onTriggerSearch(rest.searchedText);
28
+ setSearchText(rest.searchedText);
29
+ }
28
30
  return () => {};
29
31
  }, [rest.searchedText, onTriggerSearch, setSearchText]);
30
32
 
@@ -10,6 +10,7 @@ import { connect } from 'react-redux';
10
10
  import cx from 'classnames';
11
11
  import { withRouter } from 'react-router';
12
12
  import { withScrollToTarget } from '@eeacms/volto-tabs-block/hocs';
13
+ import { slugify } from '../../utils';
13
14
 
14
15
  const CclVerticalFaqTabsView = (props) => {
15
16
  const { metadata = {}, tabsList = [] } = props;
@@ -23,8 +24,10 @@ const CclVerticalFaqTabsView = (props) => {
23
24
  return (
24
25
  <div className="right-content cont-w-75">
25
26
  {tabsList.map((tab, index) => {
27
+ const title = tabs[tab].title;
28
+ const tabHash = slugify(title);
26
29
  return (
27
- <Route to={'#' + activeTab}>
30
+ <Route to={'#' + tabHash}>
28
31
  <div
29
32
  key={index}
30
33
  className={cx('panel', tab === activeTab && 'panel-selected')}
@@ -61,10 +64,11 @@ const CclVerticalFaqTabsView = (props) => {
61
64
  const nextSubTab =
62
65
  tabs[tabsList[tabIndex]]?.subTab?.subtab || false;
63
66
  const defaultTitle = `Tab ${tabIndex}`;
67
+ const tabHash = title.split(' ').join('-');
64
68
  return (
65
69
  <div
66
70
  key={index}
67
- id={tabIndex}
71
+ id={tabHash}
68
72
  className={cx(
69
73
  'card',
70
74
  tab === activeTab && 'active',
@@ -75,7 +79,7 @@ const CclVerticalFaqTabsView = (props) => {
75
79
  <span>{title || defaultTitle}</span>
76
80
  ) : (
77
81
  <NavLink
78
- to={'#tab=' + tabIndex}
82
+ to={'#' + tabHash}
79
83
  className="collapsed"
80
84
  onClick={(e) => {
81
85
  handleActive(activeTab, tab, setActiveTab);
@@ -1,15 +1,17 @@
1
- import './fontawesome';
2
-
3
- import { NavLink, Route } from 'react-router-dom';
4
-
5
1
  import React from 'react';
6
- import { RenderBlocks } from '@plone/volto/components';
7
- import { compose } from 'redux';
8
2
  import { connect } from 'react-redux';
9
- import cx from 'classnames';
10
3
  import { withRouter } from 'react-router';
4
+ import { NavLink, Route } from 'react-router-dom';
5
+ import { compose } from 'redux';
6
+
7
+ import { RenderBlocks } from '@plone/volto/components';
11
8
  import { withScrollToTarget } from '@eeacms/volto-tabs-block/hocs';
12
9
 
10
+ import { slugify } from '../../utils';
11
+ import './fontawesome';
12
+
13
+ import cx from 'classnames';
14
+
13
15
  const CclVerticalTabsView = (props) => {
14
16
  const {
15
17
  metadata = {},
@@ -34,8 +36,10 @@ const CclVerticalTabsView = (props) => {
34
36
  return (
35
37
  <div className="right-content cont-w-75">
36
38
  {tabsList.map((tab, index) => {
39
+ const title = tabs[tab].title;
40
+ const tabHash = slugify(title);
37
41
  return (
38
- <Route key={index} to={'#' + activeTab}>
42
+ <Route key={index} to={'#' + tabHash}>
39
43
  <div
40
44
  className={cx('panel', tab === activeTab && 'panel-selected')}
41
45
  role="tabpanel"
@@ -66,10 +70,11 @@ const CclVerticalTabsView = (props) => {
66
70
  const nextSubTab =
67
71
  tabs[tabsList[tabIndex]]?.subTab?.subtab || false;
68
72
  const defaultTitle = `Tab ${tabIndex}`;
73
+ const tabHash = slugify(title);
69
74
  return (
70
75
  <div
71
76
  key={index}
72
- id={tabIndex}
77
+ id={tabHash}
73
78
  className={cx(
74
79
  'card',
75
80
  tab === activeTab && 'active',
@@ -80,7 +85,7 @@ const CclVerticalTabsView = (props) => {
80
85
  <span>{title || defaultTitle}</span>
81
86
  ) : (
82
87
  <NavLink
83
- to={'#tab=' + tabIndex}
88
+ to={'#' + tabHash}
84
89
  className="collapsed"
85
90
  onClick={(e) => {
86
91
  handleClick(e, tab, activeTab, setActiveTab);
@@ -1,8 +1,10 @@
1
1
  import React from 'react';
2
+ import { slugify } from '../../utils';
2
3
 
3
4
  const RoutingHOC = (TabView) =>
4
5
  function Component(props) {
5
6
  const { tabsList = [], tabs, activeTabIndex = 0, setActiveTab } = props;
7
+
6
8
  function reloadTab(window, rTabs, rTabsList) {
7
9
  if (
8
10
  window.location.hash.length === 0 &&
@@ -16,11 +18,28 @@ const RoutingHOC = (TabView) =>
16
18
  ) {
17
19
  return rTabsList[0];
18
20
  }
21
+ const tabsDict = Object.entries(rTabs).map((t) => {
22
+ return { title: t[1].title, id: t[0] };
23
+ });
24
+ // Deprecated, now we use tab title to set the hash
25
+ // if (
26
+ // window.location.hash.match(/.*&?#?tab=(.*)/) &&
27
+ // window.location.hash.match(/.*&?#?tab=(.*)/).length > 1
28
+ // ) {
29
+ // return rTabsList[window.location.hash.match(/.*&?#?tab=(.*)/)[1] - 1];
30
+ // }
19
31
  if (
20
- window.location.hash.match(/.*&?#?tab=(.*)/) &&
21
- window.location.hash.match(/.*&?#?tab=(.*)/).length > 1
32
+ window.location.hash.match(/.*&?(#.*)/) &&
33
+ window.location.hash.match(/.*&?(#.*)/).length > 1
22
34
  ) {
23
- return rTabsList[window.location.hash.match(/.*&?#?tab=(.*)/)[1] - 1];
35
+ const hashMatch = window.location.hash
36
+ .match(/.*&?(#.*)/)[1]
37
+ .replace('#', '');
38
+ const result = tabsDict.filter((t) => slugify(t.title) === hashMatch);
39
+ if (result.length > 0) {
40
+ return result[0].id;
41
+ }
42
+ return '';
24
43
  }
25
44
  }
26
45
  React.useEffect(() => {
@@ -30,7 +49,8 @@ const RoutingHOC = (TabView) =>
30
49
  String(window.performance.getEntriesByType('navigation')[0].type) ===
31
50
  'reload';
32
51
  if (isReload) {
33
- setActiveTab(reloadTab(window, tabs, tabsList));
52
+ const existingTab = reloadTab(window, tabs, tabsList);
53
+ if (existingTab) setActiveTab(existingTab);
34
54
  }
35
55
  // eslint-disable-next-line react-hooks/exhaustive-deps
36
56
  }, [activeTabIndex]);
@@ -71,9 +71,9 @@ import linkSVG from '@plone/volto/icons/link.svg';
71
71
  import navSVG from '@plone/volto/icons/nav.svg';
72
72
  import upSVG from '@plone/volto/icons/up-key.svg';
73
73
  import ImageWidget from '@eeacms/volto-clms-theme/components/Widgets/ImageWidget';
74
- import TextWidget from '../../customizations/volto/components/manage/Widgets/TextWidget';
75
- import TextareaWidget from '../../customizations/volto/components/manage/Widgets/TextareaWidget';
76
- import EmailWidget from '../../customizations/volto/components/manage/Widgets/EmailWidget';
74
+ import TextWidget from '@plone/volto/components/manage/Widgets/TextWidget';
75
+ import TextareaWidget from '@plone/volto/components/manage/Widgets/TextareaWidget';
76
+ import EmailWidget from '@plone/volto/components/manage/Widgets/EmailWidget';
77
77
 
78
78
  export const customGroupBlocksOrder = [
79
79
  {
@@ -25,3 +25,10 @@ export const getPanels = (data) => {
25
25
  data.blocks?.[id],
26
26
  ]);
27
27
  };
28
+
29
+ export const slugify = (string) => {
30
+ return string
31
+ .toLowerCase()
32
+ .replace(/[\s-]+/g, '_')
33
+ .replace(/[^\w]+/g, '');
34
+ };
@@ -50,7 +50,7 @@ const DownloadDataSetContent = (data, token) => {
50
50
 
51
51
  {data?.mapviewer_viewservice?.length > 0 && (
52
52
  <div className="dataset-download-area">
53
- <h2>Custom download</h2>
53
+ <h2>Download by area</h2>
54
54
  <p>
55
55
  Use this option if you would like to download the dataset for
56
56
  area(s) of interest.
@@ -58,11 +58,11 @@ const DownloadDataSetContent = (data, token) => {
58
58
  {user?.['@id'] ? (
59
59
  data.mapviewer_istimeseries === true ? (
60
60
  <CclButton url={location.pathname + '/download-by-area'}>
61
- Go to custom download
61
+ Go to download by area and time
62
62
  </CclButton>
63
63
  ) : (
64
64
  <CclButton url={location.pathname + '/download-by-area'}>
65
- Go to custom download
65
+ Go to download by area
66
66
  </CclButton>
67
67
  )
68
68
  ) : (
@@ -74,7 +74,7 @@ const DownloadDataSetContent = (data, token) => {
74
74
  >
75
75
  <FormattedMessage
76
76
  id="downloadByArea"
77
- defaultMessage="Go to custom download"
77
+ defaultMessage="Go to download by area"
78
78
  />
79
79
  </CclButton>
80
80
  }
@@ -141,15 +141,15 @@ const DownloadDataSetContent = (data, token) => {
141
141
  url={location.pathname + '/download-by-area'}
142
142
  disabled={true}
143
143
  >
144
- Go to custom download
144
+ Go to download by area
145
145
  </CclButton>
146
146
  ) : data.mapviewer_istimeseries === true ? (
147
147
  <CclButton url={location.pathname + '/download-by-area'}>
148
- Go to custom download and time
148
+ Go to download by area and time
149
149
  </CclButton>
150
150
  ) : (
151
151
  <CclButton url={location.pathname + '/download-by-area'}>
152
- Go to custom download
152
+ Go to download by area
153
153
  </CclButton>
154
154
  )} */}
155
155
  </div>
@@ -207,7 +207,9 @@ const CLMSCartContent = (props) => {
207
207
  case 'nuts':
208
208
  return 'NUTS: ' + (item.area.valueName || item.area.value);
209
209
  case undefined:
210
- return item.area || '-';
210
+ return item.area || item.file || '-';
211
+ case typeof item.area === 'string':
212
+ return item.area || item.file || '-';
211
213
  default:
212
214
  return '-';
213
215
  }
@@ -45,6 +45,7 @@ export const getCartObjectFromPrepackaged = (file_data, dataset_data) => {
45
45
  return {
46
46
  name: dataset_data.title,
47
47
  title: file_data.title,
48
+ file: file_data.file,
48
49
  area: file_data.area,
49
50
  format: file_data.format?.token || file_data.format,
50
51
  resolution: file_data.resolution,
@@ -68,6 +69,7 @@ export const getCartObjectFromMapviewer = (
68
69
  nutsnames,
69
70
  ) => {
70
71
  const area = local_cart_data.area;
72
+ const file = local_cart_data.file;
71
73
  if (area?.type === 'nuts' && Object.keys(nutsnames).includes(area.value)) {
72
74
  area.valueName = nutsnames[area.value];
73
75
  }
@@ -85,6 +87,7 @@ export const getCartObjectFromMapviewer = (
85
87
  return {
86
88
  name: dataset_data.title || '-',
87
89
  area: area || '-',
90
+ file: file || '-',
88
91
  format: type_options.length > 0 ? type_options[0].full_format : null,
89
92
  original_format:
90
93
  type_options.length > 0 ? type_options[0].full_format : null,
@@ -1,29 +1,32 @@
1
- import './meetingstyles.less';
2
-
1
+ import React, { useState } from 'react';
2
+ import AnimateHeight from 'react-animate-height';
3
3
  import { FormattedMessage, defineMessages, injectIntl } from 'react-intl';
4
+ import { useDispatch, useSelector } from 'react-redux';
5
+ import { useHistory, useLocation } from 'react-router-dom';
6
+ import { toast } from 'react-toastify';
4
7
  import { Header, Image, Message, Segment } from 'semantic-ui-react';
8
+ import { Accordion } from 'semantic-ui-react';
9
+
10
+ import { createContent } from '@plone/volto/actions';
5
11
  import { Icon, Toast, UniversalLink } from '@plone/volto/components';
6
12
  import {
7
13
  Recurrence,
8
14
  When,
9
15
  } from '@plone/volto/components/theme/View/EventDatesInfo';
10
- import { useDispatch, useSelector } from 'react-redux';
11
- import { useHistory, useLocation } from 'react-router-dom';
12
-
16
+ import checkSVG from '@plone/volto/icons/check.svg';
17
+ import config from '@plone/volto/registry';
18
+ import CclListingCards from '@eeacms/volto-clms-theme/components/Blocks/CustomTemplates/VoltoListingBlock/CclListingCards';
13
19
  import CclButton from '@eeacms/volto-clms-theme/components/CclButton/CclButton';
14
- import React from 'react';
15
20
  import { StringToHTML } from '@eeacms/volto-clms-theme/components/CclUtils';
16
- import checkSVG from '@plone/volto/icons/check.svg';
17
- import { createContent } from '@plone/volto/actions';
18
- import jwtDecode from 'jwt-decode';
21
+
19
22
  import { postMeetingRegister } from '../../actions';
20
- import { toast } from 'react-toastify';
21
- import { LightGalleryListing } from './CclLightGallery';
22
- import CclListingCards from '@eeacms/volto-clms-theme/components/Blocks/CustomTemplates/VoltoListingBlock/CclListingCards';
23
- import config from '@plone/volto/registry';
24
- import AnimateHeight from 'react-animate-height';
25
- import { Accordion } from 'semantic-ui-react';
26
23
  import { CLMSRelatedItems } from '../CLMSRelatedItems';
24
+ import { LightGalleryListing } from './CclLightGallery';
25
+ import './meetingstyles.less';
26
+ import { RegisterButtonReasons } from './utils';
27
+
28
+ import jwtDecode from 'jwt-decode';
29
+
27
30
  export const CLMSMeetingView = (props) => {
28
31
  const { content, intl } = props;
29
32
  const dispatch = useDispatch();
@@ -100,6 +103,14 @@ export const CLMSMeetingView = (props) => {
100
103
  defaultMessage:
101
104
  'Some anonymous registration form parameters are not ready to go',
102
105
  },
106
+ agreePrivacyPolicy: {
107
+ id: 'agreePrivacyPolicy',
108
+ defaultMessage: 'I agree to the ',
109
+ },
110
+ agreePrivacyPolicyLinkText: {
111
+ id: 'agreePrivacyPolicyLinkText',
112
+ defaultMessage: 'privacy policy.',
113
+ },
103
114
  });
104
115
 
105
116
  function createForm() {
@@ -115,7 +126,13 @@ export const CLMSMeetingView = (props) => {
115
126
  const files = content.items
116
127
  ? content.items.filter((item) => item['@type'] === 'File')
117
128
  : [];
118
- const RegistrationButton = ({ rContent, rMeeting_register, rIsLoggedIn }) => {
129
+ const RegistrationButton = ({
130
+ rContent,
131
+ rMeeting_register,
132
+ rIsLoggedIn,
133
+ locale,
134
+ }) => {
135
+ const [privacy, setPrivacy] = useState(false);
119
136
  return (
120
137
  <>
121
138
  {rContent.is_registered ||
@@ -130,9 +147,32 @@ export const CLMSMeetingView = (props) => {
130
147
  </Message>
131
148
  ) : (
132
149
  rIsLoggedIn && (
133
- <CclButton onClick={() => handleRegister()}>
134
- <FormattedMessage id="Register" defaultMessage="Register" />
135
- </CclButton>
150
+ <>
151
+ <div>
152
+ <input
153
+ type="checkbox"
154
+ id={`footer_privacy-register`}
155
+ name={`footer_privacy-register`}
156
+ value={privacy}
157
+ onClick={() => setPrivacy(!privacy)}
158
+ className="ccl-checkbox ccl-form-check-input"
159
+ required={true}
160
+ />
161
+ <label
162
+ className="ccl-form-check-label"
163
+ htmlFor={`footer_privacy-register`}
164
+ >
165
+ {intl.formatMessage(messages.agreePrivacyPolicy)}
166
+ <UniversalLink href={`/${locale}/personal-data-protection`}>
167
+ {intl.formatMessage(messages.agreePrivacyPolicyLinkText)}
168
+ </UniversalLink>
169
+ </label>
170
+ </div>
171
+ <br />
172
+ <CclButton disabled={!privacy} onClick={() => handleRegister()}>
173
+ <FormattedMessage id="Register" defaultMessage="Register" />
174
+ </CclButton>
175
+ </>
136
176
  )
137
177
  )}
138
178
  </>
@@ -389,7 +429,9 @@ export const CLMSMeetingView = (props) => {
389
429
  </div>
390
430
  </>
391
431
  )}
392
-
432
+ {user.roles &&
433
+ user.roles.includes('Manager') &&
434
+ RegisterButtonReasons(content)}
393
435
  {content.registrations_open && (
394
436
  <div className="meeting-info-container right-content">
395
437
  <div className="card-button">
@@ -407,11 +449,14 @@ export const CLMSMeetingView = (props) => {
407
449
  )}
408
450
  </>
409
451
  ) : (
410
- <RegistrationButton
411
- rContent={content}
412
- rMeeting_register={meeting_register}
413
- rIsLoggedIn={isLoggedIn}
414
- />
452
+ <>
453
+ <RegistrationButton
454
+ rContent={content}
455
+ rMeeting_register={meeting_register}
456
+ rIsLoggedIn={isLoggedIn}
457
+ locale={props.intl.locale}
458
+ />
459
+ </>
415
460
  )}
416
461
  </div>
417
462
  </div>
@@ -0,0 +1,29 @@
1
+ export const RegisterButtonReasons = (content) => {
2
+ let results = [];
3
+ if (!content.registrations_open) {
4
+ results.push('Registrations are closed');
5
+ } else {
6
+ if (content.allow_anonymous_registration) {
7
+ if (!content.anonymous_registration_form) {
8
+ results.push('Registration form is missing');
9
+ } else {
10
+ if (!content.anonymous_registration_form?.published) {
11
+ results.push('Registration form is private');
12
+ } else if (!content.anonymous_registration_form?.email) {
13
+ results.push('Registration form has no email');
14
+ } else if (!content.anonymous_registration_form?.fullname) {
15
+ results.push('Registration form has no fullname');
16
+ }
17
+ }
18
+ }
19
+ }
20
+ return results.length > 0 ? (
21
+ <ul>
22
+ {results.map((result) => (
23
+ <li style={{ color: 'red' }}>{result}</li>
24
+ ))}
25
+ </ul>
26
+ ) : (
27
+ <></>
28
+ );
29
+ };
@@ -1,5 +1,6 @@
1
1
  import React from 'react';
2
2
  import { injectIntl } from 'react-intl';
3
+ import { FormattedMessage } from 'react-intl';
3
4
  import { useDispatch, useSelector } from 'react-redux';
4
5
  import { useHistory } from 'react-router-dom';
5
6
  import { Container } from 'semantic-ui-react';
@@ -7,9 +8,9 @@ import { Modal, Segment } from 'semantic-ui-react';
7
8
 
8
9
  import { logout } from '@plone/volto/actions';
9
10
  import CclButton from '@eeacms/volto-clms-theme/components/CclButton/CclButton';
11
+ import useCartState from '@eeacms/volto-clms-utils/cart/useCartState';
10
12
 
11
13
  import { delProfile } from '../../actions';
12
- import { FormattedMessage } from 'react-intl';
13
14
 
14
15
  /**
15
16
  * CLMSProfileView container.
@@ -26,11 +27,14 @@ export const CLMSDeleteProfileView = (props) => {
26
27
 
27
28
  const deleting = useSelector((state) => state.profile_delete.loading);
28
29
 
30
+ const { removeAllCart } = useCartState();
31
+
29
32
  function handleClick() {
30
33
  dispatch(delProfile());
31
34
  }
32
35
 
33
36
  if (isDeleted === true) {
37
+ removeAllCart();
34
38
  history.push('/');
35
39
  dispatch(logout());
36
40
  }
@@ -397,6 +397,8 @@
397
397
  }
398
398
 
399
399
  .card-doc-size {
400
+ align-self: center;
401
+ margin-bottom: 1rem;
400
402
  margin-left: 1rem;
401
403
  white-space: nowrap;
402
404
  }
@@ -139,6 +139,7 @@ function CclDownloadTable(props) {
139
139
  UID: item.UID,
140
140
  file_id: item['@id'],
141
141
  area: item.area,
142
+ file: item.file,
142
143
  unique_id: item.unique_id,
143
144
  }));
144
145
  addCartItem(selectedCartItems);
@@ -174,6 +175,7 @@ function CclDownloadTable(props) {
174
175
 
175
176
  const columns = [
176
177
  hasSome('title'),
178
+ hasSome('file'),
177
179
  hasSome('area'),
178
180
  hasSome('year'),
179
181
  hasSome('version'),
@@ -241,9 +243,8 @@ function CclDownloadTable(props) {
241
243
  </th>
242
244
  )}
243
245
  {columns.includes('title') && <th>Title</th>}
244
- {columns.includes('area') && (
245
- <th>{dataset.download_table_area_of_interest_title}</th>
246
- )}
246
+ {columns.includes('file') && <th>File name</th>}
247
+ {columns.includes('area') && <th>Area of interest</th>}
247
248
  {columns.includes('year') && <th>Year</th>}
248
249
  {columns.includes('version') && <th>Version</th>}
249
250
  {columns.includes('resolution') && <th>Resolution</th>}
@@ -273,6 +274,9 @@ function CclDownloadTable(props) {
273
274
  {columns.includes('title') && (
274
275
  <td>{contentOrDash(dataset_file?.title)}</td>
275
276
  )}
277
+ {columns.includes('file') && (
278
+ <td>{contentOrDash(dataset_file?.file)}</td>
279
+ )}
276
280
  {columns.includes('area') && (
277
281
  <td>{contentOrDash(dataset_file?.area)}</td>
278
282
  )}
@@ -9,6 +9,11 @@ const ItemSchema = () => ({
9
9
  description: 'Enter the title of this file.',
10
10
  type: 'string',
11
11
  },
12
+ file: {
13
+ title: 'File name',
14
+ description: 'Enter the file name.',
15
+ type: 'string',
16
+ },
12
17
  area: {
13
18
  title: 'Area of interest',
14
19
  description: 'Enter the area of this file.',
@@ -68,6 +73,7 @@ const ItemSchema = () => ({
68
73
  title: 'File',
69
74
  fields: [
70
75
  'title',
76
+ 'file',
71
77
  'area',
72
78
  'year',
73
79
  'version',
@@ -29,13 +29,24 @@ export const structure_taxonomy_terms = (choices) => {
29
29
  childrens: [],
30
30
  };
31
31
  splitted_option.length === 1 && options.push(modified_option);
32
+ });
33
+ choices.forEach((choice) => {
34
+ var splitted_option = choice.label.split(' » ');
35
+ var modified_option = {
36
+ value: choice.value,
37
+ label:
38
+ splitted_option.length > 1
39
+ ? splitted_option.slice(-1).pop()
40
+ : choice.label,
41
+ original: choice.label,
42
+ childrens: [],
43
+ };
32
44
  if (splitted_option.length > 1) {
33
45
  var parent_option = splitted_option.slice(0, -1).pop();
34
- options.map((opt) => {
46
+ options.forEach((opt) => {
35
47
  if (opt.label === parent_option) {
36
48
  opt.childrens.push(modified_option);
37
49
  }
38
- return '';
39
50
  });
40
51
  }
41
52
  });
@@ -97,7 +97,6 @@ const UniversalLink = ({
97
97
  href={url}
98
98
  title={title}
99
99
  target={!checkedURL.isMail && !checkedURL.isTelephone ? '_blank' : null}
100
- openLinkInNewTab={true}
101
100
  rel="noopener noreferrer"
102
101
  className={className}
103
102
  {...props}
@@ -219,10 +219,30 @@ class Header extends Component {
219
219
  </ul>
220
220
  <div
221
221
  onMouseOut={(e) => {
222
- this.setState({ mobileSearchBoxOpen: false });
222
+ // this event might be a touch on the search button, make sure it isnt.
223
+ // ccl-header-search-show
224
+ if (
225
+ !e.currentTarget.classList.contains(
226
+ 'ccl-header-search-show',
227
+ ) &&
228
+ !e.currentTarget.classList.contains(
229
+ 'ccl-header-search-hidden',
230
+ )
231
+ ) {
232
+ this.setState({ mobileSearchBoxOpen: false });
233
+ }
223
234
  }}
224
235
  onBlur={(e) => {
225
- this.setState({ mobileSearchBoxOpen: false });
236
+ if (
237
+ !e.currentTarget.classList.contains(
238
+ 'ccl-header-search-show',
239
+ ) &&
240
+ !e.currentTarget.classList.contains(
241
+ 'ccl-header-search-hidden',
242
+ )
243
+ ) {
244
+ this.setState({ mobileSearchBoxOpen: false });
245
+ }
226
246
  }}
227
247
  className={
228
248
  this.state.mobileSearchBoxOpen
@@ -247,7 +267,12 @@ class Header extends Component {
247
267
  : 'ccl-main-menu'
248
268
  }
249
269
  >
250
- <Navigation pathname={this.props.pathname} />
270
+ <Navigation
271
+ pathname={this.props.pathname}
272
+ setHeaderState={(p) => {
273
+ this.setState(p);
274
+ }}
275
+ />
251
276
  <ul className="ccl-header-menu-tools ccl-collapsible-toolmenu">
252
277
  <CclTopMainMenu></CclTopMainMenu>
253
278
  <li className="header-vertical-line">
@@ -94,10 +94,10 @@ class Navigation extends Component {
94
94
  * @returns {undefined}
95
95
  */
96
96
  closeMobileMenu() {
97
- if (!this.state.isMobileMenuOpen) {
98
- return;
99
- }
100
97
  this.setState({ isMobileMenuOpen: false });
98
+ this.props.setHeaderState({
99
+ mobileMenuOpen: false,
100
+ });
101
101
  }
102
102
 
103
103
  /**
@@ -121,6 +121,7 @@ class Navigation extends Component {
121
121
  ? item.url === `/${lang}`
122
122
  : item.url === ''
123
123
  }
124
+ onClick={this.closeMobileMenu}
124
125
  >
125
126
  {item.title}
126
127
  </NavLink>
@@ -137,11 +137,17 @@
137
137
  }
138
138
  }
139
139
 
140
- /* full width search bar on mobile */
140
+ /* CLMS-1128 */
141
141
  @media (max-width: 500px) {
142
+ /* full width search bar on mobile */
142
143
  #main > div:nth-child(2) > header > div.ccl-header-tools > div > div.ccl-header-tools-container > div > form > div{
143
144
  width: 100%
144
145
  }
146
+
147
+ /* align search icon right*/
148
+ .ccl-search-collapse-button {
149
+ margin-left: auto !important;
150
+ }
145
151
  }
146
152
 
147
153
  .ccl-header .ccl-header-tools .ccl-header-search input {
@@ -1286,7 +1286,7 @@ main .search-form button {
1286
1286
  }
1287
1287
 
1288
1288
  .left-menu-detail .menu-detail-image {
1289
- height: 8rem;
1289
+ height: 12rem;
1290
1290
  margin-bottom: 0.25rem;
1291
1291
  }
1292
1292
 
@@ -1294,7 +1294,6 @@ main .search-form button {
1294
1294
  width: 100%;
1295
1295
  height: 100%;
1296
1296
  object-fit: cover;
1297
- opacity: 0.5;
1298
1297
  }
1299
1298
 
1300
1299
  .left-menu-detail .menu-detail-button:not(:last-of-type) {
@@ -530,7 +530,7 @@ body:not(.contenttype-lrf:not(.section-cart):not(.section-profile))
530
530
  }
531
531
 
532
532
  .left-menu-detail .menu-detail-image {
533
- height: 8rem;
533
+ height: 12rem;
534
534
  margin-bottom: 0.25rem;
535
535
  }
536
536
 
@@ -538,7 +538,6 @@ body:not(.contenttype-lrf:not(.section-cart):not(.section-profile))
538
538
  width: 100%;
539
539
  height: 100%;
540
540
  object-fit: cover;
541
- opacity: 0.5;
542
541
  }
543
542
 
544
543
  .left-menu-detail .menu-detail-button:not(:last-of-type) {
@@ -1243,3 +1242,9 @@ div#page-document h1.documentFirstHeading {
1243
1242
  #page-sitemap ul > li > ul > li {
1244
1243
  margin-bottom: 0;
1245
1244
  }
1245
+
1246
+ // CLMS-1344
1247
+ #sidebar-metadata .react-select__option {
1248
+ white-space: nowrap;
1249
+ width: fit-content;
1250
+ }