PluginProbe
VikBooking Hotel Booking Engine & PMS / 1.8.15
VikBooking Hotel Booking Engine & PMS v1.8.15
1.8.15 1.8.14 1.8.13 1.8.12 1.8.11 1.8.10 1.8.9 1.8.6 1.8.7 1.8.8 trunk 1.6.0 1.6.1 1.6.2 1.6.3 1.6.4 1.6.5 1.6.6 1.6.7 1.6.8 1.6.9 1.7.0 1.7.1 1.7.2 1.7.3 All 36 releases
vikbooking / site / views / search / tmpl / default_classic.php

default_classic.php in VikBooking Hotel Booking Engine & PMS 1.8.15, at site/views/search/tmpl/default_classic.php

708 lines 26.2 KB
No matching file
Up and down to move Enter to open Esc to close
Raw Download Zip
1 <?php
2 /**
3 * @package VikBooking
4 * @subpackage com_vikbooking
5 * @author Alessio Gaggii - e4j - Extensionsforjoomla.com
6 * @copyright Copyright (C) 2018 e4j - Extensionsforjoomla.com. All rights reserved.
7 * @license GNU General Public License version 2 or later; see LICENSE
8 * @link https://vikwp.com
9 */
10
11 defined('ABSPATH') or die('No script kiddies please!');
12
13 $app = JFactory::getApplication();
14 $vat_included = VikBooking::ivaInclusa();
15 $tax_summary = !$vat_included && VikBooking::showTaxOnSummaryOnly() ? true : false;
16
17 $currencysymb = VikBooking::getCurrencySymb();
18 $pitemid = VikRequest::getInt('Itemid', '', 'request');
19
20 // whether to use links to room details
21 $link_to_details = VBOFactory::getConfig()->getBool('search_link_roomdetails', false);
22
23 // search map
24 $is_search_map_enabled = VikBooking::interactiveMapEnabled();
25
26 /**
27 * Search results (classic layout) style: list or grid.
28 *
29 * @since 1.18.3 (J) - 1.8.3 (WP)
30 */
31 $layouts = [
32 'list' => [
33 'title' => JText::translate('VBO_LIST'),
34 'icon' => 'th-list',
35 ],
36 'grid' => [
37 'title' => JText::translate('VBO_GRID'),
38 'icon' => 'table',
39 'class' => 'vblistcontainer-grid',
40 ],
41 ];
42
43 // default style (name)
44 $default_style = $is_search_map_enabled ? 'grid' : 'list';
45
46 ?>
47 <div class="vbo-results-filtering">
48 <?php
49 if (VBOFactory::getConfig()->getBool('search_filters')) {
50 // count the active filters
51 $current_filters = (array) $app->input->get('filters', [], 'array');
52 $active_filters = 0;
53 foreach ($current_filters as $filter_type => $filter_data) {
54 if (empty($filter_data)) {
55 continue;
56 }
57 if (is_array($filter_data)) {
58 if (range(0, count($filter_data) - 1) === array_keys($filter_data)) {
59 // count non-empty values for this linear array
60 $active_filters += count(array_filter($filter_data));
61 } else {
62 // associative array filter will count as a single filter
63 $is_active_filter = true;
64 if ($filter_type === 'price' && !empty($filter_data['min']) && !empty($filter_data['max'])) {
65 // ensure the value is not the default range of rates pool or even greater
66 if (!$this->rates_pool || (floor((float) $filter_data['min']) == floor(min($this->rates_pool)) && ceil((float) $filter_data['max']) == ceil(max($this->rates_pool)))) {
67 // do not count the filter as applied
68 $is_active_filter = false;
69 } elseif ($this->rates_pool && $filter_data['min'] <= min($this->rates_pool) && $filter_data['max'] >= max($this->rates_pool)) {
70 // do not count the filter as applied
71 $is_active_filter = false;
72 }
73 }
74 if ($is_active_filter) {
75 $active_filters++;
76 }
77 }
78 } else {
79 // non empty value will count as a single filter
80 $active_filters++;
81 }
82 }
83 // normalize active filters counter, if needed
84 if ($active_filters > 99) {
85 // convert it to a string
86 $active_filters = '99+';
87 }
88 ?>
89 <div class="vbo-results-filters-wrap">
90 <button type="button" class="vbo-results-filters-toggle" data-counter="<?php echo $active_filters ?: ''; ?>"><?php VikBookingIcons::e('sliders-h'); ?> <?php echo JText::translate('VBO_FILTERS'); ?></button>
91 <div class="vbo-results-filters-form-helper" style="display: none;">
92 <?php echo $this->loadTemplate('filters'); ?>
93 </div>
94 </div>
95 <?php
96 }
97 ?>
98 <div class="vbo-results-style-wrap">
99 <div class="vbo-results-style">
100 <?php
101 foreach ($layouts as $layout_type => $layout_data) {
102 ?>
103 <span class="vbo-results-style-option<?php echo $layout_type == $default_style ? ' vbo-results-style-option-active' : ''; ?>" data-type="<?php echo $layout_type; ?>" data-toggle="<?php echo $layout_data['class'] ?? ''; ?>"><?php VikBookingIcons::e($layout_data['icon']); ?> <?php echo $layout_data['title'] ?? ''; ?></span>
104 <?php
105 }
106 ?>
107 </div>
108 </div>
109 </div>
110 <div class="vbo-results-content<?php echo !$is_search_map_enabled ? ' vbo-results-without-geomap' : ''; ?>">
111 <?php
112 /**
113 * Interactive map booking. Only for classic booking layout.
114 *
115 * @since 1.14 (J) - 1.4.0 (WP)
116 */
117 if ($is_search_map_enabled) {
118 echo $this->loadTemplate('interactive_map');
119 }
120 ?>
121 <div class="vbo-searchresults-classic-wrap<?php echo !empty($layouts[$default_style]['class']) ? ' ' . $layouts[$default_style]['class'] : ''; ?>">
122 <?php
123 $writeroomnum = [];
124 foreach ($this->res as $indroom => $rooms) {
125 if ($this->roomsnum > 1 && !in_array($indroom, $writeroomnum) && $rooms) {
126 $writeroomnum[] = $indroom;
127 ?>
128 <div class="vbo-searchresults-step-content">
129 <div id="vbpositionroom<?php echo $indroom; ?>"></div>
130 <div class="vbsearchproominfo">
131 <span class="vbsearchnroom"><?php echo JText::translate('VBSEARCHROOMNUM'); ?> <?php echo $indroom; ?></span>
132 <span class="vbsearchroomparty"><?php VikBookingIcons::e('users', 'vbo-pref-color-text'); ?> <?php echo $this->arrpeople[$indroom]['adults']; ?> <?php echo ($this->arrpeople[$indroom]['adults'] == 1 ? JText::translate('VBSEARCHRESADULT') : JText::translate('VBSEARCHRESADULTS')); ?> <?php echo ($this->showchildren && $this->arrpeople[$indroom]['children'] > 0 ? ", ".$this->arrpeople[$indroom]['children']." ".($this->arrpeople[$indroom]['children'] == 1 ? JText::translate('VBSEARCHRESCHILD') : JText::translate('VBSEARCHRESCHILDREN')) : ""); ?></span>
133 </div>
134 </div>
135 <?php
136 }
137 ?>
138 <div class="vbo-searchresults-party-content">
139 <?php
140 foreach ($rooms as $room) {
141 // set a different class to the main div in case the rooms usage is for less people than the capacity
142 $rdiffusage = array_key_exists('diffusage', $room[0]) && $this->arrpeople[$indroom]['adults'] < $room[0]['toadult'] ? true : false;
143 $has_promotion = array_key_exists('promotion', $room[0]) ? true : false;
144 $maindivclass = $rdiffusage ? "room_resultdiffusage" : "room_result";
145 $carats = VikBooking::getRoomCaratOriz($room[0]['idcarat'], $this->vbo_tn);
146
147 // prepare CMS contents depending on platform
148 $room[0] = VBORoomHelper::getInstance()->prepareCMSContents($room[0], ['smalldesc']);
149
150 $saylastavail = false;
151 $showlastavail = (int)VikBooking::getRoomParam('lastavail', $room[0]['params']);
152 if (!empty($showlastavail) && $showlastavail > 0) {
153 if ($room[0]['unitsavail'] <= $showlastavail) {
154 $saylastavail = true;
155 }
156 }
157 $searchdet_link = JRoute::rewrite('index.php?option=com_vikbooking&view=searchdetails&roomid='.$room[0]['idroom'].'&checkin='.$this->checkin.'&checkout='.$this->checkout.'&adults='.$this->arrpeople[$indroom]['adults'].'&children='.$this->arrpeople[$indroom]['children'].'&tmpl=component'.(!empty($pitemid) ? '&Itemid='.$pitemid : ''));
158
159 /**
160 * Build image gallery, if available
161 *
162 * @since 1.14 (J) - 1.4.0 (WP)
163 */
164 $gallery_data = [];
165 if (!empty($room[0]['moreimgs'])) {
166 $moreimages = explode(';;', $room[0]['moreimgs']);
167 foreach (array_filter($moreimages) as $mimg) {
168 // push thumb URL
169 $gallery_data[] = $mimg;
170 }
171 }
172
173 // build listing details URI components
174 $listing_uri_data = [
175 'option' => 'com_vikbooking',
176 'view' => 'roomdetails',
177 'roomid' => $room[0]['idroom'],
178 'start_date' => date('Y-m-d', $this->checkin),
179 'end_date' => date('Y-m-d', $this->checkout),
180 'num_adults' => $this->arrpeople[$indroom]['adults'],
181 'num_children' => $this->arrpeople[$indroom]['children'],
182 'Itemid' => ($pitemid ?: null),
183 ];
184 // route proper URI
185 $listing_page_uri = JRoute::rewrite('index.php?' . http_build_query($listing_uri_data), false);
186
187 // use link to listing details page or plain text
188 $main_listing_elem = $room[0]['name'];
189 if ($link_to_details) {
190 // embed HTML link
191 $main_listing_elem = '<a class="vbo-search-results-listing-link" href="' . $listing_page_uri . '" target="_blank">' . $room[0]['name'] . '</a>';
192 }
193
194 // cut off long descriptions by eventually adding a "read more" link
195 $descr_length = strlen((string) $room[0]['smalldesc']);
196 $visible_descr = $room[0]['smalldesc'];
197 $hidden_descr = '';
198 if ($descr_length > 200 && ($descr_length - 200) > 100) {
199 $visible_descr = strip_tags($visible_descr);
200 $hidden_descr = '1';
201 if (function_exists('mb_substr')) {
202 $visible_descr = mb_substr($visible_descr, 0, 200, 'UTF-8');
203 } else {
204 $visible_descr = substr($visible_descr, 0, 200);
205 }
206 $visible_descr .= '...';
207 }
208 ?>
209 <div class="room_item <?php echo $maindivclass; ?><?php echo $has_promotion === true ? ' vbo-promotion-price' : ''; ?>" id="vbcontainer<?php echo $indroom.'_'.$room[0]['idroom']; ?>">
210 <div class="vblistroomblock">
211 <div class="vbimglistdiv">
212 <div class="vbo-dots-slider-selector">
213 <a href="<?php echo $searchdet_link; ?>" class="vbmodalframe" target="_blank" data-gallery="<?php echo implode('|', $gallery_data); ?>">
214 <?php
215 if (!empty($room[0]['img']) && is_file(VBO_SITE_PATH . DIRECTORY_SEPARATOR . 'resources' . DIRECTORY_SEPARATOR . 'uploads' . DIRECTORY_SEPARATOR . $room[0]['img'])) {
216 ?>
217 <img class="vblistimg" alt="<?php echo htmlspecialchars($room[0]['name']); ?>" id="vbroomimg<?php echo $indroom.'_'.$room[0]['idroom']; ?>" src="<?php echo VBO_SITE_URI; ?>resources/uploads/<?php echo $room[0]['img']; ?>"/>
218 <?php
219 }
220 ?>
221 </a>
222 </div>
223 <div class="vbmodalrdetails">
224 <a href="<?php echo $searchdet_link; ?>" class="vbmodalframe" target="_blank"><?php VikBookingIcons::e('plus'); ?></a>
225 </div>
226 </div>
227 <div class="vbo-info-room">
228 <div class="vbdescrlistdiv">
229 <h4 class="vbrowcname" id="vbroomname<?php echo $indroom.'_'.$room[0]['idroom']; ?>"><?php echo $main_listing_elem; ?></h4>
230 <div class="vbrowcdescr"><?php echo $visible_descr; ?></div>
231 <?php
232 if ($hidden_descr) {
233 // display a button to read the full description
234 ?>
235 <div class="vbo-result-readmore-wrap">
236 <a class="vbo-result-readmore-trig" href="JavaScript: void(0);"><?php echo JText::translate('VBO_READ_MORE'); ?></a>
237 <div class="vbo-result-readmore-hidden" style="display: none;"><?php echo $room[0]['smalldesc']; ?></div>
238 </div>
239 <?php
240 }
241 ?>
242 </div>
243 <?php
244 if (!empty($carats)) {
245 ?>
246 <div class="roomlist_carats">
247 <?php echo $carats; ?>
248 </div>
249 <?php
250 }
251 ?>
252 <?php
253 if ($has_promotion === true && !empty($room[0]['promotion']['promotxt'])) {
254 ?>
255 <div class="vbo-promotion-block">
256 <div class="vbo-promotion-icon"><?php VikBookingIcons::e('percentage'); ?></div>
257 <div class="vbo-promotion-description">
258 <?php echo $room[0]['promotion']['promotxt']; ?>
259 </div>
260 </div>
261 <?php
262 }
263 ?>
264 </div>
265 </div>
266 <div class="vbcontdivtot">
267 <div class="vbdivtot">
268 <div class="vbdivtotinline">
269 <div class="vbsrowprice">
270 <div class="vbrowroomcapacity">
271 <?php
272 for ($i = 1; $i <= $room[0]['toadult']; $i++) {
273 if ($i <= $this->arrpeople[$indroom]['adults']) {
274 VikBookingIcons::e('male', 'vbo-pref-color-text');
275 } else {
276 VikBookingIcons::e('male', 'vbo-empty-personicn');
277 }
278 }
279 $raw_roomcost = $tax_summary ? $room[0]['cost'] : VikBooking::sayCostPlusIva($room[0]['cost'], $room[0]['idprice']);
280 ?>
281 </div>
282 <div class="vbsrowpricediv">
283 <span class="room_cost">
284 <?php echo VikBooking::formatCurrencyNumber(VikBooking::numberFormat($raw_roomcost), $currencysymb, ['<span class="vbo_currency">%s</span>', '<span class="vbo_price">%s</span>']); ?>
285 </span>
286 <?php
287 if (isset($room[0]['promotion']) && isset($room[0]['promotion']['discount'])) {
288 if ($room[0]['promotion']['discount']['pcent']) {
289 /**
290 * Do not make an upper-cent operation, but rather calculate the original price proportionally:
291 * final price : (100 - discount amount) = x : 100
292 *
293 * @since 1.13.5
294 */
295 $prev_amount = $raw_roomcost * 100 / (100 - $room[0]['promotion']['discount']['amount']);
296 } else {
297 $prev_amount = $raw_roomcost + $room[0]['promotion']['discount']['amount'];
298 }
299 if ($prev_amount > 0) {
300 ?>
301 <div class="vbo-room-result-price-before-discount">
302 <span class="room_cost">
303 <?php echo VikBooking::formatCurrencyNumber(VikBooking::numberFormat($prev_amount), $currencysymb, ['<span class="vbo_currency">%s</span>', '<span class="vbo_price">%s</span>']); ?>
304 </span>
305 </div>
306 <?php
307 if ($room[0]['promotion']['discount']['pcent']) {
308 // hide by default the DIV containing the percent of discount
309 ?>
310 <div class="vbo-room-result-price-before-discount-percent" style="display: none;">
311 <span class="room_cost">
312 <span><?php echo '-' . (float)$room[0]['promotion']['discount']['amount'] . ' %'; ?></span>
313 </span>
314 </div>
315 <?php
316 }
317 }
318 }
319 ?>
320 </div>
321 <?php
322 if ($saylastavail === true) {
323 ?>
324 <span class="vblastavail"><?php echo JText::sprintf('VBLASTUNITSAVAIL', $room[0]['unitsavail']); ?></span>
325 <?php
326 }
327 ?>
328 </div>
329 <div class="vbselectordiv">
330 <button type="button" id="vbselector<?php echo $indroom.'_'.$room[0]['idroom']; ?>" class="btn vbselectr-result vbo-pref-color-btn" onclick="vbSelectRoom('<?php echo $indroom; ?>', '<?php echo $room[0]['idroom']; ?>');"><?php echo JText::translate('VBSELECTR'); ?></button>
331 </div>
332 </div>
333 </div>
334 </div>
335 </div>
336 <?php
337 }
338 ?>
339 </div>
340 <?php
341 }
342
343 /**
344 * Unavailable listings.
345 *
346 * @since 1.17.2 (J) - 1.7.2 (WP)
347 */
348 if ($this->roomsnum === 1 && $this->unavailable_listings && VBOFactory::getConfig()->getBool('search_show_busy_listings', false)) {
349 ?>
350 <div class="vbo-searchresults-party-content vbo-searchresults-party-unavailable-content">
351 <?php
352 foreach ($this->unavailable_listings as $listing_id) {
353 // fetch the room details
354 $listing_details = [VikBooking::getRoomInfo($listing_id)];
355 if (!$listing_details[0]) {
356 continue;
357 }
358
359 // translate records list
360 $this->vbo_tn->translateContents($listing_details, '#__vikbooking_rooms');
361
362 // convert list into associative
363 $listing_details = $listing_details[0];
364
365 // prepare CMS contents depending on platform
366 $listing_details = VBORoomHelper::getInstance()->prepareCMSContents($listing_details, ['smalldesc']);
367
368 // build listing details URI components
369 $listing_uri_data = [
370 'option' => 'com_vikbooking',
371 'view' => 'roomdetails',
372 'roomid' => $listing_details['id'],
373 'num_adults' => ($this->arrpeople[1]['adults'] ?? 2),
374 'num_children' => ($this->arrpeople[1]['children'] ?? 0),
375 'Itemid' => ($pitemid ?: null),
376 ];
377 // route proper URI
378 $listing_page_uri = JRoute::rewrite('index.php?' . http_build_query($listing_uri_data), false);
379
380 // listing amenities
381 $carats = VikBooking::getRoomCaratOriz($listing_details['idcarat'], $this->vbo_tn);
382
383 // build image gallery, if available
384 $gallery_data = [];
385 if (!empty($listing_details['moreimgs'])) {
386 $moreimages = explode(';;', $listing_details['moreimgs']);
387 foreach (array_filter($moreimages) as $mimg) {
388 // push thumb URL
389 $gallery_data[] = $mimg;
390 }
391 }
392
393 // cut off long descriptions by eventually adding a "read more" link
394 $descr_length = strlen((string) $listing_details['smalldesc']);
395 $visible_descr = $listing_details['smalldesc'];
396 $hidden_descr = '';
397 if ($descr_length > 200 && ($descr_length - 200) > 100) {
398 $visible_descr = strip_tags($visible_descr);
399 $hidden_descr = '1';
400 if (function_exists('mb_substr')) {
401 $visible_descr = mb_substr($visible_descr, 0, 200, 'UTF-8');
402 } else {
403 $visible_descr = substr($visible_descr, 0, 200);
404 }
405 $visible_descr .= '...';
406 }
407
408 // print unavailable listing details
409 ?>
410 <div class="room_item room_result vbo-result-listing-unavailable" data-unavailable-id="<?php echo $listing_details['id']; ?>">
411 <div class="vblistroomblock">
412 <div class="vbimglistdiv">
413 <div class="vbo-dots-slider-selector">
414 <a href="<?php echo $listing_page_uri; ?>" target="_blank" data-gallery="<?php echo implode('|', $gallery_data); ?>">
415 <?php
416 if (!empty($listing_details['img']) && is_file(VBO_SITE_PATH . DIRECTORY_SEPARATOR . 'resources' . DIRECTORY_SEPARATOR . 'uploads' . DIRECTORY_SEPARATOR . $listing_details['img'])) {
417 ?>
418 <img class="vblistimg" alt="<?php echo htmlspecialchars($listing_details['name']); ?>" src="<?php echo VBO_SITE_URI; ?>resources/uploads/<?php echo $listing_details['img']; ?>"/>
419 <?php
420 }
421 ?>
422 </a>
423 </div>
424 <div class="vbmodalrdetails">
425 <a href="<?php echo $listing_page_uri; ?>" target="_blank"><?php VikBookingIcons::e('plus'); ?></a>
426 </div>
427 </div>
428 <div class="vbo-info-room">
429 <div class="vbdescrlistdiv">
430 <h4 class="vbrowcname"><a class="vbo-search-results-listing-link" href="<?php echo $listing_page_uri; ?>" target="_blank"><?php echo $listing_details['name']; ?></a></h4>
431 <div class="vbrowcdescr"><?php echo $visible_descr; ?></div>
432 <?php
433 if ($hidden_descr) {
434 // display a button to read the full description
435 ?>
436 <div class="vbo-result-readmore-wrap">
437 <a class="vbo-result-readmore-trig" href="JavaScript: void(0);"><?php echo JText::translate('VBO_READ_MORE'); ?></a>
438 <div class="vbo-result-readmore-hidden" style="display: none;"><?php echo $listing_details['smalldesc']; ?></div>
439 </div>
440 <?php
441 }
442 ?>
443 </div>
444 <?php
445 if (!empty($carats)) {
446 ?>
447 <div class="roomlist_carats">
448 <?php echo $carats; ?>
449 </div>
450 <?php
451 }
452 ?>
453 <div class="vbo-unavailable-block">
454 <div class="vbo-unavailable-icon"><?php VikBookingIcons::e('ban'); ?></div>
455 <div class="vbo-unavailable-description"><?php echo JText::translate('VBLEGBUSY'); ?></div>
456 </div>
457 </div>
458 </div>
459 <div class="vbcontdivtot">
460 <div class="vbdivtot">
461 <div class="vbdivtotinline">
462 <div class="vbsrowprice">
463 <div class="vbrowroomcapacity">
464 <?php
465 for ($i = 1; $i <= $listing_details['toadult']; $i++) {
466 if ($i <= ($this->arrpeople[1]['adults'] ?? 2)) {
467 VikBookingIcons::e('male', 'vbo-pref-color-text');
468 } else {
469 VikBookingIcons::e('male', 'vbo-empty-personicn');
470 }
471 }
472 ?>
473 </div>
474 </div>
475 <div class="vbselectordiv">
476 <a class="btn vbselectr-result vbo-result-unavailable vbo-pref-color-btn" href="<?php echo $listing_page_uri; ?>" target="_blank"><?php echo JText::translate('VBSEARCHRESDETAILS'); ?></a>
477 </div>
478 </div>
479 </div>
480 </div>
481 </div>
482 <?php
483 }
484 ?>
485 </div>
486 <?php
487 }
488 ?>
489 </div>
490 </div>
491
492 <script type="text/javascript">
493 jQuery(function() {
494
495 /**
496 * Configure thumbnails gallery.
497 */
498 jQuery('.vbo-dots-slider-selector').each(function() {
499 var sliderLink = jQuery(this).find('a').first();
500 if (!sliderLink.length) {
501 return;
502 }
503 var gallery = sliderLink.data('gallery');
504 if (!gallery || !gallery.length) {
505 return;
506 }
507 var thumbs_base_uri = '<?php echo VBO_SITE_URI . 'resources/uploads/thumb_'; ?>';
508 var gallery_data = gallery.split('|');
509 var images = [];
510 for (var i = 0; i < gallery_data.length; i++) {
511 if (!gallery_data[i].length) {
512 continue;
513 }
514 images.push(thumbs_base_uri + gallery_data[i]);
515 }
516 if (!images.length) {
517 return;
518 }
519 // move original main photo and make it hidden so that the dialog will keep showing it
520 var room_main_photo = jQuery(this).find('img.vblistimg');
521 if (room_main_photo.length) {
522 room_main_photo.hide().appendTo(jQuery(this).parent());
523 }
524 // render slider
525 var slideWrap = sliderLink.clone();
526 jQuery(this).html('').vikDotsSlider({
527 images: images,
528 navButPrevContent: '<?php VikBookingIcons::e('chevron-left'); ?>',
529 navButNextContent: '<?php VikBookingIcons::e('chevron-right'); ?>',
530 onDisplaySlide: function() {
531 var content = jQuery(this).children().clone(true, true);
532 <?php
533 if (VBOPlatformDetection::isWordPress()) {
534 /**
535 * @wponly In order to avoid delays with Fancybox, we do not re-construct the A tag.
536 * We just append the slide image.
537 */
538 ?>
539 jQuery(this).html('').append(content);
540 <?php
541 } else {
542 ?>
543 var link = jQuery('<a target="_blank"></a>').attr('href', slideWrap.attr('href')).attr('class', slideWrap.attr('class')).append(content);
544 jQuery(this).html('').append(link);
545 <?php
546 }
547 ?>
548 }
549 });
550 });
551
552 /**
553 * Configure layout style actions.
554 */
555 document.querySelectorAll('.vbo-results-style-option').forEach((styleEl) => {
556 styleEl.addEventListener('click', (e) => {
557 let styleOption = e.target;
558 if (!styleOption.matches('.vbo-results-style-option')) {
559 styleOption = styleOption.closest('.vbo-results-style-option');
560 }
561 let styleType = styleEl.getAttribute('data-type');
562 let styleToggle = styleEl.getAttribute('data-toggle');
563 document.querySelectorAll('.vbo-searchresults-classic-wrap').forEach((wrap) => {
564 wrap.setAttribute('class', 'vbo-searchresults-classic-wrap');
565 if (styleToggle) {
566 wrap.classList.add(styleToggle);
567 }
568 });
569 document.querySelectorAll('.vbo-results-style-option-active').forEach((prevActive) => {
570 prevActive.classList.remove('vbo-results-style-option-active');
571 });
572 document.querySelectorAll('.vbo-results-style-option[data-type="' + styleType + '"]').forEach((nowActive) => {
573 nowActive.classList.add('vbo-results-style-option-active');
574 });
575 });
576 });
577
578 /**
579 * Configure description "read more" action links.
580 */
581 document.querySelectorAll('.vbo-result-readmore-trig').forEach((readMore) => {
582 readMore.addEventListener('click', (e) => {
583 try {
584 // get full (HTML & hidden) description
585 let fullDescr = readMore.closest('.vbo-result-readmore-wrap').querySelector('.vbo-result-readmore-hidden').innerHTML;
586 // replace visible description
587 readMore.closest('.vbdescrlistdiv').querySelector('.vbrowcdescr').innerHTML = fullDescr;
588 } catch(e) {
589 console.error(e);
590 }
591
592 // delete link from DOM
593 readMore.remove();
594 });
595 });
596
597 /**
598 * Configure results hovering effects on map.
599 */
600 document.querySelectorAll('.vbo-searchresults-classic-wrap .room_item:not(.vbo-result-listing-unavailable)').forEach((resultEl) => {
601 let resultData = resultEl.getAttribute('id').split('_');
602 let resultId = resultData[1] || 0;
603 resultEl.addEventListener('mouseenter', () => {
604 const mapTarget = document.querySelector('.vbo-map-listing-cost[data-room-id="' + resultId + '"]');
605 if (mapTarget) {
606 mapTarget.classList.add('vbo-map-listing-cost-highlight');
607 }
608 if (typeof vbo_geomarker_units !== 'undefined' && typeof vbo_geomarker_units[resultId + '_1'] !== 'undefined') {
609 // take marker on top of the others overlapping the same zoomed coordinates
610 vbo_geomarker_units[resultId + '_1'].zIndex = 9999;
611 }
612 });
613 resultEl.addEventListener('mouseleave', () => {
614 const mapTarget = document.querySelector('.vbo-map-listing-cost[data-room-id="' + resultId + '"]');
615 if (mapTarget) {
616 mapTarget.classList.remove('vbo-map-listing-cost-highlight');
617 }
618 if (typeof vbo_geomarker_units !== 'undefined' && typeof vbo_geomarker_units[resultId + '_1'] !== 'undefined') {
619 // restore marker z-index property
620 vbo_geomarker_units[resultId + '_1'].zIndex = 1;
621 }
622 });
623 });
624
625 /**
626 * Register event for activating the search filters.
627 */
628 const filtersBtn = document.querySelector('.vbo-results-filters-toggle');
629 if (filtersBtn) {
630 filtersBtn.addEventListener('click', () => {
631 // modal cancel filters button
632 let filtersCancelBtn = document.createElement('button');
633 filtersCancelBtn.setAttribute('type', 'button');
634 filtersCancelBtn.classList.add('btn', 'vbo-pref-color-btn-secondary', 'vbo-modal-dismiss-btn');
635 filtersCancelBtn.innerText = <?php echo json_encode(JText::translate('VBDIALOGBTNCANCEL')); ?>;
636 filtersCancelBtn.addEventListener('click', () => {
637 let filtersForm = document.querySelector('form#vbo-results-filters-form');
638 if (filtersForm) {
639 // clean up checkbox and radio elements
640 filtersForm
641 .querySelectorAll('input[type="checkbox"]:checked, input[type="radio"]:checked')
642 .forEach((el) => {
643 el.checked = false;
644 });
645 // clean up input text, number and textarea elements
646 filtersForm
647 .querySelectorAll('input[type="text"], input[type="number"], textarea')
648 .forEach((el) => {
649 el.value = '';
650 });
651 // clean up select elements
652 filtersForm
653 .querySelectorAll('select')
654 .forEach((el) => {
655 el.value = '';
656 });
657 // clean up range elements
658 filtersForm
659 .querySelectorAll('input[type="range"]')
660 .forEach((el) => {
661 el.disabled = true;
662 });
663 // submit the form with no filters set
664 filtersForm.submit();
665 }
666 VBOCore.emitEvent('vbo-dismiss-search-results-filters-modal');
667 });
668
669 // modal apply filters button
670 let filtersApplyBtn = document.createElement('button');
671 filtersApplyBtn.setAttribute('type', 'button');
672 filtersApplyBtn.classList.add('btn', 'vbo-pref-color-btn', 'vbo-modal-apply-btn');
673 filtersApplyBtn.innerText = <?php echo json_encode(JText::translate('VBSUBMITCOUPON')); ?>;
674 filtersApplyBtn.addEventListener('click', () => {
675 let filtersForm = document.querySelector('form#vbo-results-filters-form');
676 if (filtersForm) {
677 // submit the form with the current filters set
678 filtersForm.submit();
679 }
680 VBOCore.emitEvent('vbo-dismiss-search-results-filters-modal');
681 });
682
683 // display modal
684 let filtersModal = VBOCore.displayModal({
685 suffix: 'search-results-filters-modal',
686 title: <?php echo json_encode(JText::translate('VBO_FILTERS')); ?>,
687 extra_class: 'vbo-modal-tall vbo-modal-sticky-head vbo-modal-sticky-footer',
688 body_prepend: true,
689 lock_scroll: true,
690 dismiss_event: 'vbo-dismiss-search-results-filters-modal',
691 onDismiss: () => {
692 document
693 .querySelector('.vbo-results-filters-form-helper')
694 .append(
695 document.querySelector('.vbo-results-filters-form-wrapper')
696 );
697 },
698 footer_left: filtersCancelBtn,
699 footer_right: filtersApplyBtn,
700 });
701
702 // populate modal body
703 filtersModal[0].append(document.querySelector('.vbo-results-filters-form-wrapper'));
704 });
705 }
706 });
707 </script>
708