templates/_snippets/carousel_destinations.html.twig line 1

Open in your IDE?
  1. {% set effectiveSectionSettings = showSectionSettings|default(true) ? sectionSettings|default({}) : {} %}
  2. {% set carouselDestinations = effectiveSectionSettings|merge(carouselDestinations) %}
  3. {% set isArrows = carouselDestinations.isArrows == true ? 1 : 0 %}
  4. {% set arrowsColor = carouselDestinations.arrowsColor|default('#fff') %}
  5. {% set filterColor = carouselDestinations.filterColor|default('#000') %}
  6. {% set filterColorOpacity = carouselDestinations.filterColorOpacity|default(0) %}
  7. {% set padding = carouselDestinations.padding|default(25) %}
  8. {% set paddingUnit = carouselDestinations.paddingUnit|default('px') %}
  9. {# Paramètres des vignettes #}
  10. {% set showThumbnails = carouselDestinations.showThumbnails|default(false) %}
  11. {% set height = carouselDestinations.height|default(400) %}
  12. {% set heightUnit = carouselDestinations.heightUnit|default('px') %}
  13. {% set bordersRadius = carouselDestinations.bordersRadius|default(0) ~ carouselDestinations.bordersRadiusUnit|default('px') %}
  14. {% set isSwitchSlideTime = carouselDestinations.isSwitchSlideTime|default(false) %}
  15. {% set switchSlideTime = (isSwitchSlideTime and carouselDestinations.switchSlideTime is not null and carouselDestinations.switchSlideTime != 0 ? carouselDestinations.switchSlideTime * 1000 : 5000) %}
  16. {% set sectionId = 'carousel-destinations-section-' ~ random() %}
  17. {% set carouselId = 'carousel-' ~ random() %}
  18. {% set sectionTitle = attribute(carouselDestinations, 'titleTextSection')|default('') %}
  19. {% set sectionPictogram = attribute(carouselDestinations, 'pictogramTitleSection')|default('') %}
  20. {% set sectionTitleTag = attribute(carouselDestinations, 'typeTitleSection')|default('h2') %}
  21. {% set firstDestBlock = carouselDestinations.blocks|default([])|first %}
  22. {% set destLcpPreloadHref = null %}
  23. {% if firstDestBlock %}
  24. {% set firstDestMedia = firstDestBlock.media|default(null) %}
  25. {% if firstDestMedia and firstDestMedia.id is defined and (firstDestMedia.url is not defined or firstDestMedia.thumbnails is not defined) %}
  26. {% set firstDestMedia = sulu_resolve_media(firstDestMedia.id, app.request.locale) %}
  27. {% endif %}
  28. {% if firstDestMedia and firstDestMedia.url is defined %}
  29. {% set du0 = firstDestMedia.url %}
  30. {% set dv0 = du0 matches '/\.mp4(\\?.*)?$/' %}
  31. {% if not dv0 %}
  32. {% set destLcpPreloadHref = sulu_media_url(firstDestMedia, '1200x') %}
  33. {% else %}
  34. {% set pdest0 = sulu_media_url(firstDestMedia, '1200x') %}
  35. {% if pdest0 and not (pdest0 matches '/\.(mp4|webm|ogg)(\\?.*)?$/i') %}
  36. {% set destLcpPreloadHref = pdest0 %}
  37. {% endif %}
  38. {% endif %}
  39. {% endif %}
  40. {% endif %}
  41. {% if true %}
  42. {% include '_snippets/sections/tags_section_settings.html.twig' with {
  43. 'content': carouselDestinations,
  44. 'id': sectionId,
  45. } %}
  46. <section id="{{ sectionId }}" class="carousel-destinations">
  47. {% if sectionTitle is not empty or sectionPictogram is not empty %}
  48. <div class="carousel-destinations-head">
  49. <{{ sectionTitleTag }}>
  50. {% if sectionPictogram is not empty %}
  51. <div class="icon">{{ getLucidIcon(sectionPictogram) }}</div>
  52. {% endif %}
  53. {{ sectionTitle|raw }}
  54. </{{ sectionTitleTag }}>
  55. </div>
  56. {% endif %}
  57. <div class="carousel-wrapper"
  58. data-type="contentOnMedia"
  59. id="{{ carouselId }}"
  60. data-carousel-id="{{ carouselId }}"
  61. data-carousel-options='{{ {
  62. "showDots": carouselDestinations.showDots|default(false),
  63. "showThumbnails": showThumbnails,
  64. "isAutoSlide": isSwitchSlideTime,
  65. "animation": {
  66. "contentDuration": 0.5,
  67. "contentDelay": 0.2,
  68. "mediaDuration": 0.55,
  69. "mediaDelay": 0
  70. }
  71. }|json_encode|raw }}'
  72. style="--switch-slide-time: {{ switchSlideTime }}ms;">
  73. {% if destLcpPreloadHref %}
  74. <link rel="preload" as="image" href="{{ destLcpPreloadHref }}" fetchpriority="high">
  75. {% endif %}
  76. <div class="carousel-container">
  77. <div class="carousel" data-observed>
  78. {% for slide in carouselDestinations.blocks %}
  79. {% set slideMedia = slide.media|default(null) %}
  80. {% if slideMedia and slideMedia.id is defined and (slideMedia.url is not defined or slideMedia.thumbnails is not defined) %}
  81. {% set slideMedia = sulu_resolve_media(slideMedia.id, app.request.locale) %}
  82. {% endif %}
  83. {# Définir le nom de la destination au début du slide #}
  84. {% if slide.destinationCustomName is not empty %}
  85. {% set destinationName = slide.destinationCustomName %}
  86. {% elseif slide.destinationSelector is not empty %}
  87. {% set destinationData = getDestinationById(slide.destinationSelector) %}
  88. {% set destinationName = destinationData.name|default('') %}
  89. {% else %}
  90. {% set destinationName = '' %}
  91. {% endif %}
  92. {% if slide.isColorGradient or (slideMedia and slideMedia.url is defined) %}
  93. {% if slideMedia and slideMedia.url is defined %}
  94. {% set mediaUrl = sulu_media_original_url(slideMedia) %}
  95. {% set mediaPoster = sulu_media_url(slideMedia, '1200x') %}
  96. {% set mediaThumb800 = sulu_media_url(slideMedia, '800x') %}
  97. {% set mediaThumb1200 = sulu_media_url(slideMedia, '1200x') %}
  98. {% set mediaThumb1600 = sulu_media_url(slideMedia, '1600x') %}
  99. {% set isVideo = slideMedia.isVideo is defined ? slideMedia.isVideo : (mediaUrl matches '/\.mp4(\\?.*)?$/' or mediaUrl matches '/\.webm(\\?.*)?$/' or mediaUrl matches '/\.ogg(\\?.*)?$/') %}
  100. {% else %}
  101. {% set mediaUrl = '' %}
  102. {% set mediaPoster = '' %}
  103. {% set mediaThumb800 = null %}
  104. {% set mediaThumb1200 = null %}
  105. {% set mediaThumb1600 = null %}
  106. {% set isVideo = false %}
  107. {% endif %}
  108. <div class="carousel-slide {% if isArrows == 1 %}has-arrows{% endif %}">
  109. {# Media #}
  110. {% if slide.isColorGradient %}
  111. {% set gradientDirections = {
  112. 'leftRight': 'to right',
  113. 'rightLeft': 'to left',
  114. 'topBottom': 'to bottom',
  115. 'bottomTop': 'to top',
  116. 'topLeftBottomRight': 'to bottom right',
  117. 'bottomLeftTopRight': 'to top right',
  118. 'topRightBottomLeft': 'to bottom left',
  119. 'bottomRightTopLeft': 'to top left'
  120. } %}
  121. {% set gradientDirection = gradientDirections[slide.gradientOrientation|default('leftRight')] %}
  122. <div class="carousel-color-gradient carousel-media"
  123. style="background: linear-gradient({{ gradientDirection }}, {{ slide.color1|default('#000') }}, {{ slide.color2|default('#fff') }});">
  124. </div>
  125. {% else %}
  126. {% if isVideo %}
  127. <video class="carousel-media"
  128. autoplay muted loop playsinline
  129. preload="metadata"
  130. poster="{{ mediaPoster }}"
  131. {% if loop.first %}fetchpriority="high"{% endif %}>
  132. <source src="{{ mediaUrl }}" type="video/mp4">
  133. <p>{{ 'carousel.destination.video_not_supported'|trans }}</p>
  134. </video>
  135. {% else %}
  136. {% set isDestLcpImage = loop.first and mediaPoster is not empty %}
  137. <img class="carousel-media{{ isDestLcpImage ? ' carousel-media--lcp' : '' }}"
  138. src="{{ mediaPoster }}"
  139. {% if mediaThumb800 and mediaThumb1200 and mediaThumb800 != mediaThumb1200 %}
  140. srcset="{{ mediaThumb800 }} 800w{% if mediaThumb1200 %}, {{ mediaThumb1200 }} 1200w{% endif %}{% if mediaThumb1600 %}, {{ mediaThumb1600 }} 1600w{% endif %}"
  141. sizes="100vw"
  142. {% elseif mediaThumb800 %}
  143. srcset="{{ mediaThumb800 }} 800w"
  144. sizes="100vw"
  145. {% endif %}
  146. alt="{{ destinationName|default('')|e('html_attr') }}"
  147. decoding="async"
  148. {% if isDestLcpImage %}
  149. fetchpriority="high"
  150. {% else %}
  151. loading="lazy" fetchpriority="low"
  152. {% endif %}>
  153. {% endif %}
  154. {% endif %}
  155. {% if carouselDestinations.filterColor and not slide.isColorGradient %}
  156. <div class="carousel-overlay"
  157. style="background-color: {{ filterColor }};
  158. opacity: {{ filterColorOpacity ?? 0.4 }};">
  159. </div>
  160. {% endif %}
  161. <div class="carousel-content">
  162. <div class="line">
  163. {# Affichage du nom de la destination dans le contenu #}
  164. {% if destinationName is not empty %}
  165. <div class="content-destination-label">
  166. <svg width="12" height="12" viewBox="0 0 24 24" fill="currentColor">
  167. <path d="M12 2C8.13 2 5 5.13 5 9c0 5.25 7 13 7 13s7-7.75 7-13c0-3.87-3.13-7-7-7zm0 9.5c-1.38 0-2.5-1.12-2.5-2.5s1.12-2.5 2.5-2.5 2.5 1.12 2.5 2.5-1.12 2.5-2.5 2.5z"/>
  168. </svg>
  169. <span>{{ destinationName }}</span>
  170. </div>
  171. {% endif %}
  172. {% for content in slide.contents %}
  173. {% if content.type == 'text' %}
  174. <div class="carousel-text">{{ content.contentText|raw }}</div>
  175. {% elseif content.type == 'button' %}
  176. <div class="carousel-button-wrapper text-{{ content.alignmentButton }}">
  177. {% if content.isInternalLink %}
  178. <sulu-link href="#"
  179. data-id="{{ content.internalLink.id }}"
  180. data-type="{{ content.internalLink._type }}"
  181. class="carousel-button">
  182. {{ content.textButton }} {{ getLucidIcon('arrow-right') }}
  183. </sulu-link>
  184. {% else %}
  185. <a href="{{ content.externalLink }}"
  186. class="carousel-button"
  187. target="_blank"
  188. rel="noopener">
  189. {{ content.textButton }} {{ getLucidIcon('arrow-right') }}
  190. </a>
  191. {% endif %}
  192. </div>
  193. {% elseif content.type == 'image' %}
  194. <div class="carousel-image">
  195. {% set contentImage = content.contentImage|default(null) %}
  196. {% set imageUrl = sulu_media_url(contentImage, '1200x') %}
  197. <img src="{{ imageUrl }}"
  198. alt="{{ content.altImage|default(contentImage ? contentImage.title|default('') : '') }}"
  199. loading="lazy"
  200. {% if content.widthImage is defined and content.widthImage is not null %}
  201. style="width: {{ content.widthImage ~ (content.widthImageUnit)|default('px') }};"
  202. {% endif %}>
  203. </div>
  204. {% endif %}
  205. {% endfor %}
  206. {% if slide.advicedDuration is defined or slide.advicedPeriod is defined %}
  207. <div class="content-adviced">
  208. {% if slide.advicedDuration is defined and slide.advicedDuration is not empty %}
  209. <div class="content-adviced-duration">
  210. {{ getLucidIcon('clock') }}
  211. {{ 'carousel.destination.recommended_duration'|trans }} : {{ slide.advicedDuration }}
  212. </div>
  213. {% endif %}
  214. {% if slide.advicedPeriod is defined and slide.advicedPeriod is not empty %}
  215. <div class="content-adviced-period">
  216. {{ getLucidIcon('calendar') }}
  217. {{ 'carousel.destination.recommended_period'|trans }} : {{ slide.advicedPeriod }}
  218. </div>
  219. {% endif %}
  220. </div>
  221. {% endif %}
  222. {% if slide.tags is defined and slide.tags is not empty %}
  223. <div class="content-tags">
  224. {% for tag in slide.tags %}
  225. <div class="content-tag">{{ tag.tag }}</div>
  226. {% endfor %}
  227. </div>
  228. {% endif %}
  229. <div class="content-dynamic-button">
  230. <a href="http://cms.croisiland.localhost/fr/nouveau-moteur-de-recherche?destination={{ slide.destinationSelector }}" class="dynamic-button">{{ carouselDestinations.dynamicButtonText|default('carousel.destination.discover'|trans) }}
  231. {% if slide.isCallPriceDisplayed and slide.destinationSelector is not empty %}
  232. {% set destinationData = getDestinationById(slide.destinationSelector) %}
  233. {# {% set destinationPrice = getDestinationCompaniesBestPrice(destinationData) %} #}
  234. {% set destinationPrice = null %}
  235. {% if destinationPrice and destinationPrice.amount is defined %}
  236. <span class="price">{{ 'common.from'|trans|lower }} {{ destinationPrice.amount|number_format(0, ',', ' ') }}€</span>
  237. {% else %}
  238. <span class="price">{{ 'common.from'|trans|lower }} 1 400€</span>
  239. {% endif %}
  240. {% endif %} {{ getLucidIcon('arrow-right') }}</a>
  241. </div>
  242. </div>
  243. </div>
  244. </div>
  245. {% endif %}
  246. {% endfor %}
  247. </div>
  248. </div>
  249. {# Dots #}
  250. {% if carouselDestinations.showDots|default(false) %}
  251. <div class="carousel-dots">
  252. {% for slide in carouselDestinations.blocks %}
  253. <span class="dot {% if loop.first %}active{% endif %}"
  254. data-index="{{ loop.index0 }}"
  255. data-carousel-id="{{ carouselId }}"></span>
  256. {% endfor %}
  257. </div>
  258. {% endif %}
  259. {# Vignettes #}
  260. {% if showThumbnails %}
  261. {% set inactiveFilter = carouselDestinations.thumbnailInactiveFilter|default('grayscale') %}
  262. <div class="carousel-thumbnails" data-carousel-id="{{ carouselId }}">
  263. {% for slide in carouselDestinations.blocks %}
  264. {% set slideMedia = slide.media|default(null) %}
  265. {% if slideMedia and slideMedia.id is defined and (slideMedia.url is not defined or slideMedia.thumbnails is not defined) %}
  266. {% set slideMedia = sulu_resolve_media(slideMedia.id, app.request.locale) %}
  267. {% endif %}
  268. {% if slideMedia and slideMedia.url is defined %}
  269. {% set mediaUrl = sulu_media_original_url(slideMedia) %}
  270. {% set destinationId = slide.destinationSelector|default(null) %}
  271. {% set destination = getDestinationById(destinationId) %}
  272. {% set isVideo = mediaUrl matches '/\.mp4(\\?.*)?$/' %}
  273. {# Définir le nom de la destination pour cette vignette #}
  274. {% if slide.destinationCustomName is not empty %}
  275. {% set destinationName = slide.destinationCustomName %}
  276. {% elseif slide.destinationSelector is not empty %}
  277. {% set destinationData = getDestinationById(slide.destinationSelector) %}
  278. {% set destinationName = destinationData.name|default('') %}
  279. {% else %}
  280. {% set destinationName = '' %}
  281. {% endif %}
  282. {% if isVideo %}
  283. {# Pour les vidéos, utiliser un canvas pour capturer le premier frame #}
  284. <div class="thumbnail {% if loop.first %}active{% endif %} filter-{{ inactiveFilter }}"
  285. data-index="{{ loop.index0 }}"
  286. data-carousel-id="{{ carouselId }}"
  287. data-video-url="{{ mediaUrl }}">
  288. <canvas class="video-thumbnail-canvas" width="{{ carouselDestinations.thumbnailWidth|default(120) }}" height="{{ carouselDestinations.thumbnailHeight|default(80) }}"></canvas>
  289. <div class="video-play-icon">▶</div>
  290. {% else %}
  291. {# Pour les images, utiliser les thumbnails normaux #}
  292. {% set mediaPoster = sulu_media_url(slideMedia, '200x') %}
  293. <div class="thumbnail {% if loop.first %}active{% endif %} filter-{{ inactiveFilter }}"
  294. data-index="{{ loop.index0 }}"
  295. data-carousel-id="{{ carouselId }}">
  296. <img src="{{ mediaPoster }}"
  297. alt="{{ slideMedia.title|default('Thumbnail ' ~ loop.index) }}"
  298. loading="lazy">
  299. {% endif %}
  300. {# Afficher le nom de la destination #}
  301. {% if destinationName is not empty %}
  302. <div class="thumbnail-label">
  303. {{ getLucidIcon('map-pin', {width: '12', height: '12'}) }}
  304. <span>{{ destinationName }}</span>
  305. </div>
  306. {% endif %}
  307. </div>
  308. {% endif %}
  309. {% endfor %}
  310. </div>
  311. {% endif %}
  312. {# Flèches #}
  313. {% if isArrows == 1 %}
  314. <div class="carousel-arrows">
  315. <button class="carousel-arrow left" aria-label="Précédent" data-carousel-id="{{ carouselId }}">{{ getLucidIcon('chevron-left') }}</button>
  316. <button class="carousel-arrow right" aria-label="Suivant" data-carousel-id="{{ carouselId }}">{{ getLucidIcon('chevron-right') }}</button>
  317. </div>
  318. {% endif %}
  319. </div>
  320. </section>
  321. {% endif %}
  322. {# Le JavaScript du carousel est géré par snippets/hero-section.js (même système que hero_section) #}
  323. <style>
  324. #{{ carouselId }} {
  325. /* Général */
  326. --borders-radius: {{ carouselDestinations.bordersRadius|default(0) ~ carouselDestinations.bordersRadiusUnit|default('px') }};
  327. --text-width: {{ carouselDestinations.textWidth|default(100) ~ carouselDestinations.textWidthUnit|default('%') }};
  328. --height: {{ carouselDestinations.height|default(400) ~ carouselDestinations.heightUnit|default('px') }};
  329. --gap-elements: {{ carouselDestinations.gapElements|default(12) ~ carouselDestinations.gapElementsUnit|default('px') }};
  330. --carousel-padding: {{ padding ~ paddingUnit }};
  331. /* Flèches */
  332. --arrows-color: {{ arrowsColor }};
  333. --arrow-dimensions: {{ carouselDestinations.arrowDimensions|default(20) ~ carouselDestinations.arrowDimensionsUnit|default('px') }};
  334. /* Vignettes */
  335. --thumbnails-gap: {{ carouselDestinations.thumbnailGap|default(10) }}px;
  336. --thumbnails-width: {{ carouselDestinations.thumbnailWidth|default(120) }}px;
  337. --thumbnails-height: {{ carouselDestinations.thumbnailHeight|default(80) }}px;
  338. --thumbnails-border-radius: {{ carouselDestinations.thumbnailBorderRadius|default(8) }}px;
  339. --thumbnail-active-border: {{ carouselDestinations.thumbnailActiveBorderWidth|default(3) ~ 'px solid ' ~ carouselDestinations.thumbnailActiveBorderColor|default('#8B5CF6') }};
  340. --thumbnail-border: {{ carouselDestinations.thumbnailActiveBorderWidth|default(3) ~ 'px solid transparent' }};
  341. /* Vignettes responsive */
  342. --responsive-thumbnails-gap: {{ carouselDestinations.thumbnailGap|default(10) * 0.8 }}px;
  343. --responsive-thumbnails-width: {{ carouselDestinations.thumbnailWidth|default(120) * 0.9 }}px;
  344. --responsive-thumbnails-height: {{ carouselDestinations.thumbnailHeight|default(80) * 0.9 }}px;
  345. /* Filtres des vignettes inactives */
  346. --thumbnail-filter-intensity: {{ carouselDestinations.thumbnailInactiveFilterIntensity|default(50) }};
  347. --thumbnail-overlay-color: {{ carouselDestinations.thumbnailInactiveOverlayColor|default('#000000') }};
  348. /* Elements textuels des vignettes */
  349. --thumbnail-text-color: {{ carouselDestinations.thumbnailTextColor|default('#fff') }};
  350. --thumbnail-text-size: {{ carouselDestinations.thumbnailTextSize|default(12) ~ carouselDestinations.thumbnailTextSizeUnit|default('px') }};
  351. --thumbnail-text-weight: {{ carouselDestinations.thumbnailTextWeight|default(600) }};
  352. --thumbnail-text-align: {{ carouselDestinations.thumbnailTextAlign|default('left') }};
  353. --thumbnail-text-border-radius: {{ carouselDestinations.thumbnailTextBorderRadius|default(8) ~ carouselDestinations.thumbnailTextBorderRadiusUnit|default('px') }};
  354. /* Fond des étiquettes via ::after */
  355. --thumbnail-label-background: {{ carouselDestinations.thumbnailLabelBackground|default(carouselDestinations.thumbnailTextBackground|default('#000000')) }};
  356. --thumbnail-label-background-opacity: {{ carouselDestinations.thumbnailLabelBackgroundOpacity|default(carouselDestinations.thumbnailTextBackgroundOpacity|default(70)) }};
  357. --thumbnail-label-border-radius: {{ carouselDestinations.thumbnailTextBorderRadius|default(20) ~ carouselDestinations.thumbnailTextBorderRadiusUnit|default('px') }};
  358. /* Dots */
  359. --dots-color-1: {{ carouselDestinations.dotColor1|default('#004461') }};
  360. --dots-color-2: {{ carouselDestinations.dotColor2|default('#00AAD7') }};
  361. /* Bouton */
  362. --main-color-button: {{ carouselDestinations.mainColorButton|default('#004461') }};
  363. --secondary-color-button: {{ carouselDestinations.secondaryColorButton|default('#fff') }};
  364. --borders-radius-button: {{ carouselDestinations.bordersRadiusButton|default(8) ~ carouselDestinations.bordersRadiusButtonUnit|default('px') }};
  365. --padding-button: {{ carouselDestinations.paddingSizeTopBottomButton|default(4) ~ carouselDestinations.paddingButtonUnit|default('px') ~ ' ' ~ carouselDestinations.paddingSizeLeftRightButton|default(4) ~ carouselDestinations.paddingButtonUnit|default('px') }};
  366. /* Bouton dynamique */
  367. --dynamic-button-text-color: {{ carouselDestinations.dynamicButtonTextColor|default('#fff') }};
  368. --dynamic-button-background: {{ carouselDestinations.dynamicButtonBackground|default('#004461') }};
  369. --dynamic-button-price-color: {{ carouselDestinations.dynamicButtonPriceColor|default('#000') }};
  370. --dynamic-button-border-radius: {{ carouselDestinations.dynamicButtonBorderRadius|default(8) ~ carouselDestinations.dynamicButtonBorderRadiusUnit|default('px') }};
  371. --dynamic-button-padding: {{ carouselDestinations.dynamicButtonPaddingTopBottom|default(4) ~ carouselDestinations.dynamicButtonPaddingTopBottomUnit|default('px') ~ ' ' ~ carouselDestinations.dynamicButtonPaddingRightLeft|default(4) ~ carouselDestinations.dynamicButtonPaddingRightLeftUnit|default('px') }};
  372. --dynamic-button-border: {{ carouselDestinations.dynamicButtonBorderSize|default(1) ~ carouselDestinations.dynamicButtonBorderSizeUnit|default('px') ~ ' solid ' ~ carouselDestinations.dynamicButtonBorderColor|default('#fff') }};
  373. /* Tags */
  374. --tags-color: {{ carouselDestinations.tagsColor|default('#000') }};
  375. --tags-font-weight: {{ carouselDestinations.tagsFontWeight|default(600) }};
  376. --tags-text-align: {{ carouselDestinations.tagsTextAlign|default('left') }};
  377. --tags-padding: {{ carouselDestinations.tagsPaddingTopBottom|default(3) ~ carouselDestinations.tagsPaddingTopBottomUnit|default('px') }} {{ carouselDestinations.tagsPaddingRightLeft|default(6) ~ carouselDestinations.tagsPaddingRightLeftUnit|default('px') }};
  378. --tags-border-radius: {{ carouselDestinations.tagsBorderRadius|default(12) ~ carouselDestinations.tagsBorderRadiusUnit|default('px') }};
  379. --tags-font-size: {{ carouselDestinations.tagsFontSize|default(10) ~ carouselDestinations.tagsFontSizeUnit|default('px') }};
  380. --tags-background-color: {{ carouselDestinations.tagsBackgroundColor|default('rgba(217, 217, 217, 0.20)') }};
  381. }
  382. </style>