diff --git a/admin/themes/default/template/controllers/normal_products/helpers/tree/tree.tpl b/admin/themes/default/template/controllers/normal_products/helpers/tree/tree.tpl deleted file mode 100644 index ce2479919..000000000 --- a/admin/themes/default/template/controllers/normal_products/helpers/tree/tree.tpl +++ /dev/null @@ -1,39 +0,0 @@ -{* -* Since 2010 Webkul. -* -* NOTICE OF LICENSE -* -* All right is reserved, -* Please go through this link for complete license : https://store.webkul.com/license.html -* -* DISCLAIMER -* -* Do not edit or add to this file if you wish to upgrade this module to newer -* versions in the future. If you wish to customize this module for your -* needs please refer to https://store.webkul.com/customisation-guidelines/ for more information. -* -* @author Webkul IN -* @copyright Since 2010 Webkul IN -* @license https://store.webkul.com/license.html -*} -{extends file="helpers/tree/tree.tpl"} - \ No newline at end of file diff --git a/admin/themes/default/template/helpers/tree/tree.tpl b/admin/themes/default/template/helpers/tree/tree.tpl index c4ecff65f..30c4283c6 100644 --- a/admin/themes/default/template/helpers/tree/tree.tpl +++ b/admin/themes/default/template/helpers/tree/tree.tpl @@ -84,6 +84,22 @@ }); {/if} + {if isset($auto_select_children) && $auto_select_children == true} + $('#{$id|escape:'html':'UTF-8'}').find(':input[type=checkbox]').on('click', function(){ + if ($(this).is(":checked")) { + $(this).closest('.tree-folder').find(':input[type=checkbox]').each(function(){ + $(this).prop('checked', true); + $(this).parent().addClass('tree-selected'); + }); + } else { + $(this).closest('.tree-folder').find(':input[type=checkbox]').each(function(){ + $(this).prop('checked', false); + $(this).parent().removeClass('tree-selected'); + }); + } + }); + {/if} + $(document).ready(function () { var tree = $("#{$id|escape:'html':'UTF-8'}").tree('collapseAll'); diff --git a/classes/helper/HelperTree.php b/classes/helper/HelperTree.php index 0a3824205..d79bea095 100644 --- a/classes/helper/HelperTree.php +++ b/classes/helper/HelperTree.php @@ -29,6 +29,7 @@ class HelperTreeCore extends TreeCore private $_use_bulk_actions; private $_use_checkbox; private $_show_collapse_expand_button = true; + private $_auto_select_children = false; private $_max_height = 350; @@ -43,6 +44,18 @@ class HelperTreeCore extends TreeCore return (isset($this->_use_search) && $this->_use_search); } + public function setAutoSelectChildren($value) + { + $this->_auto_select_children = (bool)$value; + return $this; + } + + public function autoSelectChildren() + { + return (isset($this->_auto_select_children) && $this->_auto_select_children); + } + + public function setUseBulkActions($value) { $this->_use_bulk_actions = (bool)$value; @@ -119,6 +132,7 @@ class HelperTreeCore extends TreeCore ); $this->setAttribute('use_search', $this->useSearch()); } + $this->setAttribute('auto_select_children', $this->autoSelectChildren()); if ($this->showCollapseExpandButton()) { $collapse_all = new TreeToolbarLink( diff --git a/controllers/admin/AdminNormalProductsController.php b/controllers/admin/AdminNormalProductsController.php index 0e52ca53f..c584a46b6 100644 --- a/controllers/admin/AdminNormalProductsController.php +++ b/controllers/admin/AdminNormalProductsController.php @@ -3507,6 +3507,7 @@ class AdminNormalProductsControllerCore extends AdminController 'selectedElements' => $selectedElements ])) ->setUseCheckBox(true) + ->setAutoSelectChildren(true) ->setUseBulkActions(true) ->setUseSearch(true); $data->assign('hotel_tree', $tree->render()); diff --git a/controllers/front/OrderConfirmationController.php b/controllers/front/OrderConfirmationController.php index a60326859..2b5709135 100644 --- a/controllers/front/OrderConfirmationController.php +++ b/controllers/front/OrderConfirmationController.php @@ -469,8 +469,6 @@ class OrderConfirmationControllerCore extends FrontController { if (Tools::getValue('ajax') != 'true') { parent::setMedia(); - $this->addCSS(_THEME_CSS_DIR_.'history.css'); - $this->addJS(_THEME_JS_DIR_.'history.js'); $this->addJS(_THEME_JS_DIR_.'order-confirmation.js'); $this->addCSS(_THEME_CSS_DIR_.'order-confirmation.css'); $this->addJqueryPlugin(array('fancybox')); //fancybox not found for some client theme diff --git a/modules/hotelreservationsystem/classes/HotelBookingDetail.php b/modules/hotelreservationsystem/classes/HotelBookingDetail.php index 5d7df1dba..074dc1ea5 100644 --- a/modules/hotelreservationsystem/classes/HotelBookingDetail.php +++ b/modules/hotelreservationsystem/classes/HotelBookingDetail.php @@ -185,7 +185,7 @@ class HotelBookingDetail extends ObjectModel return $result; } - public function getBookingDataParams($params) + public function getBookingDataParams(&$params) { if (!isset($params['id_room_type'])) { $params['id_room_type'] = 0; @@ -211,6 +211,9 @@ class HotelBookingDetail extends ObjectModel if (!isset($params['search_cart_rms'])) { $params['search_cart_rms'] = 0; } + if (!isset($params['hourly_booking'])) { + $params['hourly_booking'] = false; + } if (!isset($params['only_active_roomtype'])) { $params['only_active_roomtype'] = 1; @@ -236,6 +239,8 @@ class HotelBookingDetail extends ObjectModel $params['only_search_data'] = 0; } + Hook::exec('actionBookingDataParamsModifier', array('params' => &$params)); + return $params; } @@ -292,32 +297,34 @@ class HotelBookingDetail extends ObjectModel // Unavailable Rooms if ($search_unavai) { - $params = array( + $searchParams = array( 'idHotel' => $hotel_id, 'dateFrom' => $date_from, 'dateTo' => $date_to, 'idRoomType' => $id_room_type, 'allowedIdRoomTypes' => $allowedIdRoomTypes, 'applyLosRestriction' => $applyLosRestriction, + 'allParams' => $params, ); - $unavailRoomTypes = $this->getSearchUnavailableRooms($params); + $unavailRoomTypes = $this->getSearchUnavailableRooms($searchParams); } // Cart Rooms if ($search_cart_rms) { - $params = array( + $searchParams = array( 'idHotel' => $hotel_id, 'idCart' => $id_cart, 'idGuest' => $id_guest, 'idRoomType' => $id_room_type, 'allowedIdRoomTypes' => $allowedIdRoomTypes, + 'allParams' => $params, ); - $cartRoomTypes = $this->getSearchCartRooms($params); + $cartRoomTypes = $this->getSearchCartRooms($searchParams); } // Available Rooms if ($search_available) { - $params = array( + $searchParams = array( 'idHotel' => $hotel_id, 'dateFrom' => $date_from, 'dateTo' => $date_to, @@ -327,16 +334,28 @@ class HotelBookingDetail extends ObjectModel 'searchOccupancy' => $occupancy, 'allowedIdRoomTypes' => $allowedIdRoomTypes, 'applyLosRestriction' => $applyLosRestriction, + 'hourlyBooking' => $hourly_booking, + 'allParams' => $params, ); - $availableRoomTypes = $this->getSearchAvailableRooms($params); + $availableRoomTypes = $this->getSearchAvailableRooms($searchParams); if ($availableRoomTypes['unavailableRoomTypes'] && $search_unavai) { + // format unavailable room types foreach ($availableRoomTypes['unavailableRoomTypes'] as $idProduct => $roomTypeDetail) { - if (!isset($unavailRoomTypes[$idProduct])) { - $unavailRoomTypes[$idProduct] = array(); + foreach ($roomTypeDetail as $idRoom => $roomDetail) { + if (!isset($unavailRoomTypes[$idProduct][$idRoom])) { + $unavailRoomTypes[$idProduct][$idRoom] = array( + 'id_product' => $roomDetail['id_product'], + 'id_room' => $roomDetail['id_room'], + 'id_hotel' => $roomDetail['id_hotel'], + 'room_num' => $roomDetail['room_num'], + 'detail' => array() + ); + } + $unavailRoomTypes[$idProduct][$idRoom]['detail'][] = array( + 'id_status' => $roomDetail['id_status'], + 'room_comment' => $roomDetail['room_comment'] + ); } - - // FYI: used array_merge because we have int index - $unavailRoomTypes[$idProduct] = array_merge($unavailRoomTypes[$idProduct], $roomTypeDetail); } } @@ -345,19 +364,20 @@ class HotelBookingDetail extends ObjectModel // Booked Rooms if ($search_booked) { - $params = array( + $searchParams = array( 'idHotel' => $hotel_id, 'dateFrom' => $date_from, 'dateTo' => $date_to, 'idRoomType' => $id_room_type, 'allowedIdRoomTypes' => $allowedIdRoomTypes, + 'allParams' => $params, ); - $bookedRoomTypes = $this->getSearchBookedRooms($params); + $bookedRoomTypes = $this->getSearchBookedRooms($searchParams); } // Partially available Rooms if ($search_partial) { - $params = array( + $searchParams = array( 'idHotel' => $hotel_id, 'dateFrom' => $date_from, 'dateTo' => $date_to, @@ -366,21 +386,14 @@ class HotelBookingDetail extends ObjectModel 'idRoomType' => $id_room_type, 'searchOccupancy' => $occupancy, 'allowedIdRoomTypes' => $allowedIdRoomTypes, + 'hourlyBooking' => $hourly_booking, + 'allParams' => $params, ); - $partiallyAvailRoomTypes = $this->getSearchPartiallyAvailRooms($params); - - if ($partiallyAvailRoomTypes['unavailableRoomTypes'] && $search_unavai) { - foreach ($partiallyAvailRoomTypes['unavailableRoomTypes'] as $idProduct => $roomTypeDetail) { - if (!isset($unavailRoomTypes[$idProduct])) { - $unavailRoomTypes[$idProduct] = array(); - } - - // FYI: used array_merge because we have int index - $unavailRoomTypes[$idProduct] = array_merge($unavailRoomTypes[$idProduct], $roomTypeDetail); - } - } + $partiallyAvailRoomTypes = $this->getSearchPartiallyAvailRooms($searchParams); + // Unavailable rooms and booked rooms are already included in there respective search + // So, no need to seperate them here $partiallyAvailRoomsCount = $partiallyAvailRoomTypes['partiallyAvailRoomsCount']; $partiallyAvailRoomTypes = $partiallyAvailRoomTypes['partiallyAvailRooms']; } @@ -480,6 +493,7 @@ class HotelBookingDetail extends ObjectModel * 'idRoomType' => ..., * 'allowedIdRoomTypes' => ..., * 'applyLosRestriction' => ..., + * 'allParams' => ..., * ); */ protected function getSearchUnavailableRooms($params) @@ -501,34 +515,64 @@ class HotelBookingDetail extends ObjectModel $stayStartDate = date('Y-m-d', strtotime($dateFrom)); // Room status inactive - $sql1 = 'SELECT `id` AS `id_room`, `id_product`, `id_hotel`, `room_num`, `comment` AS `room_comment` + $sql = array(); + $sql[] = 'SELECT `id` AS `id_room`, `id_product`, `id_hotel`, `room_num`, `comment` AS `room_comment`, `id_status`, NULL AS `date_from`, NULL AS `date_to` FROM `'._DB_PREFIX_.'htl_room_information` WHERE `id_hotel`='.(int)$idHotel.' AND `id_status` = '. HotelRoomInformation::STATUS_INACTIVE.' AND IF('.(int)$idRoomType.' > 0, `id_product` = '.(int)$idRoomType.', 1) AND `id_product` IN ('.$allowedIdRoomTypes.')'; // check room is temperory inactive - $sql2 = 'SELECT hri.`id` AS `id_room`, hri.`id_product`, hri.`id_hotel`, hri.`room_num`, hri.`comment` AS `room_comment` + $sql[] = 'SELECT hri.`id` AS `id_room`, hri.`id_product`, hri.`id_hotel`, hri.`room_num`, hri.`comment` AS `room_comment`, hri.`id_status`, hrdd.`date_from` AS `date_from`, hrdd.`date_to` AS `date_to` FROM `'._DB_PREFIX_.'htl_room_information` AS hri INNER JOIN `'._DB_PREFIX_.'htl_room_disable_dates` AS hrdd ON (hrdd.`id_room_type` = hri.`id_product` AND hrdd. id_room = hri.`id`) - WHERE hri.`id_hotel`='.$idHotel.' AND hri.`id_status` = '. HotelRoomInformation::STATUS_TEMPORARY_INACTIVE .' AND hrdd.`date_from` <= \''.pSql($dateFrom).'\' AND hrdd.`date_to` >= \''.pSql($dateTo).'\' AND IF('.(int)$idRoomType.' > 0, hri.`id_product` = '.(int)$idRoomType.', 1) AND hri.`id_product` IN ('.$allowedIdRoomTypes.')'; + WHERE hri.`id_hotel`='.$idHotel.' AND hri.`id_status` = '. HotelRoomInformation::STATUS_TEMPORARY_INACTIVE .' AND ( + (hrdd.`date_from` <= \''.pSQL($dateFrom).'\' AND hrdd.`date_to` > \''.pSQL($dateFrom).'\' AND hrdd.`date_to` <= \''.pSQL($dateTo).'\') OR + (hrdd.`date_from` >= \''.pSQL($dateFrom).'\' AND hrdd.`date_to` > \''.pSQL($dateFrom).'\' AND hrdd.`date_to` <= \''.pSQL($dateTo).'\') OR + (hrdd.`date_from` >= \''.pSQL($dateFrom).'\' AND hrdd.`date_from` < \''.pSQL($dateTo).'\' AND hrdd.`date_to` >= \''.pSQL($dateTo).'\') OR + (hrdd.`date_from` <= \''.pSql($dateFrom).'\' AND hrdd.`date_to` >= \''.pSql($dateTo).'\') + ) AND IF('.(int)$idRoomType.' > 0, hri.`id_product` = '.(int)$idRoomType.', 1) AND hri.`id_product` IN ('.$allowedIdRoomTypes.')'; - $sql = $sql1.' UNION '.$sql2; if ($applyLosRestriction) { - $sql3 = 'SELECT hri.`id` AS `id_room`, hri.`id_product`, hri.`id_hotel`, hri.`room_num`, hri.`comment` AS `room_comment` + $sql[] = 'SELECT hri.`id` AS `id_room`, hri.`id_product`, hri.`id_hotel`, hri.`room_num`, hri.`comment` AS `room_comment`, '.HotelRoomInformation::STATUS_SEARCH_LOS_UNSATISFIED.' AS `id_status`, NULL AS `date_from`, NULL AS `date_to` FROM `'._DB_PREFIX_.'htl_room_information` AS hri INNER JOIN `'._DB_PREFIX_.'htl_room_type` AS hrt ON (hrt.`id_product` = hri.`id_product`) LEFT JOIN `'._DB_PREFIX_.'htl_room_type_restriction_date_range` AS hrtr ON (hrt.`id_product` = hrtr.`id_product` AND (hrtr.`date_from` <= \''.pSQL($stayStartDate).'\' AND hrtr.`date_to` > \''.pSQL($stayStartDate).'\')) WHERE hri.`id_hotel`='.(int)$idHotel.' AND (IFNULL(hrtr.`min_los`, hrt.`min_los`) >'. (int)$lengthOfStay.' OR IF(IFNULL(hrtr.`max_los`, hrt.`max_los`) > 0, IFNULL(hrtr.`max_los`, hrt.`max_los`) < '.(int)$lengthOfStay.', 0)) AND IF('.(int)$idRoomType.' > 0, hri.`id_product` = '.(int)$idRoomType.', 1) AND hri.`id_product` IN ('.$allowedIdRoomTypes.')'; - $sql = $sql.' UNION '.$sql3; } - $sql .= ' ORDER BY id_room ASC'; + Hook::exec('actionUnavailRoomSearchSqlModifier', array( + 'sql' => &$sql, + 'params' => array( + 'id_hotel' => $idHotel, + 'id_product' => $idRoomType, + 'date_from' => $dateFrom, + 'date_to' => $dateTo, + 'all_params' => $allParams + ) + )); + + $sql = implode(' UNION ', $sql); + $sql .= ' ORDER BY `id_room`, `date_from` ASC'; $unavailRoomTypes = array(); if ($unavailRooms = Db::getInstance()->executeS($sql)) { foreach ($unavailRooms as $unavailRoomDetail) { - $unavailRoomTypes[$unavailRoomDetail['id_product']][] = $unavailRoomDetail; + if (!isset($unavailRoomTypes[$unavailRoomDetail['id_product']][$unavailRoomDetail['id_room']])) { + $unavailRoomTypes[$unavailRoomDetail['id_product']][$unavailRoomDetail['id_room']] = array( + 'id_product' => $unavailRoomDetail['id_product'], + 'id_room' => $unavailRoomDetail['id_room'], + 'id_hotel' => $unavailRoomDetail['id_hotel'], + 'room_num' => $unavailRoomDetail['room_num'], + 'detail' => array() + ); + } + $unavailRoomTypes[$unavailRoomDetail['id_product']][$unavailRoomDetail['id_room']]['detail'][] = array( + 'id_status' => $unavailRoomDetail['id_status'], + 'room_comment' => $unavailRoomDetail['room_comment'], + 'date_from' => $unavailRoomDetail['date_from'], + 'date_to' => $unavailRoomDetail['date_to'], + ); } } @@ -542,6 +586,7 @@ class HotelBookingDetail extends ObjectModel * 'idGuest' => ..., * 'idRoomType' => ..., * 'allowedIdRoomTypes' => ..., + * 'allParams' => ..., * ); */ protected function getSearchCartRooms($params) @@ -550,10 +595,40 @@ class HotelBookingDetail extends ObjectModel $cartRoomTypes = array(); if ($idCart && $idGuest) { - $sql = 'SELECT cbd.`id_product`, cbd.`id_room`, cbd.`id_hotel`, cbd.`booking_type`, cbd.`comment`, rf.`room_num`, cbd.`date_from`, cbd.`date_to` - FROM `'._DB_PREFIX_.'htl_cart_booking_data` AS cbd - INNER JOIN `'._DB_PREFIX_.'htl_room_information` AS rf ON (rf.`id` = cbd.`id_room`) - WHERE cbd.`id_hotel`= '.(int)$idHotel.' AND cbd.`id_cart` = '.(int)$idCart.' AND cbd.`id_guest` ='.(int)$idGuest.' AND cbd.`is_refunded` = 0 AND cbd.`is_back_order` = 0 AND IF('.(int)$idRoomType.' > 0, rf.`id_product` = '.(int)$idRoomType.', 1) AND rf.`id_product` IN ('.$allowedIdRoomTypes.')'; + $selectCartRoomSearch = 'SELECT cbd.`id_product`, cbd.`id_room`, cbd.`id_hotel`, cbd.`booking_type`, + cbd.`comment`, rf.`room_num`, cbd.`date_from`, cbd.`date_to`'; + $joinCartRoomSearch = 'INNER JOIN `'._DB_PREFIX_.'htl_room_information` AS rf ON (rf.`id` = cbd.`id_room`)'; + $whereCartRoomSearch = 'WHERE cbd.`id_hotel`= '.(int)$idHotel.' AND cbd.`id_cart` = '.(int)$idCart.' + AND cbd.`id_guest` ='.(int)$idGuest.' AND cbd.`is_refunded` = 0 AND cbd.`is_back_order` = 0 + AND IF('.(int)$idRoomType.' > 0, rf.`id_product` = '.(int)$idRoomType.', 1) AND rf.`id_product` + IN ('.$allowedIdRoomTypes.')'; + $groupByCartRoomSearch = ''; + $orderByCartRoomSearch = ''; + $orderWayCartRoomSearch = ''; + + Hook::exec('actionCartRoomSearchSqlModifier', array( + 'select' => $selectCartRoomSearch, + 'join' => &$joinCartRoomSearch, + 'where' => &$whereCartRoomSearch, + 'group_by' => &$groupByCartRoomSearch, + 'order_by' => &$orderByCartRoomSearch, + 'order_way' => &$orderWayCartRoomSearch, + 'params' => array( + 'id_hotel' => $idHotel, + 'id_product' => $idRoomType, + 'idCart' => $idCart, + 'idGuest' => $idGuest, + 'all_params' => $allParams + ) + )); + + $sql = $selectCartRoomSearch; + $sql .= ' FROM `'._DB_PREFIX_.'htl_cart_booking_data` AS cbd'; + $sql .= ' '.$joinCartRoomSearch; + $sql .= ' '.$whereCartRoomSearch; + $sql .= ' '.$groupByCartRoomSearch; + $sql .= ' '.$orderByCartRoomSearch; + $sql .= ' '.$orderWayCartRoomSearch; if ($cartRooms = Db::getInstance()->executeS($sql)) { foreach ($cartRooms as $cartRoomDetail) { @@ -568,15 +643,17 @@ class HotelBookingDetail extends ObjectModel /** * $params = array( - * 'idHotel' => ..., - * 'dateFrom' => ..., - * 'dateTo' => ..., - * 'idCart' => ..., - * 'idGuest' => ..., - * 'idRoomType' => ..., - * 'searchOccupancy' => ..., - * 'allowedIdRoomTypes' => ..., - * 'applyLosRestriction' => ..., + * 'idHotel' => ..., + * 'dateFrom' => ..., + * 'dateTo' => ..., + * 'idCart' => ..., + * 'idGuest' => ..., + * 'idRoomType' => ..., + * 'searchOccupancy' => ..., + * 'allowedIdRoomTypes' => ..., + * 'applyLosRestriction' => ..., + * 'hourlyBooking' => ..., + * 'allParams' => ..., * ); */ protected function getSearchAvailableRooms($params) @@ -606,15 +683,15 @@ class HotelBookingDetail extends ObjectModel } // Exculde Booked rooms - $exclude_ids = 'SELECT `id_room` + $excludeRoomId = array(); + $excludeRoomId['checked_out'] = 'SELECT `id_room` FROM `'._DB_PREFIX_.'htl_booking_detail` - WHERE `id_hotel` = '.(int)$idHotel.' AND `is_back_order` = 0 AND `is_refunded` = 0 AND IF(`id_status` = '. self::STATUS_CHECKED_OUT.', ( - (DATE_FORMAT(`check_out`, "%Y-%m-%d") > \''.pSQL($dateFrom).'\' AND DATE_FORMAT(`check_out`, "%Y-%m-%d") <= \''.PSQL($dateTo).'\') AND ( + WHERE `id_hotel` = '.(int)$idHotel.' AND `is_back_order` = 0 AND `is_refunded` = 0 AND IF(`id_status` = '. self::STATUS_CHECKED_OUT.', + IF('.(int) $hourlyBooking.', 1, (DATE_FORMAT(`check_out`, "%Y-%m-%d") != DATE_FORMAT(\''.pSQL($dateFrom).'\', "%Y-%m-%d")) AND (`check_out` > \''.pSQL($dateFrom).'\' AND `check_out` <= \''.PSQL($dateTo).'\')) AND ( (`date_from` <= \''.pSQL($dateFrom).'\' AND `check_out` > \''.pSQL($dateFrom).'\' AND `check_out` <= \''.PSQL($dateTo).'\') OR (`date_from` >= \''.pSQL($dateFrom).'\' AND `check_out` > \''.pSQL($dateFrom).'\' AND `check_out` <= \''.pSQL($dateTo).'\') OR (`date_from` >= \''.pSQL($dateFrom).'\' AND `date_from` < \''.pSQL($dateTo).'\' AND `check_out` >= \''.pSQL($dateTo).'\') OR (`date_from` <= \''.pSQL($dateFrom).'\' AND `check_out` >= \''.pSQL($dateTo).'\') - ) ), ( (`date_from` <= \''.pSQL($dateFrom).'\' AND `date_to` > \''.pSQL($dateFrom).'\' AND `date_to` <= \''.PSQL($dateTo).'\') OR (`date_from` >= \''.pSQL($dateFrom).'\' AND `date_to` <= \''.pSQL($dateTo).'\') OR @@ -622,55 +699,54 @@ class HotelBookingDetail extends ObjectModel (`date_from` <= \''.pSQL($dateFrom).'\' AND `date_to` >= \''.pSQL($dateTo).'\') )) AND IF('.(int)$idRoomType.' > 0, `id_product` = '.(int)$idRoomType.', 1) AND `id_product` IN ('.$allowedIdRoomTypes.')'; - // We have removed cart rooms after finally getting available rooms from booking // Exclude temporary disable rooms - $exclude_ids .= ' UNION - SELECT hri.`id` AS id_room + $excludeRoomId['disabled'] = 'SELECT hri.`id` AS id_room FROM `'._DB_PREFIX_.'htl_room_information` AS hri INNER JOIN `'._DB_PREFIX_.'htl_room_disable_dates` AS hrdd ON (hrdd.`id_room_type` = hri.`id_product` AND hrdd.`id_room` = hri.`id`) WHERE hri.`id_hotel`='.(int)$idHotel.' AND hri.`id_status` = '. HotelRoomInformation::STATUS_TEMPORARY_INACTIVE .' AND (hrdd.`date_from` < \''.pSql($dateTo).'\' AND hrdd.`date_to` > \''.pSql($dateFrom).'\') AND IF('.(int)$idRoomType.' > 0, hri.`id_product` = '.(int)$idRoomType.', 1) AND hri.`id_product` IN ('.$allowedIdRoomTypes.')'; // LOS Restriction. Also, Remember to check max LOS restriction is greater than zero if ($applyLosRestriction) { - $exclude_ids .= ' UNION - SELECT hri.`id` AS `id_room` + $excludeRoomId['length_of_stay'] = 'SELECT hri.`id` AS `id_room` FROM `'._DB_PREFIX_.'htl_room_information` AS hri INNER JOIN `'._DB_PREFIX_.'htl_room_type` AS hrt ON (hrt.`id_product` = hri.`id_product`) LEFT JOIN `'._DB_PREFIX_.'htl_room_type_restriction_date_range` AS hrtr ON (hrt.`id_product` = hrtr.`id_product` AND (hrtr.`date_from` <= \''.pSQL($stayStartDate).'\' AND hrtr.`date_to` > \''.pSQL($stayStartDate).'\')) WHERE hri.`id_hotel`='.(int)$idHotel.' AND (IFNULL(hrtr.`min_los`, hrt.`min_los`) >'. (int)$lengthOfStay.' OR IF(IFNULL(hrtr.`max_los`, hrt.`max_los`) > 0, IFNULL(hrtr.`max_los`, hrt.`max_los`) < '.(int)$lengthOfStay.', 0)) AND IF('.(int)$idRoomType.' > 0, hri.`id_product` = '.(int)$idRoomType.', 1) AND hri.`id_product` IN ('.$allowedIdRoomTypes.')'; } + // We will remove cart rooms after finally getting available rooms from booking $selectAvailRoomSearch = 'SELECT ri.`id` AS `id_room`, ri.`id_product`, ri.`id_hotel`, ri.`room_num`, ri.`comment` AS `room_comment`, hrt.`max_adults` AS max_adult, hrt.`max_children`, hrt.`max_guests` AS max_occupancy'; $joinAvailRoomSearch = 'INNER JOIN `'._DB_PREFIX_.'htl_room_type` AS hrt ON (hrt.`id_product` = ri.`id_product`)'; - $whereAvailRoomSearch = 'WHERE ri.`id_hotel`='.(int)$idHotel.' AND ri.`id_status` != '. HotelRoomInformation::STATUS_INACTIVE.' AND ri.`id` NOT IN ('.$exclude_ids.') AND IF('.(int)$idRoomType.' > 0, ri.`id_product` = '.(int)$idRoomType.', 1) AND ri.`id_product` IN ('.$allowedIdRoomTypes.')'; + $whereAvailRoomSearch = 'WHERE ri.`id_hotel`='.(int)$idHotel.' AND ri.`id_status` != '. HotelRoomInformation::STATUS_INACTIVE.' AND IF('.(int)$idRoomType.' > 0, ri.`id_product` = '.(int)$idRoomType.', 1) AND ri.`id_product` IN ('.$allowedIdRoomTypes.')'; $groupByAvailRoomSearch = ''; $orderByAvailRoomSearch = 'ORDER BY ri.`id`'; $orderWayAvailRoomSearch = 'ASC'; - Hook::exec('actionAvailRoomSearchSqlModifier', - array( - 'select' => $selectAvailRoomSearch, - 'join' => &$joinAvailRoomSearch, - 'where' => &$whereAvailRoomSearch, - 'group_by' => &$groupByAvailRoomSearch, - 'order_by' => &$orderByAvailRoomSearch, - 'order_way' => &$orderWayAvailRoomSearch, - 'params' => array( - 'id_hotel' => $idHotel, - 'id_product' => $idRoomType, - 'date_from' => $dateFrom, - 'date_to' => $dateTo - ) + Hook::exec('actionAvailRoomSearchSqlModifier', array( + 'select' => $selectAvailRoomSearch, + 'join' => &$joinAvailRoomSearch, + 'where' => &$whereAvailRoomSearch, + 'exclude_room_id' => &$excludeRoomId, + 'group_by' => &$groupByAvailRoomSearch, + 'order_by' => &$orderByAvailRoomSearch, + 'order_way' => &$orderWayAvailRoomSearch, + 'params' => array( + 'id_hotel' => $idHotel, + 'id_product' => $idRoomType, + 'date_from' => $dateFrom, + 'date_to' => $dateTo, + 'all_params' => $allParams ) - ); + )); $sql = $selectAvailRoomSearch; $sql .= ' FROM `'._DB_PREFIX_.'htl_room_information` AS ri'; $sql .= ' '.$joinAvailRoomSearch; $sql .= ' '.$whereAvailRoomSearch; + $sql .= ' AND ri.`id` NOT IN ('.implode(' UNION ', $excludeRoomId).')'; $sql .= ' '.$groupByAvailRoomSearch; $sql .= ' '.$orderByAvailRoomSearch; $sql .= ' '.$orderWayAvailRoomSearch; @@ -708,7 +784,19 @@ class HotelBookingDetail extends ObjectModel if ($QLO_SEARCH_TYPE == HotelBookingDetail::SEARCH_TYPE_OWS && $searchOccupancy) { $availableRoomTypes = $this->getAvailableRoomSatisfingOccupancy($searchOccupancy, $availableRoomTypes, $QLO_OWS_SEARCH_ALGO_TYPE); + + // segregating available and unavailable roomTypes $unavailableRoomTypes = $availableRoomTypes['unavailableRoomTypes']; + if ($unavailableRoomTypes) { + // Adding an id_status key to the unavailable rooms array to identify rooms unavailable due to unsatisfied occupancy search criteria. + // if in case we need to add multiple keys then we can use array union operator + // Instead of looping here, we can do this in the getavailableRoomSatisfingOccupancy function + foreach ($unavailableRoomTypes as $idProduct => $roomTypeDetail) { + foreach ($roomTypeDetail as $idRoom => $roomDetail) { + $unavailableRoomTypes[$idProduct][$roomDetail['id_room']]['id_status'] = HotelRoomInformation::STATUS_SEARCH_OCCUPANCY_UNSATISFIED; + } + } + } $availableRoomTypes = $availableRoomTypes['availableRoomTypes']; } @@ -915,29 +1003,30 @@ class HotelBookingDetail extends ObjectModel * 'idRoomType' => ..., * 'searchOccupancy' => ..., * 'allowedIdRoomTypes' => ..., + * 'hourlyBooking' => ..., + * 'allParams' => ..., * ); */ protected function getSearchPartiallyAvailRooms($params) { extract($params); - $sql1 = 'SELECT bd.`id_product`, bd.`id_room`, bd.`id_hotel`, bd.`id_customer`, bd.`booking_type`, bd.`id_status` AS booking_status, bd.`comment` AS `room_comment`, rf.`room_num`, bd.`date_from`, IF(bd.`id_status` = '. self::STATUS_CHECKED_OUT .', bd.`check_out`, bd.`date_to`) AS `date_to`, hrt.`max_adults` AS `max_adult`, hrt.`max_children`, hrt.`max_guests` AS `max_occupancy` + $sql = array(); + $sql[] = 'SELECT bd.`id_product`, bd.`id_room`, bd.`id_hotel`, bd.`id_customer`, bd.`booking_type`, bd.`id_status` AS booking_status, bd.`comment` AS `room_comment`, rf.`room_num`, bd.`date_from`, IF(bd.`id_status` = '. self::STATUS_CHECKED_OUT .', bd.`check_out`, bd.`date_to`) AS `date_to`, hrt.`max_adults` AS `max_adult`, hrt.`max_children`, hrt.`max_guests` AS `max_occupancy` FROM `'._DB_PREFIX_.'htl_booking_detail` AS bd INNER JOIN `'._DB_PREFIX_.'htl_room_information` AS rf ON (rf.`id` = bd.`id_room`) INNER JOIN `'._DB_PREFIX_.'htl_room_type` AS hrt ON (hrt.`id_product` = rf.`id_product`) - WHERE bd.`id_hotel`='.(int)$idHotel.' AND rf.`id_status` != '. HotelRoomInformation::STATUS_INACTIVE .' AND bd.`is_back_order` = 0 AND bd.`is_refunded` = 0 AND IF(bd.`id_status` = '. self::STATUS_CHECKED_OUT .', ( - (DATE_FORMAT(`check_out`, "%Y-%m-%d") > \''.pSQL($dateFrom).'\' AND DATE_FORMAT(`check_out`, "%Y-%m-%d") < \''.PSQL($dateTo).'\') AND ( - (bd.`date_from` <= \''.pSQL($dateFrom).'\' AND bd.`check_out` > \''.pSQL($dateFrom).'\' AND bd.`check_out` < \''.pSQL($dateTo).'\') OR - (bd.`date_from` > \''.pSQL($dateFrom).'\' AND bd.`date_from` < \''.pSQL($dateTo).'\' AND bd.`check_out` >= \''.pSQL($dateTo).'\') OR - (bd.`date_from` > \''.pSQL($dateFrom).'\' AND bd.`date_from` < \''.pSQL($dateTo).'\' AND bd.`check_out` > \''.pSQL($dateFrom).'\' AND bd.`check_out` < \''.pSQL($dateTo).'\') - ) + WHERE bd.`id_hotel`='.(int)$idHotel.' AND rf.`id_status` != '. HotelRoomInformation::STATUS_INACTIVE .' AND bd.`is_back_order` = 0 AND bd.`is_refunded` = 0 AND IF(bd.`id_status` = '. self::STATUS_CHECKED_OUT .', IF('.(int) $hourlyBooking.', 1, (DATE_FORMAT(`check_out`, "%Y-%m-%d") != DATE_FORMAT(\''.pSQL($dateFrom).'\', "%Y-%m-%d")) AND (`check_out` > \''.pSQL($dateFrom).'\' AND `check_out` <= \''.PSQL($dateTo).'\')) AND ( + (bd.`date_from` <= \''.pSQL($dateFrom).'\' AND bd.`check_out` > \''.pSQL($dateFrom).'\' AND bd.`check_out` < \''.pSQL($dateTo).'\') OR + (bd.`date_from` > \''.pSQL($dateFrom).'\' AND bd.`date_from` < \''.pSQL($dateTo).'\' AND bd.`check_out` >= \''.pSQL($dateTo).'\') OR + (bd.`date_from` > \''.pSQL($dateFrom).'\' AND bd.`date_from` < \''.pSQL($dateTo).'\' AND bd.`check_out` > \''.pSQL($dateFrom).'\' AND bd.`check_out` < \''.pSQL($dateTo).'\') ), ( (bd.`date_from` <= \''.pSQL($dateFrom).'\' AND bd.`date_to` > \''.pSQL($dateFrom).'\' AND bd.`date_to` < \''.pSQL($dateTo).'\') OR (bd.`date_from` > \''.pSQL($dateFrom).'\' AND bd.`date_from` < \''.pSQL($dateTo).'\' AND bd.`date_to` >= \''.pSQL($dateTo).'\') OR (bd.`date_from` > \''.pSQL($dateFrom).'\' AND bd.`date_from` < \''.pSQL($dateTo).'\' AND bd.`date_to` < \''.pSQL($dateTo).'\') )) AND IF('.(int)$idRoomType.' > 0, rf.`id_product` = '.(int)$idRoomType.', 1) AND rf.`id_product` IN ('.$allowedIdRoomTypes.')'; - $sql2 = 'SELECT hri.`id_product`, hrdd.`id_room`, hri.`id_hotel`, 0 AS `id_customer`, 0 AS `booking_type`, 0 AS `booking_status`, 0 AS `room_comment`, hri.`room_num`, hrdd.`date_from`, hrdd.`date_to`, hrt.`max_adults` AS `max_adult`, hrt.`max_children`, hrt.`max_guests` AS `max_occupancy` + $sql[] = 'SELECT hri.`id_product`, hrdd.`id_room`, hri.`id_hotel`, 0 AS `id_customer`, 0 AS `booking_type`, 0 AS `booking_status`, 0 AS `room_comment`, hri.`room_num`, hrdd.`date_from`, hrdd.`date_to`, hrt.`max_adults` AS `max_adult`, hrt.`max_children`, hrt.`max_guests` AS `max_occupancy` FROM `'._DB_PREFIX_.'htl_room_information` AS hri INNER JOIN `'._DB_PREFIX_.'htl_room_type` AS hrt ON (hrt.`id_product` = hri.`id_product`) INNER JOIN `'._DB_PREFIX_.'htl_room_disable_dates` AS hrdd ON (hrdd.`id_room_type` = hri.`id_product` AND hrdd.`id_room` = hri.`id`) @@ -947,7 +1036,20 @@ class HotelBookingDetail extends ObjectModel (hrdd.`date_from` > \''.pSQL($dateFrom).'\' AND hrdd.`date_from` < \''.pSQL($dateTo).'\' AND hrdd.`date_to` < \''.pSQL($dateTo).'\') ) AND IF('.(int)$idRoomType.' > 0, hri.`id_product` = '.(int)$idRoomType.', 1) AND hri.`id_product` IN ('.$allowedIdRoomTypes.')'; - $sql = $sql1.' UNION '.$sql2.' ORDER BY id_room ASC'; + Hook::exec('actionPartiallyAvailRoomSearchSqlModifier', array( + 'sql' => &$sql, + 'params' => array( + 'id_hotel' => $idHotel, + 'id_product' => $idRoomType, + 'date_from' => $dateFrom, + 'date_to' => $dateTo, + 'all_params' => $allParams + ) + )); + + $sql = implode(' UNION ', $sql); + $sql .= ' ORDER BY id_room ASC'; + $part_arr = Db::getInstance()->executeS($sql); // Get date wise available rooms @@ -1207,16 +1309,14 @@ class HotelBookingDetail extends ObjectModel } } else { // If all dates are not covered then move all partially available room types to unavailable - foreach ($partiallyAvailRooms as $roomDetail) { - if (!isset($unavailableRoomTypes[$roomDetail['id_product']][$roomDetail['id_room']])) { - $unavailableRoomTypes[$roomDetail['id_product']][$roomDetail['id_room']] = array( - 'id_room' => $roomDetail['id_room'], - 'id_product' => $roomDetail['id_product'], - 'id_hotel' => $roomDetail['id_hotel'], - 'room_num' => $roomDetail['room_num'], - 'room_comment' => '' - ); - } + foreach ($partiallyAvailRooms as $partAvailRoomDetail) { + $unavailableRoomTypes[$partAvailRoomDetail['id_product']][$partAvailRoomDetail['id_room']] = array( + 'id_room' => $partAvailRoomDetail['id_room'], + 'id_product' => $partAvailRoomDetail['id_product'], + 'id_hotel' => $partAvailRoomDetail['id_hotel'], + 'room_num' => $partAvailRoomDetail['room_num'], + 'room_comment' => '' + ); } $partiallyAvailRooms = array(); @@ -1246,11 +1346,46 @@ class HotelBookingDetail extends ObjectModel { extract($params); - $sql = 'SELECT bd.`id`, bd.`id_product`, bd.`id_room`, bd.`id_hotel`, bd.`id_customer`, bd.`booking_type`, bd.`id_status` AS booking_status, bd.`comment`, rf.`room_num`, bd.`date_from`, bd.`date_to` - FROM `'._DB_PREFIX_.'htl_booking_detail` AS bd - INNER JOIN `'._DB_PREFIX_.'htl_room_information` AS rf ON (rf.`id` = bd.`id_room`) - WHERE bd.`id_hotel`='.(int)$idHotel.' AND bd.`is_refunded` = 0 AND bd.`is_back_order` = 0 AND IF(bd.`id_status` = '. self::STATUS_CHECKED_OUT .', bd.`date_from` <= \''.pSQL($dateFrom).'\' AND bd.`check_out` >= \''.pSQL($dateTo).'\', bd.`date_from` <= \''.pSQL($dateFrom).'\' AND bd.date_to >= \''.pSQL($dateTo).'\') AND IF('.(int)$idRoomType.' > 0, rf.`id_product` = '.(int)$idRoomType.', 1) AND rf.`id_product` IN ('.$allowedIdRoomTypes.') - ORDER BY bd.`id_room` ASC'; + $selectBookedRoomSearch = 'SELECT `id`, `id_order`, `id_product`, `id_room`, `id_hotel`, `id_customer`, `booking_type`, `id_status` AS booking_status, `comment`, `room_num`, `date_from`, IF(`id_status` = '. self::STATUS_CHECKED_OUT.', `check_out`,`date_to`) AS `date_to`, `check_in`, `check_out`, `date_to` AS `booking_date_to`'; + $joinBookedRoomSearch = ''; + $whereBookedRoomSearch = 'WHERE `id_hotel` = '.(int)$idHotel.' AND `is_back_order` = 0 AND `is_refunded` = 0 AND IF(`id_status` = '. self::STATUS_CHECKED_OUT.', ( + (`date_from` <= \''.pSQL($dateFrom).'\' AND `check_out` > \''.pSQL($dateFrom).'\' AND `check_out` <= \''.PSQL($dateTo).'\') OR + (`date_from` >= \''.pSQL($dateFrom).'\' AND `check_out` > \''.pSQL($dateFrom).'\' AND `check_out` <= \''.pSQL($dateTo).'\') OR + (`date_from` >= \''.pSQL($dateFrom).'\' AND `date_from` < \''.pSQL($dateTo).'\' AND `check_out` >= \''.pSQL($dateTo).'\') OR + (`date_from` <= \''.pSQL($dateFrom).'\' AND `check_out` >= \''.pSQL($dateTo).'\') + ), ( + (`date_from` <= \''.pSQL($dateFrom).'\' AND `date_to` > \''.pSQL($dateFrom).'\' AND `date_to` <= \''.PSQL($dateTo).'\') OR + (`date_from` >= \''.pSQL($dateFrom).'\' AND `date_to` <= \''.pSQL($dateTo).'\') OR + (`date_from` >= \''.pSQL($dateFrom).'\' AND `date_from` < \''.pSQL($dateTo).'\' AND `date_to` >= \''.pSQL($dateTo).'\') OR + (`date_from` <= \''.pSQL($dateFrom).'\' AND `date_to` >= \''.pSQL($dateTo).'\') + )) AND IF('.(int)$idRoomType.' > 0, `id_product` = '.(int)$idRoomType.', 1) AND `id_product` IN ('.$allowedIdRoomTypes.')'; + $groupByBookedRoomSearch = ''; + $orderByBookedRoomSearch = 'ORDER BY `id_room`, `date_from`'; + $orderWayBookedRoomSearch = 'ASC'; + + Hook::exec('actionBookedRoomSearchSqlModifier', array( + 'select' => $selectBookedRoomSearch, + 'join' => &$joinBookedRoomSearch, + 'where' => &$whereBookedRoomSearch, + 'group_by' => &$groupByBookedRoomSearch, + 'order_by' => &$orderByBookedRoomSearch, + 'order_way' => &$orderWayBookedRoomSearch, + 'params' => array( + 'id_hotel' => $idHotel, + 'id_product' => $idRoomType, + 'date_from' => $dateFrom, + 'date_to' => $dateTo, + 'all_params' => $allParams + ) + )); + + $sql = $selectBookedRoomSearch; + $sql .= ' FROM `'._DB_PREFIX_.'htl_booking_detail`'; + $sql .= ' '.$joinBookedRoomSearch; + $sql .= ' '.$whereBookedRoomSearch; + $sql .= ' '.$groupByBookedRoomSearch; + $sql .= ' '.$orderByBookedRoomSearch; + $sql .= ' '.$orderWayBookedRoomSearch; $bookedRoomTypes = array(); if ($booked_rooms = Db::getInstance()->executeS($sql)) { @@ -1400,25 +1535,24 @@ class HotelBookingDetail extends ObjectModel * @param [date] $dateTo [End date of the booking] * * @return [int] [Returns number of days between two dates] - * @deprecated use hotelBookingDetail::getDays() instead + * @deprecated use HotelHelper::getNumberOfDays() instead */ public function getNumberOfDays($dateFrom, $dateTo) { - return self::getDays($dateFrom, $dateTo); - // $startDate = new DateTime($dateFrom); - // $endDate = new DateTime($dateTo); - // $daysDifference = $startDate->diff($endDate)->days; - - // return $daysDifference; + return HotelHelper::getNumberOfDays($dateFrom, $dateTo); } + /** + * + * @param [date] $dateFrom [Start date of the booking] + * @param [date] $dateTo [End date of the booking] + * + * @return [int] [Returns number of days between two dates] + * @deprecated use HotelHelper::getNumberOfDays() instead + */ public static function getDays($dateFrom, $dateTo) { - $startDate = new DateTime($dateFrom); - $endDate = new DateTime($dateTo); - $daysDifference = $startDate->diff($endDate)->days; - - return $daysDifference; + return HotelHelper::getNumberOfDays($dateFrom, $dateTo); } public function generateRoomOccupancyWeight($availRoomTypeCount, $totalOccupancy, $totalAdult, $totalChildren) @@ -1517,10 +1651,18 @@ class HotelBookingDetail extends ObjectModel $this->context = Context::getContext(); - $bookingParams['search_available'] = 1; - $bookingParams['search_partial'] = 0; - $bookingParams['search_booked'] = 0; - $bookingParams['search_unavai'] = 0; + if (!isset($bookingParams['search_available'])) { + $bookingParams['search_available'] = 1; + } + if (!isset($bookingParams['search_partial'])) { + $bookingParams['search_partial'] = 0; + } + if (!isset($bookingParams['search_booked'])) { + $bookingParams['search_booked'] = 0; + } + if (!isset($bookingParams['search_unavai'])) { + $bookingParams['search_unavai'] = 0; + } $bookingData = $this->getBookingData($bookingParams); diff --git a/modules/hotelreservationsystem/classes/HotelHelper.php b/modules/hotelreservationsystem/classes/HotelHelper.php index d44240626..dc442e32d 100644 --- a/modules/hotelreservationsystem/classes/HotelHelper.php +++ b/modules/hotelreservationsystem/classes/HotelHelper.php @@ -2730,11 +2730,7 @@ class HotelHelper if (isset($rooms[$roomType['value']])) { $roomType['children'] = $rooms[$roomType['value']]; } - $roomType['hint'] = 'This is Room type hint'; - $roomType['badge'] = array( - 'class' => 'badge-danger', - 'title' => 'Disabled' - ); + if ($previousElements) { $return[$roomType['id_hotel']][] = $roomType; } else { diff --git a/modules/hotelreservationsystem/classes/HotelRoomInformation.php b/modules/hotelreservationsystem/classes/HotelRoomInformation.php index f3c2b05af..d1f8dc2de 100644 --- a/modules/hotelreservationsystem/classes/HotelRoomInformation.php +++ b/modules/hotelreservationsystem/classes/HotelRoomInformation.php @@ -34,6 +34,9 @@ class HotelRoomInformation extends ObjectModel const STATUS_INACTIVE = 2; const STATUS_TEMPORARY_INACTIVE = 3; + const STATUS_SEARCH_LOS_UNSATISFIED = 4; + const STATUS_SEARCH_OCCUPANCY_UNSATISFIED = 5; + public static $definition = array( 'table' => 'htl_room_information', 'primary' => 'id', @@ -76,7 +79,7 @@ class HotelRoomInformation extends ObjectModel { if ($idRoom = $this->id) { // delete rooms from cart which are set inactive - if ($this->id_status == self::STATUS_INACTIVE) { + if ($this->id_status == HotelRoomInformation::STATUS_INACTIVE) { $objCartBookingData = new HotelCartBookingData(); if (!$objCartBookingData->deleteCartBookingData(0, 0, $idRoom)) { return false; @@ -138,25 +141,37 @@ class HotelRoomInformation extends ObjectModel public function getAllRoomStatus() { - $moduleInstance = Module::getInstanceByName('hotelreservationsystem'); - $status = array( 'STATUS_ACTIVE' => array( - 'id' => self::STATUS_ACTIVE, - 'status' => $moduleInstance->l('Active', 'hotelreservationsystem') + 'id' => HotelRoomInformation::STATUS_ACTIVE, + 'status' => self::getRoomStatusTitle(HotelRoomInformation::STATUS_ACTIVE) ), 'STATUS_INACTIVE' => array( - 'id' => self::STATUS_INACTIVE, - 'status' => $moduleInstance->l('Inactive', 'hotelreservationsystem') + 'id' => HotelRoomInformation::STATUS_INACTIVE, + 'status' => self::getRoomStatusTitle(HotelRoomInformation::STATUS_INACTIVE) ), 'STATUS_TEMPORARY_INACTIVE' => array( - 'id' => self::STATUS_TEMPORARY_INACTIVE, - 'status' => $moduleInstance->l('Temporarily Inactive', 'hotelreservationsystem') + 'id' => HotelRoomInformation::STATUS_TEMPORARY_INACTIVE, + 'status' => self::getRoomStatusTitle(HotelRoomInformation::STATUS_TEMPORARY_INACTIVE) ), ); return $status; } + public static function getRoomStatusTitle($idStatus) + { + $moduleInstance = Module::getInstanceByName('hotelreservationsystem'); + $status = array( + HotelRoomInformation::STATUS_ACTIVE => $moduleInstance->l('Active', 'hotelreservationsystem'), + HotelRoomInformation::STATUS_INACTIVE => $moduleInstance->l('Inactive', 'hotelreservationsystem'), + HotelRoomInformation::STATUS_TEMPORARY_INACTIVE => $moduleInstance->l('Temporarily Inactive', 'hotelreservationsystem'), + HotelRoomInformation::STATUS_SEARCH_LOS_UNSATISFIED => $moduleInstance->l('Length of stay restriction not satisfied', 'hotelreservationsystem'), + HotelRoomInformation::STATUS_SEARCH_OCCUPANCY_UNSATISFIED => $moduleInstance->l('Occupancy exceeds room capacity', 'hotelreservationsystem'), + ); + + return isset($status[$idStatus]) ? $status[$idStatus] : ''; + } + /** * [getHotelRoomInfoByProductId :: To get all rooms information belong to a room type(product) by product id] * @param [int] $id_product [Id of the product] diff --git a/modules/hotelreservationsystem/controllers/admin/AdminHotelRoomsBookingController.php b/modules/hotelreservationsystem/controllers/admin/AdminHotelRoomsBookingController.php index cc7edbc92..b1fea57e4 100644 --- a/modules/hotelreservationsystem/controllers/admin/AdminHotelRoomsBookingController.php +++ b/modules/hotelreservationsystem/controllers/admin/AdminHotelRoomsBookingController.php @@ -379,6 +379,7 @@ class AdminHotelRoomsBookingController extends ModuleAdminController 'occupancy_required_for_booking' => $occupancyRequiredForBooking, 'max_child_age' => Configuration::get('WK_GLOBAL_CHILD_MAX_AGE'), 'max_child_in_room' => Configuration::get('WK_GLOBAL_MAX_CHILD_IN_ROOM'), + 'link' => $this->context->link )); if (Configuration::get('PS_BACKOFFICE_SEARCH_TYPE') == HotelBookingDetail::SEARCH_TYPE_OWS) { diff --git a/modules/hotelreservationsystem/views/css/HotelReservationAdmin.css b/modules/hotelreservationsystem/views/css/HotelReservationAdmin.css index 5325c1198..91dd1825b 100644 --- a/modules/hotelreservationsystem/views/css/HotelReservationAdmin.css +++ b/modules/hotelreservationsystem/views/css/HotelReservationAdmin.css @@ -216,7 +216,13 @@ p.room_cat_data font-weight: 700; margin-bottom: 0px; } - +.status-info-tooltip { + position: relative; + display: inline-block; + left: 100%; + margin-left: -10px; + padding: 0px; +} .color_indicate { width: 10px; @@ -239,6 +245,7 @@ p.room_cat_data margin: 10px 0px; } + .cart-table-thead { border-bottom: 1px solid #555!important; @@ -279,7 +286,10 @@ p.room_cat_data font-size: 14px!important; font-weight: 600!important; } - +#htl_rooms_list table td { + padding-top: 10px; + padding-bottom: 10px; +} #room-status-tabs li { font-size: 14px; diff --git a/modules/hotelreservationsystem/views/js/admin/hotel_rooms_booking.js b/modules/hotelreservationsystem/views/js/admin/hotel_rooms_booking.js index e7a4d00cd..6cf0c7d5f 100644 --- a/modules/hotelreservationsystem/views/js/admin/hotel_rooms_booking.js +++ b/modules/hotelreservationsystem/views/js/admin/hotel_rooms_booking.js @@ -954,10 +954,56 @@ $(document).ready(function() { success: function(result) { if (result.success) { $(".htl_room_data_cont").html(result.data.stats_panel); + initstatstooltip(); } } }); } + initstatstooltip(); + + function initstatstooltip() + { + $(".htl_room_data_cont").find('.status-info-tooltip').tooltip({ + trigger : 'hover', + show: { + delay: 100, + }, + hide: { + delay: 300, + }, + open: function(event, ui) + { + if(event.buttons == 1 || event.buttons == 3){ + ui.tooltip.remove(); + } + + if (typeof(event.originalEvent) === 'undefined') { + return false; + } + + var $id = $(ui.tooltip).attr('id'); + + // close any lingering tooltips + if ($('div.ui-tooltip').not('#' + $id).length) { + return false; + } + + // ajax function to pull in data and add it to the tooltip goes here + }, + close: function(event, ui) + { + ui.tooltip.hover(function() { + $(this).stop(true).fadeTo(300, 1); + }, + function() { + $(this).fadeOut('300', function() + { + $(this).remove(); + }); + }); + } + }); + } var allotmentTypes = { auto: ALLOTMENT_AUTO, diff --git a/modules/hotelreservationsystem/views/templates/admin/hotel_rooms_booking/helpers/view/_partials/booking-rooms.tpl b/modules/hotelreservationsystem/views/templates/admin/hotel_rooms_booking/helpers/view/_partials/booking-rooms.tpl index 579eb756a..5783f4798 100644 --- a/modules/hotelreservationsystem/views/templates/admin/hotel_rooms_booking/helpers/view/_partials/booking-rooms.tpl +++ b/modules/hotelreservationsystem/views/templates/admin/hotel_rooms_booking/helpers/view/_partials/booking-rooms.tpl @@ -203,6 +203,7 @@ {l s='Room No.' mod='hotelreservationsystem'} {l s='Duration' mod='hotelreservationsystem'} + {l s='Order' mod='hotelreservationsystem'} {l s='Message' mod='hotelreservationsystem'} {l s='Allotment Type' mod='hotelreservationsystem'} {l s='Reallocate' mod='hotelreservationsystem'} @@ -216,6 +217,7 @@ {$booked_v['room_num']|escape:'htmlall':'UTF-8'} {hook h='displayRoomNumAfter' data=$booked_v key=$rm_dtl_k type='booked'} {/if} {dateFormat date=date('Y-m-d', strtotime($rm_dtl_v['date_from']))} - {dateFormat date=date('Y-m-d', strtotime($rm_dtl_v['date_to']))} + #{$rm_dtl_v['id_order']} {$rm_dtl_v['comment']|escape:'htmlall':'UTF-8'} {if $rm_dtl_v['booking_type'] == HotelBookingDetail::ALLOTMENT_AUTO}{l s='Auto Allotment' mod='hotelreservationsystem'}{elseif $rm_dtl_v['booking_type'] == HotelBookingDetail::ALLOTMENT_MANUAL}{l s='Manual Allotment' mod='hotelreservationsystem'}{/if} @@ -242,15 +244,29 @@ {l s='Room No.' mod='hotelreservationsystem'} + {l s='Status' mod='hotelreservationsystem'} + {l s='Duration' mod='hotelreservationsystem'} {l s='Message' mod='hotelreservationsystem'} {foreach from=$book_v['data']['unavailable'] key=unavai_k item=unavai_v} - - {$unavai_v['room_num']|escape:'htmlall':'UTF-8'} - {$unavai_v['room_comment']|escape:'htmlall':'UTF-8'} - + {foreach from=$unavai_v['detail'] key=rm_dtl_k item=unavail_dtl_v} + + {if $unavail_dtl_v@first} + {$unavai_v['room_num']|escape:'htmlall':'UTF-8'} + {/if} + {HotelRoomInformation::getRoomStatusTitle($unavail_dtl_v['id_status'])|escape:'htmlall':'UTF-8'} + + {if $unavail_dtl_v['date_from'] && $unavail_dtl_v['date_to']} + {dateFormat date=date('Y-m-d', strtotime($unavail_dtl_v['date_from']))} - {dateFormat date=date('Y-m-d', strtotime($unavail_dtl_v['date_to']))} + {else} + -- + {/if} + + {$unavail_dtl_v['room_comment']|escape:'htmlall':'UTF-8'} + + {/foreach} {/foreach} diff --git a/modules/hotelreservationsystem/views/templates/admin/hotel_rooms_booking/helpers/view/_partials/search-stats.tpl b/modules/hotelreservationsystem/views/templates/admin/hotel_rooms_booking/helpers/view/_partials/search-stats.tpl index 560836b5b..11690bc24 100644 --- a/modules/hotelreservationsystem/views/templates/admin/hotel_rooms_booking/helpers/view/_partials/search-stats.tpl +++ b/modules/hotelreservationsystem/views/templates/admin/hotel_rooms_booking/helpers/view/_partials/search-stats.tpl @@ -1,4 +1,7 @@
+
+ +
diff --git a/themes/hotel-reservation-theme/_partials/order-extra-services.tpl b/themes/hotel-reservation-theme/_partials/order-extra-services.tpl index 695b47c28..8a101f3cb 100644 --- a/themes/hotel-reservation-theme/_partials/order-extra-services.tpl +++ b/themes/hotel-reservation-theme/_partials/order-extra-services.tpl @@ -23,91 +23,83 @@
{if (isset($extraDemands) && $extraDemands) || (isset($additionalServices) && $additionalServices)} -
- -
- {if isset($extraDemands) && $extraDemands} -
-
-

{l s='Facilities chosen for this booking.'}

-
- {assign var=roomCount value=1} - {foreach $extraDemands as $roomDemand} -
-
- {l s='Room'} {$roomCount|string_format:'%02d'}  - ({if {$roomDemand['adults']} <= 9}0{$roomDemand['adults']}{else}{$roomDemand['adults']}{/if} {if $roomDemand['adults'] > 1}{l s='Adults'}{else}{l s='Adult'}{/if}{if $roomDemand['children'] > 0}, {if {$roomDemand['children']} <= 9}0{$roomDemand['children']}{else}{$roomDemand['children']}{/if} {if $roomDemand['children'] > 1}{l s='Children'}{else}{l s='Child'}{/if}{/if}) -
-
- {foreach $roomDemand['extra_demands'] as $demand} -
-
{$demand['name']|escape:'html':'UTF-8'}
+ +
+ {if isset($additionalServices) && $additionalServices} +
+ {assign var=roomCount value=1} + {foreach $additionalServices as $key => $roomAdditionalService} +
+
+ {l s='Room'} {$roomCount|string_format:'%02d'}  + ({if {$roomAdditionalService['adults']} <= 9}0{$roomAdditionalService['adults']}{else}{$roomAdditionalService['adults']}{/if} {if $roomAdditionalService['adults'] > 1}{l s='Adults'}{else}{l s='Adult'}{/if}{if $roomAdditionalService['children'] > 0}, {if {$roomAdditionalService['children']} <= 9}0{$roomAdditionalService['children']}{else}{$roomAdditionalService['children']}{/if} {if $roomAdditionalService['children'] > 1}{l s='Children'}{else}{l s='Child'}{/if}{/if}) +
+
+ {foreach $roomAdditionalService['additional_services'] as $additionalService} +
+
- - {if $useTax} - {displayPrice price="{$demand['total_price_tax_incl']|escape:'html':'UTF-8'}" currency=$objOrder->id_currency} - {else} - {displayPrice price="{$demand['total_price_tax_excl']|escape:'html':'UTF-8'}" currency=$objOrder->id_currency} - {/if} - + {$additionalService['name']|escape:'html':'UTF-8'} + {if $additionalService['allow_multiple_quantity']} + {l s='(Quantity: %s)' sprintf=[$additionalService['quantity']|string_format:'%02d']} + {/if}
- {/foreach} -
-
- {assign var=roomCount value=$roomCount+1} - {/foreach} -
- {/if} - - {if isset($additionalServices) && $additionalServices} -
-
-

{l s='Services chosen for this booking.'}

-
- {assign var=roomCount value=1} - {foreach $additionalServices as $key => $roomAdditionalService} -
-
- {l s='Room'} {$roomCount|string_format:'%02d'}  - ({if {$roomAdditionalService['adults']} <= 9}0{$roomAdditionalService['adults']}{else}{$roomAdditionalService['adults']}{/if} {if $roomAdditionalService['adults'] > 1}{l s='Adults'}{else}{l s='Adult'}{/if}{if $roomAdditionalService['children'] > 0}, {if {$roomAdditionalService['children']} <= 9}0{$roomAdditionalService['children']}{else}{$roomAdditionalService['children']}{/if} {if $roomAdditionalService['children'] > 1}{l s='Children'}{else}{l s='Child'}{/if}{/if}) -
-
- {foreach $roomAdditionalService['additional_services'] as $additionalService} -
-
-
- {$additionalService['name']|escape:'html':'UTF-8'} - {if $additionalService['allow_multiple_quantity']} - {l s='(Quantity: %s)' sprintf=[$additionalService['quantity']|string_format:'%02d']} - {/if} -
-
-
- - {if $useTax} - {displayPrice price=$additionalService['total_price_tax_incl']|escape:'html':'UTF-8' currency=$objOrder->id_currency} - {else} - {displayPrice price=$additionalService['total_price_tax_excl']|escape:'html':'UTF-8' currency=$objOrder->id_currency} - {/if} - -
+
+ + {if $useTax} + {displayPrice price=$additionalService['total_price_tax_incl']|escape:'html':'UTF-8' currency=$objOrder->id_currency} + {else} + {displayPrice price=$additionalService['total_price_tax_excl']|escape:'html':'UTF-8' currency=$objOrder->id_currency} + {/if} +
- {/foreach} -
+
+ {/foreach}
- {assign var=roomCount value=$roomCount+1} - {/foreach} +
+ {assign var=roomCount value=$roomCount+1} + {/foreach} +
+ {/if} + {if isset($extraDemands) && $extraDemands} +
+ {assign var=roomCount value=1} + {foreach $extraDemands as $roomDemand} +
+
+ {l s='Room'} {$roomCount|string_format:'%02d'}  + ({if {$roomDemand['adults']} <= 9}0{$roomDemand['adults']}{else}{$roomDemand['adults']}{/if} {if $roomDemand['adults'] > 1}{l s='Adults'}{else}{l s='Adult'}{/if}{if $roomDemand['children'] > 0}, {if {$roomDemand['children']} <= 9}0{$roomDemand['children']}{else}{$roomDemand['children']}{/if} {if $roomDemand['children'] > 1}{l s='Children'}{else}{l s='Child'}{/if}{/if}) +
+
+ {foreach $roomDemand['extra_demands'] as $demand} +
+
{$demand['name']|escape:'html':'UTF-8'}
+
+ + {if $useTax} + {displayPrice price="{$demand['total_price_tax_incl']|escape:'html':'UTF-8'}" currency=$objOrder->id_currency} + {else} + {displayPrice price="{$demand['total_price_tax_excl']|escape:'html':'UTF-8'}" currency=$objOrder->id_currency} + {/if} + +
+
+ {/foreach} +
+
+ {assign var=roomCount value=$roomCount+1} + {/foreach}
- {/if} -
+
+ {/if}
{/if}
diff --git a/themes/hotel-reservation-theme/css/global.css b/themes/hotel-reservation-theme/css/global.css index ab37bfe6a..cd790b7c6 100644 --- a/themes/hotel-reservation-theme/css/global.css +++ b/themes/hotel-reservation-theme/css/global.css @@ -8981,7 +8981,6 @@ a.open_rooms_extra_services_panel { margin-bottom: 18px;} */ #rooms_extra_services .room_demand_block { - margin-bottom: 15px; color: #333; font-size: 14px;} #rooms_extra_services .checkbox { diff --git a/themes/hotel-reservation-theme/css/order-confirmation.css b/themes/hotel-reservation-theme/css/order-confirmation.css index 654658b95..68c5a778d 100644 --- a/themes/hotel-reservation-theme/css/order-confirmation.css +++ b/themes/hotel-reservation-theme/css/order-confirmation.css @@ -113,12 +113,15 @@ } /* card-tabs - end */ +#rooms_extra_services .card-body{ + padding: 0px 18px; +} + #rooms_extra_services .nav-tabs { border-bottom: none; } #rooms_extra_services .nav-tabs > li { - width: 50%; text-align: center; margin: 0; } @@ -160,7 +163,6 @@ } #rooms_extra_services .tab-content .room_demands { - padding: 0 18px; margin-top: 20px; } @@ -190,4 +192,24 @@ #rooms_extra_services .nav-tabs > li.active:after { content: unset; -} \ No newline at end of file +} + +#rooms_extra_services .services_not_booked { + text-align: center; + margin: 30px 0px; + font-size: 14px; +} + +.price-info-tooltip-cont { + min-width: 180px; +} + +.price-info-tooltip-cont .list-row { + display: flex; + justify-content: space-between; + margin: 5px 0; +} + +.price-info-tooltip-cont .list-row p { + margin: 0; +} diff --git a/themes/hotel-reservation-theme/css/order-detail.css b/themes/hotel-reservation-theme/css/order-detail.css index a779fd760..1f188cedc 100644 --- a/themes/hotel-reservation-theme/css/order-detail.css +++ b/themes/hotel-reservation-theme/css/order-detail.css @@ -750,16 +750,6 @@ display: none; } -.ui-tooltip.price-tootip { - box-shadow: 0 2px 6px 0 rgb(0 0 0 / 20%); - background: #FFFFFF; - border: unset; - color: #333; - padding: 2px 10px; - max-height: 310px; - overflow-y: auto; -} - .price-info-tooltip-cont { min-width: 180px; } @@ -1013,12 +1003,15 @@ line-height: 24px; } +#popup-view-extra-services .card-body{ + padding: 0px 18px; +} + #popup-view-extra-services .nav-tabs { border-bottom: none; } #popup-view-extra-services .nav-tabs > li { - width: 50%; text-align: center; margin: 0; } @@ -1059,7 +1052,6 @@ } #popup-view-extra-services .tab-content .room_demands { - padding: 0 18px; margin-top: 20px; } @@ -1089,6 +1081,12 @@ align-items: center; } +#popup-view-extra-services .services_not_booked { + text-align: center; + margin: 30px 0px; + font-size: 14px; +} + /* Guest Tracking page styles - start */ .transform-account .card-text p { margin: 0; diff --git a/themes/hotel-reservation-theme/js/order-confirmation.js b/themes/hotel-reservation-theme/js/order-confirmation.js index 87175d20f..a150a491e 100644 --- a/themes/hotel-reservation-theme/js/order-confirmation.js +++ b/themes/hotel-reservation-theme/js/order-confirmation.js @@ -70,4 +70,41 @@ $(document).ready(function(){ }, }); }); -}); \ No newline at end of file + + initPriceTooltip(); +}); + +function initPriceTooltip() { + if ($('.order-price-info').length) { + $('.order-price-info').each(function () { + $(this).tooltip({ + content: $(this).closest('td').find('.price-info-container').html(), + items: 'span', + trigger: 'hover', + tooltipClass: 'price-tootip', + open: function (event, ui) { + if (typeof (event.originalEvent) === 'undefined') { + return false; + } + + var $id = $(ui.tooltip).attr('id'); + + // close any lingering tooltips + if ($('div.ui-tooltip').not('#' + $id).length) { + return false; + } + }, + close: function (event, ui) { + ui.tooltip.hover(function () { + $(this).stop(true).fadeTo(400, 1); + }, + function () { + $(this).fadeOut('400', function () { + $(this).remove(); + }); + }); + } + }); + }); + } +} \ No newline at end of file