design-comuni-plone-theme 10.6.1 → 10.6.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,32 @@
1
1
 
2
2
 
3
+ ## [10.6.3](https://github.com/redturtle/design-comuni-plone-theme/compare/v10.6.2...v10.6.3) (2023-12-15)
4
+
5
+
6
+ ### Bug Fixes
7
+
8
+ * different styles and ui for all Search block listing templates when compared to default Listing template ([#437](https://github.com/redturtle/design-comuni-plone-theme/issues/437)) ([d6cf41d](https://github.com/redturtle/design-comuni-plone-theme/commit/d6cf41dd63e6d1b891ff045238d5d7d9d9df5ff0))
9
+ * gdpr privacy conditional embed to work in diff view ([#438](https://github.com/redturtle/design-comuni-plone-theme/issues/438)) ([6a8c361](https://github.com/redturtle/design-comuni-plone-theme/commit/6a8c361feda654f0301b5026533234438469ff37))
10
+
11
+
12
+ ### Documentation
13
+
14
+ * aggiornamento della lista dei comuni in publiccode.yml ([#159](https://github.com/redturtle/design-comuni-plone-theme/issues/159)) ([7e87e9f](https://github.com/redturtle/design-comuni-plone-theme/commit/7e87e9f2071adeced38eae57eb8d09cee6433fa1))
15
+ * updated publiccode and release log ([f27a61a](https://github.com/redturtle/design-comuni-plone-theme/commit/f27a61aef3f41ac34bcbdf9e58e2a6ae0166d0f9))
16
+
17
+ ## [10.6.2](https://github.com/redturtle/design-comuni-plone-theme/compare/v10.6.1...v10.6.2) (2023-12-14)
18
+
19
+
20
+ ### Bug Fixes
21
+
22
+ * custom inline styles rendering in wysiwygwidget ([17e1d10](https://github.com/redturtle/design-comuni-plone-theme/commit/17e1d10a2de1c8ba4d12a7364bc8858761b4b92e))
23
+
24
+
25
+ ### Documentation
26
+
27
+ * aggiornamento lista dei comuni in publiccode.yml ([#158](https://github.com/redturtle/design-comuni-plone-theme/issues/158)) ([2abad9a](https://github.com/redturtle/design-comuni-plone-theme/commit/2abad9aecaa288ca87670183df13212bdb47fa66))
28
+ * updated publiccode and release log ([38d8d00](https://github.com/redturtle/design-comuni-plone-theme/commit/38d8d00daf1b3c822d11a701ecc3a83657c865cb))
29
+
3
30
  ## [10.6.1](https://github.com/RedTurtle/design-comuni-plone-theme/compare/v10.6.0...v10.6.1) (2023-12-13)
4
31
 
5
32
 
package/RELEASE.md CHANGED
@@ -41,11 +41,23 @@
41
41
  - ...
42
42
  -->
43
43
 
44
+ ## Versione 10.6.3 (15/12/2023)
45
+
46
+ ### Fix
47
+
48
+ - Sistemati alcuni problemi di visualizzazione nei template disponibili per il blocco Cerca. Ora tutti i template disponibili per questo blocco rispecchiano graficamente quelli per il blocco Elenco sia in visualizzazione che in modifica.
49
+
50
+ ## Versione 10.6.2 (14/12/2023)
51
+
52
+ ### Fix
53
+
54
+ - Ora si vedono correttamente gli stili di allineamento del testo in alcuni editor di testo, ad esempio header e footer dei sottositi.
55
+
44
56
  ## Versione 10.6.1 (13/12/2023)
45
57
 
46
58
  ### Novità
47
59
 
48
- - I seguenti campi sono ora riordinabili liberamente: "Timeline tempi e scadenze" per il tipo di contenuto *Servizio* e "Valore punto di contatto" del tipo di contenuto *Punto di contatto*.
60
+ - I seguenti campi sono ora riordinabili liberamente: "Timeline tempi e scadenze" per il tipo di contenuto _Servizio_ e "Valore punto di contatto" del tipo di contenuto _Punto di contatto_.
49
61
 
50
62
  ### Fix
51
63
 
package/package.json CHANGED
@@ -2,7 +2,7 @@
2
2
  "name": "design-comuni-plone-theme",
3
3
  "description": "Volto Theme for Italia design guidelines",
4
4
  "license": "GPL-v3",
5
- "version": "10.6.1",
5
+ "version": "10.6.3",
6
6
  "main": "src/index.js",
7
7
  "keywords": [
8
8
  "volto-addon",
@@ -146,7 +146,7 @@
146
146
  "volto-editablefooter": "5.0.1",
147
147
  "volto-feedback": "0.1.5",
148
148
  "volto-form-block": "3.1.0",
149
- "volto-gdpr-privacy": "2.1.0",
149
+ "volto-gdpr-privacy": "2.1.1",
150
150
  "volto-google-analytics": "2.0.0",
151
151
  "volto-multilingual-widget": "3.0.0",
152
152
  "volto-querywidget-with-browser": "0.4.0",
package/publiccode.yml CHANGED
@@ -227,9 +227,9 @@ maintenance:
227
227
  name: io-Comune - Il sito AgID per Comuni ed Enti Pubblici
228
228
  platforms:
229
229
  - web
230
- releaseDate: '2023-12-13'
230
+ releaseDate: '2023-12-15'
231
231
  softwareType: standalone/web
232
- softwareVersion: 10.6.1
232
+ softwareVersion: 10.6.3
233
233
  url: 'https://github.com/italia/design-comuni-plone-theme'
234
234
  usedBy:
235
235
  - ASP Comuni Modenesi Area Nord
@@ -243,6 +243,7 @@ usedBy:
243
243
  - Biblioteche Pianura Est
244
244
  - Camera di Commercio dell'Umbria
245
245
  - Camera di Commercio di Reggio Emilia
246
+ - Comune della Spezia
246
247
  - Comune di Bibbiano
247
248
  - Comune di Camposanto
248
249
  - Comune di Cantagallo
@@ -251,14 +252,21 @@ usedBy:
251
252
  - Comune di Concordia sul Secchia
252
253
  - Comune di Gattatico
253
254
  - Comune di Finale Emilia
255
+ - Comune di Fiorano Modenese
256
+ - Comune di Formigine
257
+ - Comune di Frassinoro
254
258
  - Comune di Imola
259
+ - Comune di Maranello
255
260
  - Comune di Medolla
256
261
  - Comune di Mirandola
257
262
  - Comune di Modena
258
263
  - Comune di Montecchio Emilia
264
+ - Comune di Montefiorino
259
265
  - Comune di Novellara
266
+ - Comune di Palagano
260
267
  - Comune di Parma
261
268
  - Comune di Piacenza
269
+ - Comune di Prignano
262
270
  - Comune di Reggio Emilia
263
271
  - Comune di San Felice sul Panaro
264
272
  - Comune di San Lazzaro di Savena
@@ -266,6 +274,8 @@ usedBy:
266
274
  - Comune di San Possidonio
267
275
  - Comune di San Prospero
268
276
  - Comune di Santilario d'Enza
277
+ - Comune di Sassuolo
278
+ - Comune di Toscolano Maderno
269
279
  - Comune di Vaiano
270
280
  - Comune di Vernio
271
281
  - Comando Generale della Guardia di Finanza
@@ -273,6 +283,7 @@ usedBy:
273
283
  - Nuovo Circondario Imolese
274
284
  - Ospedali Galliera - Bilancio Sociale
275
285
  - Provincia di Pisa
286
+ - Unione Comuni Distretto Ceramico
276
287
  - UCMAN (Unione dei Comuni Modenesi Area Nord)
277
288
  - Unione Val d'Enza
278
289
  - Unione Val di Bisenzio
@@ -136,33 +136,50 @@ const ItaliaFromHTMLCustomBlockFn = (element) => {
136
136
  ret = {
137
137
  type: 'buttons',
138
138
  };
139
- } else if (element.className === 'draftjs-text-larger') {
139
+ } else if (element.className === 'text-center') {
140
140
  ret = {
141
- type: 'TEXT_LARGER',
141
+ type: 'align-center',
142
+ };
143
+ } else if (element.className === 'text-end') {
144
+ ret = {
145
+ type: 'align-right',
146
+ };
147
+ } else if (element.className === 'text-justify') {
148
+ ret = {
149
+ type: 'align-justify',
142
150
  };
143
151
  }
144
152
  }
145
153
  return ret;
146
154
  };
147
155
 
156
+ const ItaliaFromHTMLCustomInlineFn = (element, { Style }) => {
157
+ if (element.tagName === 'SPAN') {
158
+ if (element.className === 'draftjs-text-larger') {
159
+ return Style('TEXT_LARGER');
160
+ }
161
+ }
162
+ };
163
+
148
164
  export default function applyConfig(config) {
149
165
  config.settings.richtextEditorSettings = (props) => {
150
166
  const { plugins /*, inlineToolbarButtons*/ } = Plugins(props); // volto plugins
151
- const { extendedBlockRenderMap, blockStyleFn, listBlockTypes } =
152
- Blocks(props);
167
+ const { extendedBlockRenderMap, blockStyleFn, listBlockTypes } = Blocks(
168
+ props,
169
+ );
153
170
 
154
171
  const { immutableLib } = props;
155
172
  const { Map } = immutableLib;
156
173
 
157
174
  const blockRenderMap = Map({
158
175
  'align-center': {
159
- element: 'p',
176
+ element: (props) => <p {...props} style={{ textAlign: 'center' }} />,
160
177
  },
161
178
  'align-right': {
162
- element: 'p',
179
+ element: (props) => <p {...props} style={{ textAlign: 'right' }} />,
163
180
  },
164
181
  'align-justify': {
165
- element: 'p',
182
+ element: (props) => <p {...props} style={{ textAlign: 'justify' }} />,
166
183
  },
167
184
  'callout-bg': {
168
185
  element: 'p',
@@ -179,9 +196,6 @@ export default function applyConfig(config) {
179
196
  r = r.length > 0 ? ' ' : r;
180
197
 
181
198
  const styles = {
182
- 'align-center': 'text-center',
183
- 'align-right': 'text-end',
184
- 'align-justify': 'text-justify',
185
199
  callout: 'callout',
186
200
  'callout-bg': 'callout-bg',
187
201
  buttons: 'draftjs-buttons',
@@ -203,9 +217,12 @@ export default function applyConfig(config) {
203
217
  ...plugins,
204
218
  ...ItaliaRichTextEditorPlugins(props),
205
219
  ],
206
- richTextEditorInlineToolbarButtons:
207
- ItaliaRichTextEditorInlineToolbarButtons(props, plugins), //[inlineToolbarButtons,...ItaliaRichTextEditorInlineToolbarButtons(props)]
208
- FromHTMLCustomBlockFn: ItaliaFromHTMLCustomBlockFn, //FromHTMLCustomBlockFn
220
+ richTextEditorInlineToolbarButtons: ItaliaRichTextEditorInlineToolbarButtons(
221
+ props,
222
+ plugins,
223
+ ), //[inlineToolbarButtons,...ItaliaRichTextEditorInlineToolbarButtons(props)]
224
+ FromHTMLCustomBlockFn: ItaliaFromHTMLCustomBlockFn,
225
+ FromHTMLCustomInlineFn: ItaliaFromHTMLCustomInlineFn,
209
226
  customStyleMap: {
210
227
  TEXT_LARGER: { fontSize: '1.75rem' },
211
228
  },
@@ -1,5 +1,7 @@
1
1
  /* CUSTOMIZATIONS:
2
2
  - Agid styling
3
+ - Add class .block.listing in listing body container div to use
4
+ existing listing template styles
3
5
  */
4
6
 
5
7
  import React from 'react';
@@ -99,7 +101,8 @@ const SearchBlockView = (props) => {
99
101
  selectedView={selectedView}
100
102
  setSelectedView={setSelectedView}
101
103
  >
102
- <div className="search-results">
104
+ {/* Add class .block.listing to benefit from existing listing template styles */}
105
+ <div className="block listing search-results">
103
106
  <ListingBody
104
107
  variation={{ ...data, ...listingBodyVariation }}
105
108
  data={listingBodyData}
@@ -0,0 +1,362 @@
1
+ /**
2
+ * Customizations
3
+ * - add customInlineFn to stateFromHTML call (line 179)
4
+ */
5
+ /**
6
+ * WysiwygWidget container.
7
+ * @module components/manage/WysiwygWidget/WysiwygWidget
8
+ */
9
+
10
+ import React, { Component } from 'react';
11
+ import ReactDOMServer from 'react-dom/server';
12
+ import PropTypes from 'prop-types';
13
+ import { connect, Provider } from 'react-redux';
14
+ import { compose } from 'redux';
15
+ import redraft from 'redraft';
16
+ import { Form, Label, TextArea } from 'semantic-ui-react';
17
+ import { map } from 'lodash';
18
+ import { defineMessages, injectIntl } from 'react-intl';
19
+ import configureStore from 'redux-mock-store';
20
+ import { MemoryRouter } from 'react-router-dom';
21
+ import config from '@plone/volto/registry';
22
+
23
+ import { FormFieldWrapper } from '@plone/volto/components';
24
+
25
+ import loadable from '@loadable/component';
26
+ import { injectLazyLibs } from '@plone/volto/helpers/Loadable/Loadable';
27
+
28
+ const Editor = loadable(() => import('draft-js-plugins-editor'));
29
+
30
+ const messages = defineMessages({
31
+ default: {
32
+ id: 'Default',
33
+ defaultMessage: 'Default',
34
+ },
35
+ idTitle: {
36
+ id: 'Short Name',
37
+ defaultMessage: 'Short Name',
38
+ },
39
+ idDescription: {
40
+ id: 'Used for programmatic access to the fieldset.',
41
+ defaultMessage: 'Used for programmatic access to the fieldset.',
42
+ },
43
+ title: {
44
+ id: 'Title',
45
+ defaultMessage: 'Title',
46
+ },
47
+ description: {
48
+ id: 'Description',
49
+ defaultMessage: 'Description',
50
+ },
51
+ required: {
52
+ id: 'Required',
53
+ defaultMessage: 'Required',
54
+ },
55
+ delete: {
56
+ id: 'Delete',
57
+ defaultMessage: 'Delete',
58
+ },
59
+ });
60
+
61
+ /**
62
+ * WysiwygWidget HTML richtext editing widget
63
+ *
64
+ * To use it, in schema properties, declare a field like:
65
+ *
66
+ * ```jsx
67
+ * {
68
+ * title: "Rich text",
69
+ * widget: 'richtext',
70
+ * }
71
+ * ```
72
+ *
73
+ */
74
+ class WysiwygWidgetComponent extends Component {
75
+ /**
76
+ * Property types.
77
+ * @property {Object} propTypes Property types.
78
+ * @static
79
+ */
80
+ static propTypes = {
81
+ /**
82
+ * Id of the field
83
+ */
84
+ id: PropTypes.string.isRequired,
85
+ /**
86
+ * Title of the field
87
+ */
88
+ title: PropTypes.string.isRequired,
89
+ /**
90
+ * Description of the field
91
+ */
92
+ description: PropTypes.string,
93
+ /**
94
+ * True if field is required
95
+ */
96
+ required: PropTypes.bool,
97
+ /**
98
+ * Value of the field
99
+ */
100
+ value: PropTypes.shape({
101
+ /**
102
+ * Content type of the value
103
+ */
104
+ 'content-type': PropTypes.string,
105
+ /**
106
+ * Data of the value
107
+ */
108
+ data: PropTypes.string,
109
+ /**
110
+ * Encoding of the value
111
+ */
112
+ encoding: PropTypes.string,
113
+ }),
114
+ /**
115
+ * Placeholder for the editor
116
+ */
117
+ placeholder: PropTypes.string,
118
+ /**
119
+ * List of error messages
120
+ */
121
+ error: PropTypes.arrayOf(PropTypes.string),
122
+ /**
123
+ * On change handler
124
+ */
125
+ onChange: PropTypes.func,
126
+ /**
127
+ * On delete handler
128
+ */
129
+ onDelete: PropTypes.func,
130
+ /**
131
+ * On edit handler
132
+ */
133
+ onEdit: PropTypes.func,
134
+ /**
135
+ * Wrapped form component
136
+ */
137
+ wrapped: PropTypes.bool,
138
+ };
139
+
140
+ /**
141
+ * Default properties
142
+ * @property {Object} defaultProps Default properties.
143
+ * @static
144
+ */
145
+ static defaultProps = {
146
+ description: null,
147
+ required: false,
148
+ value: {
149
+ 'content-type': 'text/html',
150
+ data: '',
151
+ encoding: 'utf8',
152
+ },
153
+ error: [],
154
+ onEdit: null,
155
+ onDelete: null,
156
+ onChange: null,
157
+ };
158
+
159
+ /**
160
+ * Constructor
161
+ * @method constructor
162
+ * @param {Object} props Component properties
163
+ * @constructs WysiwygWidget
164
+ */
165
+ constructor(props) {
166
+ super(props);
167
+
168
+ const { stateFromHTML } = props.draftJsImportHtml;
169
+ const { EditorState } = props.draftJs;
170
+ const createInlineToolbarPlugin = props.draftJsInlineToolbarPlugin.default;
171
+
172
+ this.draftConfig = config.settings.richtextEditorSettings(props);
173
+
174
+ if (!__SERVER__) {
175
+ let editorState;
176
+ if (props.value && props.value.data) {
177
+ const contentState = stateFromHTML(props.value.data, {
178
+ customBlockFn: this.draftConfig.FromHTMLCustomBlockFn,
179
+ customInlineFn: this.draftConfig.FromHTMLCustomInlineFn,
180
+ });
181
+ editorState = EditorState.createWithContent(contentState);
182
+ } else {
183
+ editorState = EditorState.createEmpty();
184
+ }
185
+
186
+ const inlineToolbarPlugin = createInlineToolbarPlugin({
187
+ structure: this.draftConfig.richTextEditorInlineToolbarButtons,
188
+ });
189
+
190
+ this.state = { editorState, inlineToolbarPlugin };
191
+ }
192
+
193
+ this.schema = {
194
+ fieldsets: [
195
+ {
196
+ id: 'default',
197
+ title: props.intl.formatMessage(messages.default),
198
+ fields: ['title', 'id', 'description', 'required'],
199
+ },
200
+ ],
201
+ properties: {
202
+ id: {
203
+ type: 'string',
204
+ title: props.intl.formatMessage(messages.idTitle),
205
+ description: props.intl.formatMessage(messages.idDescription),
206
+ },
207
+ title: {
208
+ type: 'string',
209
+ title: props.intl.formatMessage(messages.title),
210
+ },
211
+ description: {
212
+ type: 'string',
213
+ widget: 'textarea',
214
+ title: props.intl.formatMessage(messages.description),
215
+ },
216
+ required: {
217
+ type: 'boolean',
218
+ title: props.intl.formatMessage(messages.required),
219
+ },
220
+ },
221
+ required: ['id', 'title'],
222
+ };
223
+
224
+ this.onChange = this.onChange.bind(this);
225
+ }
226
+
227
+ /**
228
+ * Change handler
229
+ * @method onChange
230
+ * @param {object} editorState Editor state.
231
+ * @returns {undefined}
232
+ */
233
+ onChange(editorState) {
234
+ const { convertToRaw } = this.props.draftJs;
235
+ this.setState({ editorState });
236
+ const mockStore = configureStore();
237
+
238
+ this.props.onChange(this.props.id, {
239
+ 'content-type': this.props.value
240
+ ? this.props.value['content-type']
241
+ : 'text/html',
242
+ encoding: this.props.value ? this.props.value.encoding : 'utf8',
243
+ data: ReactDOMServer.renderToStaticMarkup(
244
+ <Provider
245
+ store={mockStore({
246
+ userSession: {
247
+ token: this.props.token,
248
+ },
249
+ })}
250
+ >
251
+ <MemoryRouter>
252
+ {redraft(
253
+ convertToRaw(editorState.getCurrentContent()),
254
+ config.settings.richtextViewSettings.ToHTMLRenderers,
255
+ config.settings.richtextViewSettings.ToHTMLOptions,
256
+ )}
257
+ </MemoryRouter>
258
+ </Provider>,
259
+ ),
260
+ });
261
+ }
262
+
263
+ /**
264
+ * Render method.
265
+ * @method render
266
+ * @returns {string} Markup for the component.
267
+ */
268
+ render() {
269
+ const {
270
+ id,
271
+ title,
272
+ description,
273
+ required,
274
+ value,
275
+ error,
276
+ fieldSet,
277
+ } = this.props;
278
+
279
+ if (__SERVER__) {
280
+ return (
281
+ <Form.Field
282
+ inline
283
+ required={required}
284
+ error={error.length > 0}
285
+ className={description ? 'help' : ''}
286
+ id={`${fieldSet || 'field'}-${id}`}
287
+ >
288
+ <div className="wrapper">
289
+ <label htmlFor={`field-${id}`}>{title}</label>
290
+ <TextArea id={id} name={id} value={value ? value.data : ''} />
291
+ {description && <p className="help">{description}</p>}
292
+ {map(error, (message) => (
293
+ <Label key={message} basic color="red" pointing>
294
+ {message}
295
+ </Label>
296
+ ))}
297
+ </div>
298
+ </Form.Field>
299
+ );
300
+ }
301
+ const { InlineToolbar } = this.state.inlineToolbarPlugin;
302
+
303
+ return (
304
+ <FormFieldWrapper {...this.props} className="wysiwyg">
305
+ <div style={{ boxSizing: 'initial' }}>
306
+ {this.props.onChange ? (
307
+ <>
308
+ <Editor
309
+ id={`field-${id}`}
310
+ readOnly={this.props.isDisabled}
311
+ onChange={this.onChange}
312
+ editorState={this.state.editorState}
313
+ plugins={[
314
+ this.state.inlineToolbarPlugin,
315
+ ...this.draftConfig.richTextEditorPlugins,
316
+ ]}
317
+ placeholder={this.props.placeholder}
318
+ blockRenderMap={this.draftConfig.extendedBlockRenderMap}
319
+ blockStyleFn={this.draftConfig.blockStyleFn}
320
+ customStyleMap={this.draftConfig.customStyleMap}
321
+ />
322
+ {this.props.onChange && <InlineToolbar />}
323
+ </>
324
+ ) : (
325
+ <div className="DraftEditor-root" />
326
+ )}
327
+ </div>
328
+ </FormFieldWrapper>
329
+ );
330
+ }
331
+ }
332
+
333
+ export const WysiwygWidget = compose(
334
+ injectIntl,
335
+ injectLazyLibs([
336
+ 'draftJs',
337
+ 'draftJsBlockBreakoutPlugin',
338
+ 'draftJsCreateBlockStyleButton',
339
+ 'draftJsCreateInlineStyleButton',
340
+ 'draftJsFilters',
341
+ 'draftJsImportHtml',
342
+ 'draftJsInlineToolbarPlugin',
343
+ 'draftJsLibIsSoftNewlineEvent',
344
+ 'immutableLib',
345
+ ]),
346
+ connect(
347
+ (state, props) => ({
348
+ token: state.userSession.token,
349
+ }),
350
+ {},
351
+ ),
352
+ )(WysiwygWidgetComponent);
353
+
354
+ const Preloader = (props) => {
355
+ const [loaded, setLoaded] = React.useState(false);
356
+ React.useEffect(() => {
357
+ Editor.load().then(() => setLoaded(true));
358
+ }, []);
359
+ return loaded ? <WysiwygWidget {...props} /> : null;
360
+ };
361
+
362
+ export default Preloader;
@@ -56,8 +56,8 @@
56
56
 
57
57
  // tablet
58
58
  .bandi-in-evidence-cards-wrapper {
59
- @media (min-width: #{map-get($grid-breakpoints, md)}) and (max-width: #{map-get($grid-breakpoints, xxl)}) {
60
- grid-template-columns: auto auto;
59
+ @media (min-width: #{map-get($grid-breakpoints, md)}) and (max-width: #{map-get($grid-breakpoints, xl)}) {
60
+ grid-template-columns: repeat(auto-fill, minmax(250px, 1fr));
61
61
  }
62
62
 
63
63
  @media (min-width: #{map-get($grid-breakpoints, md)}) and (max-width: #{map-get($grid-breakpoints, lg)}) {
@@ -151,15 +151,13 @@
151
151
  border-color: hsl(210deg, 17.6470588235%, 43.35%) !important;
152
152
  border-bottom: 1px solid;
153
153
  font-size: 1rem;
154
- transition:
155
- border-color 0.3s ease-in,
154
+ transition: border-color 0.3s ease-in,
156
155
  background-color 0.2s cubic-bezier(0, 1, 0, 1) 0.2s;
157
156
 
158
157
  &[aria-expanded='true'] {
159
158
  border-color: transparent !important;
160
159
  box-shadow: 0 1rem 2rem -0.25rem rgba(0, 0, 0, 0.15) !important;
161
- transition:
162
- background-color 0.2s cubic-bezier(0, 1, 0, 1),
160
+ transition: background-color 0.2s cubic-bezier(0, 1, 0, 1),
163
161
  border-color 0.05s cubic-bezier(1, 0, 1, 0);
164
162
  }
165
163
 
@@ -246,8 +244,16 @@
246
244
  }
247
245
  }
248
246
  }
247
+ .block.listing {
248
+ .bandi-in-evidence .bandi-in-evidence-cards-wrapper {
249
+ grid-template-columns: repeat(auto-fill, minmax(300px, 1fr));
250
+ @media (min-width: #{map-get($grid-breakpoints, md)}) and (max-width: #{map-get($grid-breakpoints, lg)}) {
251
+ display: block !important;
252
+ }
253
+ }
254
+ }
249
255
  }
250
256
 
251
- body.cms-ui .block.search.public-ui a {
257
+ .cms-ui .block.search .sideColumn .columnText .draftjs-buttons a {
252
258
  color: $primary-text;
253
259
  }
@@ -1,135 +0,0 @@
1
- /*
2
- CUSTOMIZATIONS
3
- - permit render if server, cannot use in history diff otherwise
4
- */
5
-
6
- import React, { useEffect, useState } from 'react';
7
- import { useSelector, useDispatch } from 'react-redux';
8
- import { useIntl, defineMessages } from 'react-intl';
9
- import { useLocation } from 'react-router-dom';
10
- import {
11
- displayBanner,
12
- updateGdprPrivacyConsent,
13
- } from 'volto-gdpr-privacy/actions';
14
-
15
- import {
16
- usePanelConfigAndPreferences,
17
- GDPRCookies,
18
- getLocaleConf,
19
- } from 'volto-gdpr-privacy/helpers';
20
-
21
- import 'volto-gdpr-privacy/components/ConditionalEmbed/conditional-embed.css';
22
-
23
- const messages = defineMessages({
24
- conditionalEmbedAcceptCookiesDefaultDescription: {
25
- id: 'volto-gdpr-privacy-conditional-embed-default-description',
26
- defaultMessage:
27
- 'Please, accept {cookie_type} cookies to view this content.',
28
- },
29
- conditionalEmbedAcceptCookiesAcceptMessage: {
30
- id: 'volto-gdpr-privacy-conditional-embed-accept-message',
31
- defaultMessage: '{enable_cookie_button}, or {manage_preferences_button}',
32
- },
33
- specificCookieLink: {
34
- id: 'volto-gdpr-privacy-conditional-embed-specific-cookie-link',
35
- defaultMessage: 'Enable {cookie_type} cookies',
36
- },
37
- genericCookieLink: {
38
- id: 'volto-gdpr-privacy-conditional-embed-generic-cookie-link',
39
- defaultMessage: 'manage your cookie preferences',
40
- },
41
- });
42
- const ConditionalEmbed = ({ code, url, children }) => {
43
- const intl = useIntl();
44
- const cookies = new GDPRCookies();
45
- const embed = code ?? url ?? '';
46
- const dispatch = useDispatch();
47
- const location = useLocation();
48
-
49
- const { defaultPreferences } = usePanelConfigAndPreferences(cookies);
50
- const profilingConfig = useSelector((state) =>
51
- state.gdprPrivacyConfig?.config?.profiling?.choices?.filter(
52
- (c) => c?.referenceUrls?.length > 0,
53
- ),
54
- );
55
- const gdprPreferences = useSelector(
56
- (state) => state.gdprPrivacyConsent.preferences ?? defaultPreferences,
57
- );
58
- const [urlReferenceConfig, setUrlReferenceConfig] = useState(null);
59
-
60
- useEffect(() => {
61
- if (profilingConfig && !urlReferenceConfig) {
62
- let conditionalConfig = profilingConfig.filter(
63
- (c) =>
64
- c.referenceUrls.filter((r) => embed?.indexOf(r) >= 0)?.length > 0,
65
- );
66
-
67
- setUrlReferenceConfig(conditionalConfig?.[0] ?? null);
68
- }
69
- // eslint-disable-next-line react-hooks/exhaustive-deps
70
- }, [profilingConfig, setUrlReferenceConfig, urlReferenceConfig, embed]);
71
-
72
- //return value
73
- let ret = <></>;
74
- let embedDisabled = true;
75
-
76
- embedDisabled =
77
- urlReferenceConfig != null &&
78
- !gdprPreferences[urlReferenceConfig.config_key];
79
- const isDiffView = location.pathname?.includes('/diff');
80
- if (__CLIENT__ && !gdprPreferences && !isDiffView) {
81
- return <></>;
82
- } else if (embedDisabled && !isDiffView) {
83
- //embed disabled
84
- const text = getLocaleConf(urlReferenceConfig.text, intl.locale);
85
- const key = urlReferenceConfig.config_key;
86
- ret = (
87
- <div className="volto-gdpr-embed-disabled">
88
- {text.conditional_embed_text ??
89
- intl.formatMessage(
90
- messages.conditionalEmbedAcceptCookiesDefaultDescription,
91
- { cookie_type: key },
92
- )}{' '}
93
- {intl.formatMessage(
94
- messages.conditionalEmbedAcceptCookiesAcceptMessage,
95
- {
96
- enable_cookie_button: (
97
- <button
98
- onClick={(e) => {
99
- e.preventDefault();
100
- cookies.set(key, true);
101
- dispatch(
102
- updateGdprPrivacyConsent({
103
- ...gdprPreferences,
104
- [key]: true,
105
- }),
106
- );
107
- }}
108
- >
109
- {intl.formatMessage(messages.specificCookieLink, {
110
- cookie_type: key,
111
- })}
112
- </button>
113
- ),
114
- manage_preferences_button: (
115
- <button
116
- onClick={(e) => {
117
- e.preventDefault();
118
- dispatch(displayBanner(true, true));
119
- }}
120
- >
121
- {intl.formatMessage(messages.genericCookieLink)}
122
- </button>
123
- ),
124
- },
125
- )}
126
- </div>
127
- );
128
- } else {
129
- ret = <>{children}</>;
130
- }
131
-
132
- return ret;
133
- };
134
-
135
- export default ConditionalEmbed;