@plone/volto 17.0.0-alpha.2 → 17.0.0-alpha.20

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 (297) hide show
  1. package/.yarn/install-state.gz +0 -0
  2. package/CHANGELOG.md +530 -15
  3. package/CONTRIBUTING.md +1 -1
  4. package/README.md +11 -14
  5. package/addon-registry.js +34 -0
  6. package/create-theme-addons-loader.js +79 -0
  7. package/cypress/support/commands.js +56 -4
  8. package/cypress/support/volto-slate.js +4 -5
  9. package/docker-compose.yml +1 -1
  10. package/locales/ca/LC_MESSAGES/volto.po +272 -6
  11. package/locales/ca.json +1 -1
  12. package/locales/de/LC_MESSAGES/volto.po +291 -25
  13. package/locales/de.json +1 -1
  14. package/locales/en/LC_MESSAGES/volto.po +271 -5
  15. package/locales/en.json +1 -1
  16. package/locales/es/LC_MESSAGES/volto.po +281 -15
  17. package/locales/es.json +1 -1
  18. package/locales/eu/LC_MESSAGES/volto.po +272 -6
  19. package/locales/eu.json +1 -1
  20. package/locales/fi/LC_MESSAGES/volto.po +4882 -0
  21. package/locales/fi.json +1 -1
  22. package/locales/fr/LC_MESSAGES/volto.po +272 -6
  23. package/locales/fr.json +1 -1
  24. package/locales/it/LC_MESSAGES/volto.po +273 -7
  25. package/locales/it.json +1 -1
  26. package/locales/ja/LC_MESSAGES/volto.po +272 -6
  27. package/locales/ja.json +1 -1
  28. package/locales/nl/LC_MESSAGES/volto.po +927 -649
  29. package/locales/nl.json +1 -1
  30. package/locales/pt/LC_MESSAGES/volto.po +272 -6
  31. package/locales/pt.json +1 -1
  32. package/locales/pt_BR/LC_MESSAGES/volto.po +281 -15
  33. package/locales/pt_BR.json +1 -1
  34. package/locales/ro/LC_MESSAGES/volto.po +272 -6
  35. package/locales/ro.json +1 -1
  36. package/locales/volto.pot +272 -6
  37. package/locales/zh_CN/LC_MESSAGES/volto.po +272 -6
  38. package/locales/zh_CN.json +1 -1
  39. package/package.json +5 -3
  40. package/packages/volto-slate/build/messages/src/blocks/Table/TableBlockEdit.json +1 -1
  41. package/packages/volto-slate/build/messages/src/blocks/Text/DefaultTextBlockEditor.json +1 -1
  42. package/packages/volto-slate/build/messages/src/blocks/Text/DetachedTextBlockEditor.json +1 -1
  43. package/packages/volto-slate/build/messages/src/blocks/Text/SlashMenu.json +1 -1
  44. package/packages/volto-slate/build/messages/src/editor/plugins/AdvancedLink/index.json +1 -1
  45. package/packages/volto-slate/build/messages/src/editor/plugins/Link/index.json +1 -1
  46. package/packages/volto-slate/build/messages/src/editor/plugins/Table/index.json +1 -1
  47. package/packages/volto-slate/build/messages/src/elementEditor/messages.json +1 -1
  48. package/packages/volto-slate/build/messages/src/widgets/HtmlSlateWidget.json +1 -1
  49. package/packages/volto-slate/build/messages/src/widgets/RichTextWidgetView.json +1 -1
  50. package/packages/volto-slate/package.json +1 -1
  51. package/packages/volto-slate/src/actions/index.js +1 -1
  52. package/packages/volto-slate/src/blocks/Table/TableBlockEdit.jsx +21 -212
  53. package/packages/volto-slate/src/blocks/Table/schema.js +122 -0
  54. package/packages/volto-slate/src/blocks/Text/DefaultTextBlockEditor.jsx +8 -3
  55. package/packages/volto-slate/src/blocks/Text/SlashMenu.jsx +4 -3
  56. package/packages/volto-slate/src/blocks/Text/TextBlockView.jsx +20 -16
  57. package/packages/volto-slate/src/blocks/Text/extensions/withDeserializers.js +3 -1
  58. package/packages/volto-slate/src/blocks/Text/index.js +10 -2
  59. package/packages/volto-slate/src/editor/config.jsx +5 -4
  60. package/packages/volto-slate/src/editor/deserialize.js +0 -1
  61. package/packages/volto-slate/src/editor/index.js +4 -4
  62. package/packages/volto-slate/src/editor/less/slate.less +28 -0
  63. package/packages/volto-slate/src/editor/plugins/StyleMenu/StyleMenu.jsx +14 -4
  64. package/packages/volto-slate/src/editor/plugins/StyleMenu/utils.js +14 -5
  65. package/packages/volto-slate/src/editor/render.jsx +68 -8
  66. package/packages/volto-slate/src/editor/ui/SlateContextToolbar.jsx +2 -2
  67. package/packages/volto-slate/src/editor/ui/index.js +15 -15
  68. package/packages/volto-slate/src/index.js +2 -2
  69. package/packages/volto-slate/src/utils/blocks.js +7 -0
  70. package/packages/volto-slate/src/widgets/RichTextWidget.jsx +15 -8
  71. package/razzle.config.js +28 -0
  72. package/src/actions/index.js +6 -0
  73. package/src/actions/language/language.js +9 -8
  74. package/src/actions/querystringsearch/querystringsearch.js +20 -14
  75. package/src/actions/relations/rebuild.js +25 -0
  76. package/src/actions/relations/relations.js +86 -0
  77. package/src/actions/relations/relations.test.js +15 -0
  78. package/src/components/index.js +2 -0
  79. package/src/components/manage/Add/Add.jsx +2 -2
  80. package/src/components/manage/AnchorPlugin/index.jsx +2 -2
  81. package/src/components/manage/AnchorPlugin/utils/EditorUtils.js +3 -1
  82. package/src/components/manage/BlockChooser/BlockChooser.jsx +14 -5
  83. package/src/components/manage/BlockChooser/BlockChooser.test.jsx +5 -0
  84. package/src/components/manage/Blocks/Block/BlocksForm.jsx +19 -2
  85. package/src/components/manage/Blocks/Block/Edit.jsx +1 -1
  86. package/src/components/manage/Blocks/Block/Style.jsx +2 -2
  87. package/src/components/manage/Blocks/Container/Data.jsx +32 -0
  88. package/src/components/manage/Blocks/Container/Edit.jsx +174 -0
  89. package/src/components/manage/Blocks/Container/EditBlockWrapper.jsx +120 -0
  90. package/src/components/manage/Blocks/Container/NewBlockAddButton.jsx +84 -0
  91. package/src/components/manage/Blocks/Container/SimpleContainerToolbar.jsx +54 -0
  92. package/src/components/manage/Blocks/Grid/Edit.jsx +33 -0
  93. package/src/components/manage/Blocks/Grid/View.jsx +43 -0
  94. package/src/components/manage/Blocks/Grid/adapter.js +14 -0
  95. package/src/components/manage/Blocks/Grid/grid-1.svg +6 -0
  96. package/src/components/manage/Blocks/Grid/grid-2.svg +9 -0
  97. package/src/components/manage/Blocks/Grid/grid-3.svg +10 -0
  98. package/src/components/manage/Blocks/Grid/grid-4.svg +11 -0
  99. package/src/components/manage/Blocks/Grid/schema.js +35 -0
  100. package/src/components/manage/Blocks/Grid/templates.js +47 -0
  101. package/src/components/manage/Blocks/HeroImageLeft/Edit.jsx +6 -1
  102. package/src/components/manage/Blocks/Image/Edit.jsx +11 -7
  103. package/src/components/manage/Blocks/Image/ImageSidebar.jsx +2 -1
  104. package/src/components/manage/Blocks/Image/schema.js +11 -0
  105. package/src/components/manage/Blocks/Listing/DefaultTemplate.jsx +18 -3
  106. package/src/components/manage/Blocks/Listing/Edit.jsx +0 -14
  107. package/src/components/manage/Blocks/Listing/ListingBody.jsx +30 -8
  108. package/src/components/manage/Blocks/Listing/ListingBody.test.jsx +20 -0
  109. package/src/components/manage/Blocks/Listing/getAsyncData.js +9 -3
  110. package/src/components/manage/Blocks/Listing/withQuerystringResults.jsx +26 -18
  111. package/src/components/manage/Blocks/Search/SearchBlockEdit.jsx +5 -4
  112. package/src/components/manage/Blocks/Search/SearchBlockView.jsx +2 -1
  113. package/src/components/manage/Blocks/Search/components/DateRangeFacet.jsx +4 -1
  114. package/src/components/manage/Blocks/Search/components/Facets.jsx +64 -4
  115. package/src/components/manage/Blocks/Search/components/SearchInput.jsx +9 -2
  116. package/src/components/manage/Blocks/Search/components/index.js +13 -13
  117. package/src/components/manage/Blocks/Search/hocs/index.js +2 -2
  118. package/src/components/manage/Blocks/Search/hocs/withQueryString.jsx +2 -2
  119. package/src/components/manage/Blocks/Search/hocs/withSearch.jsx +43 -15
  120. package/src/components/manage/Blocks/Search/layout/LeftColumnFacets.jsx +17 -5
  121. package/src/components/manage/Blocks/Search/layout/RightColumnFacets.jsx +17 -5
  122. package/src/components/manage/Blocks/Search/layout/TopSideFacets.jsx +21 -5
  123. package/src/components/manage/Blocks/Search/schema.js +16 -1
  124. package/src/components/manage/Blocks/Teaser/Body.jsx +0 -1
  125. package/src/components/manage/Blocks/Teaser/DefaultBody.jsx +20 -15
  126. package/src/components/manage/Blocks/Teaser/schema.js +5 -0
  127. package/src/components/manage/Blocks/Title/View.jsx +15 -5
  128. package/src/components/manage/Blocks/Title/View.test.jsx +16 -1
  129. package/src/components/manage/Blocks/ToC/Schema.jsx +5 -1
  130. package/src/components/manage/Blocks/ToC/View.jsx +8 -1
  131. package/src/components/manage/Blocks/ToC/variations/DefaultTocRenderer.jsx +17 -4
  132. package/src/components/manage/Blocks/ToC/variations/HorizontalMenu.jsx +148 -10
  133. package/src/components/manage/Blocks/ToC/variations/index.js +3 -1
  134. package/src/components/manage/Contents/Contents.jsx +39 -26
  135. package/src/components/manage/Contents/ContentsItem.jsx +6 -0
  136. package/src/components/manage/Contents/ContentsUploadModal.jsx +10 -5
  137. package/src/components/manage/Controlpanels/AddonsControlpanel.jsx +3 -3
  138. package/src/components/manage/Controlpanels/Controlpanels.jsx +199 -224
  139. package/src/components/manage/Controlpanels/Controlpanels.test.jsx +46 -7
  140. package/src/components/manage/Controlpanels/Relations/BrokenRelations.jsx +66 -0
  141. package/src/components/manage/Controlpanels/Relations/Relations.jsx +114 -0
  142. package/src/components/manage/Controlpanels/Relations/RelationsListing.jsx +479 -0
  143. package/src/components/manage/Controlpanels/Relations/RelationsMatrix.jsx +531 -0
  144. package/src/components/manage/Controlpanels/Users/UserGroupMembershipControlPanel.jsx +3 -3
  145. package/src/components/manage/Controlpanels/Users/UserGroupMembershipListing.jsx +51 -82
  146. package/src/components/manage/Controlpanels/Users/UserGroupMembershipMatrix.jsx +79 -75
  147. package/src/components/manage/DragDropList/DragDropList.jsx +18 -13
  148. package/src/components/manage/Form/Form.jsx +5 -3
  149. package/src/components/manage/Form/InlineForm.jsx +39 -9
  150. package/src/components/manage/Form/InlineFormState.js +8 -0
  151. package/src/components/manage/History/History.jsx +11 -1
  152. package/src/components/manage/LinksToItem/LinksToItem.jsx +209 -0
  153. package/src/components/manage/LinksToItem/LinksToItem.test.jsx +97 -0
  154. package/src/components/manage/Multilingual/CreateTranslation.jsx +2 -2
  155. package/src/components/manage/Multilingual/TranslationObject.jsx +4 -3
  156. package/src/components/manage/Preferences/ChangePassword.jsx +2 -2
  157. package/src/components/manage/Preferences/PersonalPreferences.jsx +2 -2
  158. package/src/components/manage/Sharing/Sharing.jsx +5 -1
  159. package/src/components/manage/TemplateChooser/TemplateChooser.jsx +38 -0
  160. package/src/components/manage/TemplateChooser/TemplateChooser.test.jsx +34 -0
  161. package/src/components/manage/TemplateChooser/template.svg +10 -0
  162. package/src/components/manage/Toast/Toast.jsx +2 -2
  163. package/src/components/manage/Toolbar/More.jsx +15 -0
  164. package/src/components/manage/Toolbar/Types.jsx +2 -2
  165. package/src/components/manage/UniversalLink/UniversalLink.jsx +2 -6
  166. package/src/components/manage/UniversalLink/UniversalLink.test.jsx +36 -0
  167. package/src/components/manage/Widgets/ColorPickerWidget.jsx +6 -1
  168. package/src/components/manage/Widgets/DatetimeWidget.jsx +9 -5
  169. package/src/components/manage/Widgets/FileWidget.jsx +2 -1
  170. package/src/components/manage/Widgets/ObjectListWidget.jsx +3 -8
  171. package/src/components/manage/Widgets/RecurrenceWidget/ByDayField.jsx +2 -1
  172. package/src/components/manage/Widgets/RecurrenceWidget/MonthOfTheYearField.jsx +2 -1
  173. package/src/components/manage/Widgets/RecurrenceWidget/Occurences.jsx +2 -1
  174. package/src/components/manage/Widgets/RecurrenceWidget/RecurrenceWidget.jsx +8 -3
  175. package/src/components/manage/Widgets/RecurrenceWidget/WeekdayOfTheMonthField.jsx +2 -1
  176. package/src/components/manage/Widgets/SelectUtils.js +1 -1
  177. package/src/components/manage/Widgets/SelectWidget.jsx +1 -1
  178. package/src/components/theme/Anontools/Anontools.jsx +44 -72
  179. package/src/components/theme/Anontools/Anontools.stories.jsx +16 -6
  180. package/src/components/theme/Anontools/Anontools.test.jsx +16 -2
  181. package/src/components/theme/Breadcrumbs/Breadcrumbs.jsx +52 -99
  182. package/src/components/theme/Breadcrumbs/Breadcrumbs.stories.jsx +14 -13
  183. package/src/components/theme/Comments/CommentEditModal.jsx +63 -115
  184. package/src/components/theme/Component/Component.jsx +1 -1
  185. package/src/components/theme/ContactForm/ContactForm.jsx +108 -192
  186. package/src/components/theme/ContactForm/ContactForm.stories.jsx +1 -1
  187. package/src/components/theme/ContactForm/ContactForm.test.jsx +2 -3
  188. package/src/components/theme/Footer/Footer.jsx +2 -13
  189. package/src/components/theme/Header/Header.jsx +37 -63
  190. package/src/components/theme/Header/Header.test.jsx +18 -0
  191. package/src/components/theme/Icon/Icon.jsx +2 -2
  192. package/src/components/theme/LanguageSelector/LanguageSelector.js +8 -3
  193. package/src/components/theme/Login/Login.jsx +1 -0
  194. package/src/components/theme/Logo/Logo.jsx +2 -1
  195. package/src/components/theme/MultilingualRedirector/MultilingualRedirector.jsx +2 -2
  196. package/src/components/theme/Navigation/NavItem.jsx +4 -2
  197. package/src/components/theme/NotFound/NotFound.jsx +55 -41
  198. package/src/components/theme/PasswordReset/PasswordReset.jsx +7 -4
  199. package/src/components/theme/PasswordReset/RequestPasswordReset.jsx +1 -1
  200. package/src/components/theme/SearchWidget/SearchWidget.jsx +38 -98
  201. package/src/components/theme/Sitemap/Sitemap.jsx +5 -3
  202. package/src/components/theme/View/AlbumView.jsx +9 -1
  203. package/src/components/theme/View/DefaultView.jsx +1 -1
  204. package/src/components/theme/View/EventDatesInfo.jsx +2 -1
  205. package/src/components/theme/View/EventView.jsx +6 -2
  206. package/src/components/theme/View/FileView.jsx +23 -18
  207. package/src/components/theme/View/ImageView.jsx +37 -32
  208. package/src/components/theme/View/LinkView.jsx +53 -78
  209. package/src/components/theme/View/ListingView.jsx +33 -27
  210. package/src/components/theme/View/NewsItemView.jsx +10 -5
  211. package/src/components/theme/View/RenderBlocks.jsx +56 -21
  212. package/src/components/theme/View/RenderEmptyBlock.jsx +5 -0
  213. package/src/components/theme/View/SummaryView.jsx +47 -38
  214. package/src/components/theme/View/TabularView.jsx +59 -53
  215. package/src/components/theme/Widgets/DateWidget.jsx +2 -1
  216. package/src/components/theme/Widgets/DatetimeWidget.jsx +2 -1
  217. package/src/components/theme/Widgets/RelationsWidget.jsx +13 -11
  218. package/src/config/Blocks.jsx +44 -0
  219. package/src/config/ControlPanels.js +2 -0
  220. package/src/config/NonContentRoutes.jsx +1 -0
  221. package/src/config/RichTextEditor/Blocks.jsx +2 -2
  222. package/src/config/RichTextEditor/FromHTML.jsx +2 -2
  223. package/src/config/RichTextEditor/Styles.jsx +1 -1
  224. package/src/config/Widgets.jsx +2 -0
  225. package/src/config/index.js +24 -0
  226. package/src/config/server.js +2 -0
  227. package/src/constants/ActionTypes.js +4 -0
  228. package/src/constants/Indexes.js +3 -1
  229. package/src/constants/Languages.js +8 -4
  230. package/src/express-middleware/devproxy.js +1 -1
  231. package/src/express-middleware/files.js +3 -3
  232. package/src/express-middleware/images.js +4 -4
  233. package/src/express-middleware/ok.js +16 -0
  234. package/src/express-middleware/robotstxt.js +1 -1
  235. package/src/express-middleware/sitemap.js +37 -5
  236. package/src/express-middleware/static.js +3 -3
  237. package/src/helpers/Api/Api.js +1 -1
  238. package/src/helpers/Blocks/Blocks.js +48 -0
  239. package/src/helpers/Blocks/Blocks.test.js +79 -0
  240. package/src/helpers/Extensions/index.js +2 -1
  241. package/src/helpers/Extensions/withBlockSchemaEnhancer.js +15 -11
  242. package/src/helpers/Extensions/withBlockSchemaEnhancer.test.js +145 -0
  243. package/src/helpers/FormValidation/FormValidation.js +40 -2
  244. package/src/helpers/FormValidation/FormValidation.test.js +73 -0
  245. package/src/helpers/Html/Html.jsx +3 -1
  246. package/src/helpers/Html/Html.test.jsx +5 -0
  247. package/src/helpers/MessageLabels/MessageLabels.js +80 -0
  248. package/src/helpers/Robots/Robots.js +24 -6
  249. package/src/helpers/ScrollToTop/ScrollToTop.jsx +5 -3
  250. package/src/helpers/Sitemap/Sitemap.js +44 -2
  251. package/src/helpers/Url/Url.js +27 -6
  252. package/src/helpers/Url/Url.test.js +26 -0
  253. package/src/helpers/Utils/UseDetectClickOutside.stories.jsx +191 -0
  254. package/src/helpers/Utils/Utils.js +63 -13
  255. package/src/helpers/Utils/Utils.test.js +4 -4
  256. package/src/helpers/Utils/usePagination.js +67 -14
  257. package/src/helpers/Utils/usePagination.test.js +115 -0
  258. package/src/helpers/index.js +20 -10
  259. package/src/hooks/client/useClient.js +11 -0
  260. package/src/hooks/clipboard/useClipboard.js +26 -0
  261. package/src/hooks/index.js +2 -0
  262. package/src/icons/grid-block.svg +11 -0
  263. package/src/middleware/Api.test.js +54 -0
  264. package/src/middleware/api.js +24 -6
  265. package/src/middleware/index.js +2 -2
  266. package/src/reducers/actions/actions.js +8 -6
  267. package/src/reducers/actions/actions.test.js +70 -0
  268. package/src/reducers/breadcrumbs/breadcrumbs.js +1 -1
  269. package/src/reducers/index.js +2 -0
  270. package/src/reducers/navigation/navigation.js +1 -1
  271. package/src/reducers/relations/relations.js +173 -0
  272. package/src/reducers/types/types.js +1 -1
  273. package/src/routes.js +14 -0
  274. package/src/server.jsx +28 -23
  275. package/src/start-server.js +2 -2
  276. package/test-setup-config.js +2 -0
  277. package/theme/themes/pastanaga/extras/blocks.less +3 -1
  278. package/theme/themes/pastanaga/extras/contents.less +1 -0
  279. package/theme/themes/pastanaga/extras/grid.less +426 -0
  280. package/theme/themes/pastanaga/extras/main.less +3 -1
  281. package/theme/themes/pastanaga/extras/search.less +6 -0
  282. package/theme/themes/pastanaga/extras/sidebar.less +4 -0
  283. package/theme/themes/pastanaga/extras/toc.less +29 -0
  284. package/theme/themes/pastanaga/extras/userscontrolpanel.less +99 -76
  285. package/.changelog.draft +0 -31
  286. package/.editorconfig +0 -36
  287. package/.storybook/main.js +0 -127
  288. package/.storybook/manager.js +0 -15
  289. package/.storybook/preview.js +0 -21
  290. package/.storybook/static/previewImage.svg +0 -48
  291. package/.yarnrc.yml +0 -5
  292. package/jsdoc.json +0 -16
  293. package/netlify.toml +0 -5
  294. package/pyvenv.cfg +0 -3
  295. package/share/man/man1/ttx.1 +0 -225
  296. package/src/components/theme/Header/Header.md +0 -27
  297. package/towncrier.toml +0 -33
@@ -0,0 +1,14 @@
1
+ export const GridBlockDataAdapter = ({
2
+ block,
3
+ data,
4
+ id,
5
+ onChangeBlock,
6
+ value,
7
+ }) => {
8
+ let dataSaved = {
9
+ ...data,
10
+ [id]: value,
11
+ };
12
+
13
+ onChangeBlock(block, dataSaved);
14
+ };
@@ -0,0 +1,6 @@
1
+ <svg xmlns="http://www.w3.org/2000/svg" width="96" height="96" viewBox="0 0 96 96">
2
+ <g fill="none" fill-rule="evenodd">
3
+ <rect width="96" height="96" fill="#9FD1E5" rx="3"/>
4
+ <rect width="67" height="53" fill="#FFF" opacity=".9" transform="translate(15 22)"/>
5
+ </g>
6
+ </svg>
@@ -0,0 +1,9 @@
1
+ <svg xmlns="http://www.w3.org/2000/svg" width="96" height="96" viewBox="0 0 96 96">
2
+ <g fill="none" fill-rule="evenodd">
3
+ <rect width="96" height="96" fill="#9FD1E5" rx="3"/>
4
+ <g fill="#FFF" opacity=".9" transform="translate(9 22)">
5
+ <rect width="37" height="53"/>
6
+ <rect width="37" height="53" x="42"/>
7
+ </g>
8
+ </g>
9
+ </svg>
@@ -0,0 +1,10 @@
1
+ <svg xmlns="http://www.w3.org/2000/svg" width="96" height="96" viewBox="0 0 96 96">
2
+ <g fill="none" fill-rule="evenodd">
3
+ <rect width="96" height="96" fill="#9FD1E5" rx="3"/>
4
+ <g fill="#FFF" opacity=".9" transform="translate(6 22)">
5
+ <rect width="25" height="53" x="58"/>
6
+ <rect width="25" height="53"/>
7
+ <rect width="25" height="53" x="29"/>
8
+ </g>
9
+ </g>
10
+ </svg>
@@ -0,0 +1,11 @@
1
+ <svg xmlns="http://www.w3.org/2000/svg" width="96" height="96" viewBox="0 0 96 96">
2
+ <g fill="none" fill-rule="evenodd">
3
+ <rect width="96" height="96" fill="#9FD1E5" rx="3"/>
4
+ <g fill="#FFF" opacity=".9" transform="translate(8 22)">
5
+ <rect width="18" height="53" x="42"/>
6
+ <rect width="18" height="53" x="63"/>
7
+ <rect width="18" height="53"/>
8
+ <rect width="18" height="53" x="21"/>
9
+ </g>
10
+ </g>
11
+ </svg>
@@ -0,0 +1,35 @@
1
+ import { defineMessages } from 'react-intl';
2
+
3
+ const messages = defineMessages({
4
+ headline: {
5
+ id: 'Headline',
6
+ defaultMessage: 'Headline',
7
+ },
8
+ grid: {
9
+ id: 'Grid',
10
+ defaultMessage: 'Grid',
11
+ },
12
+ });
13
+
14
+ export const GridBlockSchema = (props) => {
15
+ const { intl } = props;
16
+
17
+ return {
18
+ title: intl.formatMessage(messages.grid),
19
+ block: 'grid',
20
+ fieldsets: [
21
+ {
22
+ id: 'default',
23
+ title: 'Default',
24
+ fields: ['headline'],
25
+ },
26
+ ],
27
+
28
+ properties: {
29
+ headline: {
30
+ title: intl.formatMessage(messages.headline),
31
+ },
32
+ },
33
+ required: [],
34
+ };
35
+ };
@@ -0,0 +1,47 @@
1
+ import { defineMessages } from 'react-intl';
2
+ import { blocksFormGenerator } from '@plone/volto/helpers';
3
+
4
+ import gridTemplate1 from './grid-1.svg';
5
+ import gridTemplate2 from './grid-2.svg';
6
+ import gridTemplate3 from './grid-3.svg';
7
+ import gridTemplate4 from './grid-4.svg';
8
+
9
+ const messages = defineMessages({
10
+ column: {
11
+ id: 'column',
12
+ defaultMessage: 'column',
13
+ },
14
+ columns: {
15
+ id: 'columns',
16
+ defaultMessage: 'columns',
17
+ },
18
+ });
19
+
20
+ const templates = (type) => (intl) => [
21
+ {
22
+ image: gridTemplate1,
23
+ id: 'gridtemplateone',
24
+ title: `1 ${intl.formatMessage(messages.column)}`,
25
+ blocksData: blocksFormGenerator(1, type),
26
+ },
27
+ {
28
+ image: gridTemplate2,
29
+ id: 'gridtemplatetwo',
30
+ title: `2 ${intl.formatMessage(messages.columns)}`,
31
+ blocksData: blocksFormGenerator(2, type),
32
+ },
33
+ {
34
+ image: gridTemplate3,
35
+ id: 'gridtemplatethree',
36
+ title: `3 ${intl.formatMessage(messages.columns)}`,
37
+ blocksData: blocksFormGenerator(3, type),
38
+ },
39
+ {
40
+ image: gridTemplate4,
41
+ id: 'gridtemplatefour',
42
+ title: `4 ${intl.formatMessage(messages.columns)}`,
43
+ blocksData: blocksFormGenerator(4, type),
44
+ },
45
+ ];
46
+
47
+ export default templates;
@@ -14,7 +14,11 @@ import { defineMessages, injectIntl } from 'react-intl';
14
14
  import cx from 'classnames';
15
15
 
16
16
  import { injectLazyLibs } from '@plone/volto/helpers/Loadable/Loadable';
17
- import { flattenToAppURL, getBaseUrl } from '@plone/volto/helpers';
17
+ import {
18
+ flattenToAppURL,
19
+ getBaseUrl,
20
+ validateFileUploadSize,
21
+ } from '@plone/volto/helpers';
18
22
  import { createContent } from '@plone/volto/actions';
19
23
  import { Icon, SidebarPortal, LinkMore } from '@plone/volto/components';
20
24
 
@@ -275,6 +279,7 @@ class EditComponent extends Component {
275
279
  */
276
280
  onUploadImage({ target }) {
277
281
  const file = target.files[0];
282
+ if (!validateFileUploadSize(file, this.props.intl.formatMessage)) return;
278
283
  this.setState({
279
284
  uploading: true,
280
285
  });
@@ -21,6 +21,7 @@ import {
21
21
  flattenToAppURL,
22
22
  getBaseUrl,
23
23
  isInternalURL,
24
+ validateFileUploadSize,
24
25
  } from '@plone/volto/helpers';
25
26
 
26
27
  import imageBlockSVG from '@plone/volto/components/manage/Blocks/Image/block-image.svg';
@@ -125,6 +126,7 @@ class Edit extends Component {
125
126
  onUploadImage = (e) => {
126
127
  e.stopPropagation();
127
128
  const file = e.target.files[0];
129
+ if (!validateFileUploadSize(file, this.props.intl.formatMessage)) return;
128
130
  this.setState({
129
131
  uploading: true,
130
132
  });
@@ -178,23 +180,25 @@ class Edit extends Component {
178
180
  * @param {array} files File objects
179
181
  * @returns {undefined}
180
182
  */
181
- onDrop = (file) => {
182
- this.setState({
183
- uploading: true,
184
- });
183
+ onDrop = (files) => {
184
+ if (!validateFileUploadSize(files[0], this.props.intl.formatMessage)) {
185
+ this.setState({ dragging: false });
186
+ return;
187
+ }
188
+ this.setState({ uploading: true });
185
189
 
186
- readAsDataURL(file[0]).then((data) => {
190
+ readAsDataURL(files[0]).then((data) => {
187
191
  const fields = data.match(/^data:(.*);(.*),(.*)$/);
188
192
  this.props.createContent(
189
193
  getBaseUrl(this.props.pathname),
190
194
  {
191
195
  '@type': 'Image',
192
- title: file[0].name,
196
+ title: files[0].name,
193
197
  image: {
194
198
  data: fields[3],
195
199
  encoding: fields[2],
196
200
  'content-type': fields[1],
197
- filename: file[0].name,
201
+ filename: files[0].name,
198
202
  },
199
203
  },
200
204
  this.props.block,
@@ -8,7 +8,7 @@ import { ImageSchema } from './schema';
8
8
  import imageSVG from '@plone/volto/icons/image.svg';
9
9
 
10
10
  const ImageSidebar = (props) => {
11
- const { data, block, onChangeBlock } = props;
11
+ const { blocksConfig, data, block, onChangeBlock } = props;
12
12
  const intl = useIntl();
13
13
  const schema = ImageSchema({ formData: data, intl });
14
14
  return (
@@ -55,6 +55,7 @@ const ImageSidebar = (props) => {
55
55
  onChangeBlock={onChangeBlock}
56
56
  formData={data}
57
57
  block={block}
58
+ blocksConfig={blocksConfig}
58
59
  />
59
60
  </>
60
61
  );
@@ -101,3 +101,14 @@ export function ImageSchema({ formData, intl }) {
101
101
  required: [],
102
102
  };
103
103
  }
104
+
105
+ export const gridImageDisableSizeAndPositionHandlersSchema = ({
106
+ schema,
107
+ formData,
108
+ intl,
109
+ }) => {
110
+ schema.fieldsets[0].fields = schema.fieldsets[0].fields.filter(
111
+ (item) => !['align', 'size'].includes(item),
112
+ );
113
+ return schema;
114
+ };
@@ -2,10 +2,15 @@ import React from 'react';
2
2
  import PropTypes from 'prop-types';
3
3
  import { ConditionalLink, UniversalLink } from '@plone/volto/components';
4
4
  import { flattenToAppURL } from '@plone/volto/helpers';
5
-
6
5
  import { isInternalURL } from '@plone/volto/helpers/Url/Url';
7
6
 
8
- const DefaultTemplate = ({ items, linkTitle, linkHref, isEditMode }) => {
7
+ const DefaultTemplate = ({
8
+ headlineTag,
9
+ items,
10
+ linkTitle,
11
+ linkHref,
12
+ isEditMode,
13
+ }) => {
9
14
  let link = null;
10
15
  let href = linkHref?.[0]?.['@id'] || '';
11
16
 
@@ -19,6 +24,16 @@ const DefaultTemplate = ({ items, linkTitle, linkHref, isEditMode }) => {
19
24
  link = <UniversalLink href={href}>{linkTitle || href}</UniversalLink>;
20
25
  }
21
26
 
27
+ const getTitleTag = (tag) => {
28
+ const level = tag.slice(-1);
29
+ if (/\d/.test(level)) {
30
+ return `h${Number(level) + 1}`;
31
+ } else {
32
+ return 'h3';
33
+ }
34
+ };
35
+ const TitleTag = headlineTag ? getTitleTag(headlineTag) : 'h3';
36
+
22
37
  return (
23
38
  <>
24
39
  <div className="items">
@@ -26,7 +41,7 @@ const DefaultTemplate = ({ items, linkTitle, linkHref, isEditMode }) => {
26
41
  <div className="listing-item" key={item['@id']}>
27
42
  <ConditionalLink item={item} condition={!isEditMode}>
28
43
  <div className="listing-body">
29
- <h4>{item.title ? item.title : item.id}</h4>
44
+ <TitleTag>{item.title ? item.title : item.id}</TitleTag>
30
45
  <p>{item.description}</p>
31
46
  </div>
32
47
  </ConditionalLink>
@@ -26,21 +26,7 @@ const messages = defineMessages({
26
26
  const Edit = React.memo(
27
27
  (props) => {
28
28
  const { data, onChangeBlock, block, selected, pathname } = props;
29
-
30
29
  const intl = useIntl();
31
-
32
- // componentDidMount
33
- React.useEffect(() => {
34
- if (!data.query) {
35
- onChangeBlock(block, {
36
- ...data,
37
- query: [],
38
- block,
39
- });
40
- }
41
- /* eslint-disable react-hooks/exhaustive-deps */
42
- }, []);
43
-
44
30
  const placeholder =
45
31
  data.placeholder ||
46
32
  (data?.querystring?.query?.length
@@ -1,14 +1,35 @@
1
- import React, { createRef } from 'react';
1
+ import React, { createRef, useMemo } from 'react';
2
2
  import { FormattedMessage, injectIntl } from 'react-intl';
3
3
  import cx from 'classnames';
4
4
  import { Pagination, Dimmer, Loader } from 'semantic-ui-react';
5
+ import Slugger from 'github-slugger';
5
6
  import { Icon } from '@plone/volto/components';
7
+ import { renderLinkElement } from '@plone/volto-slate/editor/render';
6
8
  import config from '@plone/volto/registry';
7
9
  import withQuerystringResults from './withQuerystringResults';
8
10
 
9
11
  import paginationLeftSVG from '@plone/volto/icons/left-key.svg';
10
12
  import paginationRightSVG from '@plone/volto/icons/right-key.svg';
11
13
 
14
+ const Headline = ({ headlineTag, id, data = {}, listingItems, isEditMode }) => {
15
+ let attr = { id };
16
+ const slug = Slugger.slug(data.headline);
17
+ attr.id = slug || id;
18
+ const LinkedHeadline = useMemo(() => renderLinkElement(headlineTag), [
19
+ headlineTag,
20
+ ]);
21
+ return (
22
+ <LinkedHeadline
23
+ mode={!isEditMode && 'view'}
24
+ children={data.headline}
25
+ attributes={attr}
26
+ className={cx('headline', {
27
+ emptyListing: !listingItems?.length > 0,
28
+ })}
29
+ />
30
+ );
31
+ };
32
+
12
33
  const ListingBody = withQuerystringResults((props) => {
13
34
  const {
14
35
  data = {},
@@ -22,6 +43,7 @@ const ListingBody = withQuerystringResults((props) => {
22
43
  nextBatch,
23
44
  isFolderContentsListing,
24
45
  hasLoaded,
46
+ id,
25
47
  } = props;
26
48
 
27
49
  let ListingBodyTemplate;
@@ -50,13 +72,13 @@ const ListingBody = withQuerystringResults((props) => {
50
72
  return (
51
73
  <>
52
74
  {data.headline && (
53
- <HeadlineTag
54
- className={cx('headline', {
55
- emptyListing: !listingItems?.length > 0,
56
- })}
57
- >
58
- {data.headline}
59
- </HeadlineTag>
75
+ <Headline
76
+ headlineTag={HeadlineTag}
77
+ id={id}
78
+ listingItems={listingItems}
79
+ data={data}
80
+ isEditMode={isEditMode}
81
+ />
60
82
  )}
61
83
  {listingItems?.length > 0 ? (
62
84
  <div ref={listingRef}>
@@ -36,6 +36,26 @@ test('renders a ListingBody component', () => {
36
36
  content: {
37
37
  data: {
38
38
  is_folderish: true,
39
+ blocks: {
40
+ '839ee00b-013b-4f4a-9b10-8867938fdac3': {
41
+ '@type': 'listing',
42
+ block: '839ee00b-013b-4f4a-9b10-8867938fdac3',
43
+ headlineTag: 'h2',
44
+ query: [],
45
+ querystring: {
46
+ b_size: '2',
47
+ query: [
48
+ {
49
+ i: 'path',
50
+ o: 'plone.app.querystring.operation.string.absolutePath',
51
+ v: '/',
52
+ },
53
+ ],
54
+ sort_order: 'ascending',
55
+ },
56
+ variation: 'default',
57
+ },
58
+ },
39
59
  },
40
60
  },
41
61
  intl: {
@@ -1,7 +1,13 @@
1
1
  import { getQueryStringResults } from '@plone/volto/actions';
2
2
  import { resolveBlockExtensions } from '@plone/volto/helpers';
3
3
 
4
- export default ({ dispatch, data, path, blocksConfig }) => {
4
+ export default function getListingBlockAsyncData({
5
+ dispatch,
6
+ id,
7
+ data,
8
+ path,
9
+ blocksConfig,
10
+ }) {
5
11
  const { resolvedExtensions } = resolveBlockExtensions(data, blocksConfig);
6
12
 
7
13
  return [
@@ -14,8 +20,8 @@ export default ({ dispatch, data, path, blocksConfig }) => {
14
20
  ? { fullobjects: 1 }
15
21
  : { metadata_fields: '_all' }),
16
22
  },
17
- data.block,
23
+ id,
18
24
  ),
19
25
  ),
20
26
  ];
21
- };
27
+ }
@@ -1,4 +1,4 @@
1
- import React from 'react';
1
+ import React, { useRef } from 'react';
2
2
  import { useDispatch, useSelector } from 'react-redux';
3
3
  import hoistNonReactStatics from 'hoist-non-react-statics';
4
4
  import useDeepCompareEffect from 'use-deep-compare-effect';
@@ -14,18 +14,23 @@ function getDisplayName(WrappedComponent) {
14
14
 
15
15
  export default function withQuerystringResults(WrappedComponent) {
16
16
  function WithQuerystringResults(props) {
17
- const { data = {}, properties: content, path, variation } = props;
17
+ const {
18
+ data = {},
19
+ id = data.block,
20
+ properties: content,
21
+ path,
22
+ variation,
23
+ } = props;
18
24
  const { settings } = config;
19
25
  const querystring = data.querystring || data; // For backwards compat with data saved before Blocks schema. Note, this is also how the Search block passes data to ListingBody
20
26
 
21
- const { block } = data;
22
27
  const { b_size = settings.defaultPageSize } = querystring; // batchsize
23
28
 
24
29
  // save the path so it won't trigger dispatch on eager router location change
25
30
  const [initialPath] = React.useState(getBaseUrl(path));
26
31
 
27
32
  const copyFields = ['limit', 'query', 'sort_on', 'sort_order', 'depth'];
28
-
33
+ const { currentPage, setCurrentPage } = usePagination(id, 1);
29
34
  const adaptedQuery = Object.assign(
30
35
  variation?.fullobjects ? { fullobjects: 1 } : { metadata_fields: '_all' },
31
36
  {
@@ -37,7 +42,9 @@ export default function withQuerystringResults(WrappedComponent) {
37
42
  : {},
38
43
  ),
39
44
  );
40
- const { currentPage, setCurrentPage } = usePagination(querystring, 1);
45
+ const adaptedQueryRef = useRef(adaptedQuery);
46
+ const currentPageRef = useRef(currentPage);
47
+
41
48
  const querystringResults = useSelector(
42
49
  (state) => state.querystringsearch.subrequests,
43
50
  );
@@ -45,32 +52,31 @@ export default function withQuerystringResults(WrappedComponent) {
45
52
 
46
53
  const folderItems = content?.is_folderish ? content.items : [];
47
54
  const hasQuery = querystring?.query?.length > 0;
48
- const hasLoaded = hasQuery ? !querystringResults?.[block]?.loading : true;
55
+ const hasLoaded = hasQuery ? querystringResults?.[id]?.loaded : true;
49
56
 
50
- const listingItems =
51
- querystring?.query?.length > 0 && querystringResults?.[block]
52
- ? querystringResults?.[block]?.items || []
53
- : folderItems;
57
+ const listingItems = hasQuery
58
+ ? querystringResults?.[id]?.items || []
59
+ : folderItems;
54
60
 
55
61
  const showAsFolderListing = !hasQuery && content?.items_total > b_size;
56
62
  const showAsQueryListing =
57
- hasQuery && querystringResults?.[block]?.total > b_size;
63
+ hasQuery && querystringResults?.[id]?.total > b_size;
58
64
 
59
65
  const totalPages = showAsFolderListing
60
66
  ? Math.ceil(content.items_total / b_size)
61
67
  : showAsQueryListing
62
- ? Math.ceil(querystringResults[block].total / b_size)
68
+ ? Math.ceil(querystringResults[id].total / b_size)
63
69
  : 0;
64
70
 
65
71
  const prevBatch = showAsFolderListing
66
72
  ? content.batching?.prev
67
73
  : showAsQueryListing
68
- ? querystringResults[block].batching?.prev
74
+ ? querystringResults[id].batching?.prev
69
75
  : null;
70
76
  const nextBatch = showAsFolderListing
71
77
  ? content.batching?.next
72
78
  : showAsQueryListing
73
- ? querystringResults[block].batching?.next
79
+ ? querystringResults[id].batching?.next
74
80
  : null;
75
81
 
76
82
  const isImageGallery =
@@ -80,7 +86,7 @@ export default function withQuerystringResults(WrappedComponent) {
80
86
  useDeepCompareEffect(() => {
81
87
  if (hasQuery) {
82
88
  dispatch(
83
- getQueryStringResults(initialPath, adaptedQuery, block, currentPage),
89
+ getQueryStringResults(initialPath, adaptedQuery, id, currentPage),
84
90
  );
85
91
  } else if (isImageGallery && !hasQuery) {
86
92
  // when used as image gallery, it doesn't need a query to list children
@@ -98,14 +104,16 @@ export default function withQuerystringResults(WrappedComponent) {
98
104
  },
99
105
  ],
100
106
  },
101
- block,
107
+ id,
102
108
  ),
103
109
  );
104
110
  } else {
105
111
  dispatch(getContent(initialPath, null, null, currentPage));
106
112
  }
113
+ adaptedQueryRef.current = adaptedQuery;
114
+ currentPageRef.current = currentPage;
107
115
  }, [
108
- block,
116
+ id,
109
117
  isImageGallery,
110
118
  adaptedQuery,
111
119
  hasQuery,
@@ -118,7 +126,7 @@ export default function withQuerystringResults(WrappedComponent) {
118
126
  <WrappedComponent
119
127
  {...props}
120
128
  onPaginationChange={(e, { activePage }) => setCurrentPage(activePage)}
121
- total={querystringResults?.[block]?.total}
129
+ total={querystringResults?.[id]?.total}
122
130
  batch_size={b_size}
123
131
  currentPage={currentPage}
124
132
  totalPages={totalPages}
@@ -1,5 +1,4 @@
1
- import React from 'react';
2
- import useDeepCompareEffect from 'use-deep-compare-effect';
1
+ import React, { useEffect } from 'react';
3
2
  import { defineMessages } from 'react-intl';
4
3
  import { compose } from 'redux';
5
4
 
@@ -60,9 +59,11 @@ const SearchBlockEdit = (props) => {
60
59
  };
61
60
 
62
61
  const { query = {} } = data || {};
63
- useDeepCompareEffect(() => {
62
+ // We don't need deep compare here, as this is just json serializable data.
63
+ const deepQuery = JSON.stringify(query);
64
+ useEffect(() => {
64
65
  onTriggerSearch();
65
- }, [query, onTriggerSearch]);
66
+ }, [deepQuery, onTriggerSearch]);
66
67
 
67
68
  return (
68
69
  <>
@@ -57,7 +57,7 @@ const applyDefaults = (data, root) => {
57
57
  };
58
58
 
59
59
  const SearchBlockView = (props) => {
60
- const { data, searchData, mode = 'view', variation } = props;
60
+ const { id, data, searchData, mode = 'view', variation } = props;
61
61
 
62
62
  const Layout = variation.view;
63
63
 
@@ -89,6 +89,7 @@ const SearchBlockView = (props) => {
89
89
  setSelectedView={setSelectedView}
90
90
  >
91
91
  <ListingBody
92
+ id={id}
92
93
  variation={{ ...data, ...listingBodyVariation }}
93
94
  data={listingBodyData}
94
95
  path={props.path}
@@ -4,6 +4,7 @@ import { defineMessages, injectIntl } from 'react-intl';
4
4
  import { injectLazyLibs } from '@plone/volto/helpers/Loadable/Loadable';
5
5
  import { compose } from 'redux';
6
6
  import { Icon } from '@plone/volto/components';
7
+ import { toBackendLang } from '@plone/volto/helpers/Utils/Utils';
7
8
  import { connect } from 'react-redux';
8
9
 
9
10
  import leftKey from '@plone/volto/icons/left-key.svg';
@@ -82,7 +83,9 @@ const DateRangeFacet = (props) => {
82
83
  noBorder
83
84
  showClearDates
84
85
  customCloseIcon={<CloseIcon />}
85
- displayFormat={moment.localeData(lang).longDateFormat('L')}
86
+ displayFormat={moment
87
+ .localeData(toBackendLang(lang))
88
+ .longDateFormat('L')}
86
89
  focusedInput={focused}
87
90
  onFocusChange={(focusedInput) => setFocused(focusedInput)}
88
91
  onDatesChange={({ startDate, endDate }) => {