if (typeof Bricks == 'undefined') {
    var Bricks = {};
}

Bricks.module = function(name, moduleDefinition) {
    var names = name.split('.');
    var modulePart = Bricks;
    for (var i = 0, length = names.length; i < length; i += 1) {
        if (typeof modulePart[names[i]] == 'undefined') {
            if (i === (length - 1)) {
                modulePart[names[i]] = moduleDefinition(jQuery);
            } else {
                modulePart[names[i]] = {};
            }
        } else if (i === (length - 1)) {
            jQuery.extend(modulePart[names[i]], moduleDefinition(jQuery));
        }
        modulePart = modulePart[names[i]];
    }
};

Bricks.some = function(collection, predicate) {
    if (typeof Array.some === 'function') {
        return collection.some(predicate);
    }
    for (var i = 0, length = collection.length; i < length; i += 1) {
        var value = collection[i];
        if (predicate(value, i, collection)) {
            return true;
        }
    }
    return false;
};

Bricks.every = function(collection, predicate) {
    if (typeof Array.every === 'function') {
        return collection.every(predicate);
    }
    for (var i = 0, length = collection.length; i < length; i += 1) {
        var value = collection[i];
        if (!predicate(value, i, collection)) {
            return false;
        }
    }
    return true;
};

Bricks.map = function(collection, callback) {
    if (typeof Array.map === 'function') {
        return collection.map(callback);
    }
    var ret = [];
    for (var i = 0, length = collection.length; i < length; i += 1) {
        var value = collection[i];
        ret.push(callback(value, i, collection));
    }
    return ret;
};

Bricks.filter = function(collection, predicate) {
    if (typeof Array.filter === 'function') {
        return collection.filter(predicate);
    }
    var ret = [];
    for (var i = 0, length = collection.length; i < length; i += 1) {
        var value = collection[i];
        if (predicate(value, i, collection)) {
            ret.push(value);
        }
    }
    return ret;
};

Bricks.indexBy = function(collection, keySelector) {
    var index = {}, key = null;
    if (!jQuery.isFunction(keySelector)) {
        throw new TypeError();
    }
    for (var i = 0, length = collection.length; i < length; i += 1) {
        var value = collection[i];
        key = keySelector.call(null, value, i, collection);
        if (typeof index[key] === 'undefined') {
            index[key] = [];
        }
        index[key].push(value);
    }
    return index;
};

Bricks.uniqueIndexBy = function(collection, keySelector) {
    var index = {}, key = null;
    if (!jQuery.isFunction(keySelector)) {
        throw new TypeError();
    }
    for (var i = 0, length = collection.length; i < length; i += 1) {
        var value = collection[i];
        key = keySelector.call(null, value, i, collection);
        if (typeof index[key] === 'undefined') {
            index[key] = value;
        } else {
            throw new "Key '" + key + "' already present in unique index.";
        }
    }
    return index;
};

Bricks.forEach = function(collection, callback) {
    var thisObject = arguments[2] || null;
    if (!jQuery.isFunction(callback)) {
        throw new TypeError();
    }
    if (typeof Array.forEach === 'function') {
        return collection.forEach(callback, thisObject);
    }
    for (var i = 0, length = collection.length; i < length; i += 1) {
        var value = collection[i];
        callback.call(thisObject, value, i, collection);
    }
};

Bricks.find = function(collection, predicate) {
    if (!jQuery.isFunction(predicate)) {
        throw new TypeError();
    }
    for (var i = 0, length = collection.length; i < length; i += 1) {
        if (predicate(collection[i])) {
            return i;
        }
    }
    return -1;
};

/**
 * Based on getPageSize() by quirksmode.com
 *
 * @return Object Return an object with page width, height and window width, height
*/
Bricks.getPageSize = function() {
    var xScroll, yScroll;
    if (window.innerHeight && window.scrollMaxY) {	
        xScroll = window.innerWidth + window.scrollMaxX;
        yScroll = window.innerHeight + window.scrollMaxY;
    } else if (document.body.scrollHeight > document.body.offsetHeight){ // all but Explorer Mac
        xScroll = document.body.scrollWidth;
        yScroll = document.body.scrollHeight;
    } else { // Explorer Mac...would also work in Explorer 6 Strict, Mozilla and Safari
        xScroll = document.body.offsetWidth;
        yScroll = document.body.offsetHeight;
    }
    var windowWidth, windowHeight;
    if (self.innerHeight) {	// all except Explorer
        if (document.documentElement.clientWidth) {
            windowWidth = document.documentElement.clientWidth; 
        } else {
            windowWidth = self.innerWidth;
        }
        windowHeight = self.innerHeight;
    } else if (document.documentElement && document.documentElement.clientHeight) { // Explorer 6 Strict Mode
        windowWidth = document.documentElement.clientWidth;
        windowHeight = document.documentElement.clientHeight;
    } else if (document.body) { // other Explorers
        windowWidth = document.body.clientWidth;
        windowHeight = document.body.clientHeight;
    }
    // for small pages with total height less then height of the viewport
    if (yScroll < windowHeight) {
        pageHeight = windowHeight;
    } else { 
        pageHeight = yScroll;
    }
    // for small pages with total width less then width of the viewport
    if (xScroll < windowWidth) {	
        pageWidth = xScroll;
    } else {
        pageWidth = windowWidth;
    }

    return {
        pageWidth: pageWidth, 
        pageHeight: pageHeight, 
        windowWidth: windowWidth, 
        windowHeight: windowHeight
    };
};
/**
  * Based on getPageScroll() by quirksmode.com
  *
  * @return Object Return an object with x,y page scroll values.
  */
Bricks.getPageScroll = function() {
    var xScroll, yScroll;
    if (self.pageYOffset) {
        yScroll = self.pageYOffset;
        xScroll = self.pageXOffset;
    } else if (document.documentElement && document.documentElement.scrollTop) {	 // Explorer 6 Strict
        yScroll = document.documentElement.scrollTop;
        xScroll = document.documentElement.scrollLeft;
    } else if (document.body) {// all other Explorers
        yScroll = document.body.scrollTop;
        xScroll = document.body.scrollLeft;
    }
    return {
        xScroll: xScroll,
        yScroll: yScroll
    };
};

Bricks.log = function(message) {
    if (window.console && window.console.log) {
        window.console.log(message);
    }
};

Bricks.toInt = function (value) {
    var defaultValue = (arguments.length == 2 ? arguments[1] : null);
    var intValue;
    if (jQuery.trim(value) === "0") return 0;
    if (/^[1-9][0-9]*$/.test(jQuery.trim(value))) {
        intValue = parseInt(jQuery.trim(value), 10);
        if (!isNaN(intValue)) {
            return intValue;
        }
    }
    return defaultValue;
};

Bricks.Keys = {
    LeftArrow: 37,
    UpArrow: 38,
    RightArrow: 39,
    DownArrow: 40,
    Return: 13,
    Escape: 27,
    Tab: 9,
    BackSpace: 8,
    Delete: 46
};

Bricks.module("Html", function($) {

    var formatNumber = function(amount, roundToDecimal) {
        var options = { decimalSeparator: ',', groupSeparator: '.', currency: null };
        options = $.extend(options, arguments[2] || {});

        if (typeof amount !== 'number') {
            return amount;
        }

        amount = amount.toFixed(roundToDecimal);

        var nonDecimals = amount.toString().replace(/\.\d+$/, "");

        var decimals = "";
        for (var i = 0; i < roundToDecimal; i += 1) {
            decimals += "0";
        }

        if (amount.toString().indexOf('.') > -1) {
            decimals = amount.toString().replace(/^[^\.]+\./, "");
            for (var i = decimals.length; i < roundToDecimal; i += 1) {
                decimals += "0";
            }
        }

        decimals = decimals.substring(0, roundToDecimal);

        var formattedNumber = "";
        while (nonDecimals.length) {
            if (nonDecimals.length > 3) {
                formattedNumber = nonDecimals.substring(nonDecimals.length - 3) + formattedNumber;
                nonDecimals = nonDecimals.substring(0, nonDecimals.length - 3);
                if (nonDecimals === "-") {
                    formattedNumber = "-" + formattedNumber;
                    nonDecimals = "";
                } else if (nonDecimals.length) {
                    formattedNumber = options.groupSeparator + formattedNumber;
                }
            } else {
                formattedNumber = nonDecimals + formattedNumber;
                nonDecimals = "";
            }
        }
        if (options.currency) {
            return options.currency + ' ' + formattedNumber + options.decimalSeparator + decimals;
        }
        return formattedNumber + options.decimalSeparator + decimals;
    };

    var makePrice = function(displayPrice) {
        var displayNormalPrice = arguments[1] || null;
        var showBeforePrice = arguments[2] || null;
        var bookingUrl = arguments[3] || null;

        var html = "";
        html += '<div class="bricks-lodging-price">';
        if (showBeforePrice) {
            html += '<div class="bricks-before-price">' + displayNormalPrice + '</div>';
        }
        if (bookingUrl) {
            html += '<div class="bricks-price"><a href="' + bookingUrl + '">' + displayPrice + '</a></div>';
        } else {
            html += '<div class="bricks-price">' + displayPrice + '</div>';
        }
        html += '</div>';
        return html;
    };

    var cssValue = function(value) {
        if (/^\d+px$/.test(value)) {
            return parseInt(value.replace(/px$/, ''), 10);
        }
        return 0;
    };

    var totalWidth = function(elem) {
        var width = elem.width();
        var widthModifiers = ['margin-left', 'border-left', 'padding-left', 'padding-right', 'border-right', 'margin-right'];
        Bricks.forEach(widthModifiers, function(widthModifier) {
            width += cssValue(elem.css(widthModifier));
        });
        return width;
    };

    var totalHeight = function(elem) {
        var height = elem.height();
        var heightModifiers = ['margin-top', 'border-top', 'padding-top', 'padding-bottom', 'border-bottom', 'margin-bottom'];
        Bricks.forEach(heightModifiers, function(heightModifier) {
            height += cssValue(elem.css(heightModifier));
        });
        return height;
    };

    var printInNewWindow = function(elem) {
        var options = arguments.length == 2 ? arguments[1] : {};
        var width = options.width || 750;
        var height = options.height || 400;
        var title = options.title || 'Print';
        var printWindow = window.open('', '_blank', 'width=' + width + ',height=' + height + ',scrollbars=yes,resizable=yes');

        if (options.doctype) {
            printWindow.document.writeln(options.doctype);
        }
        printWindow.document.writeln('<html>');
        printWindow.document.writeln('<head>');
        printWindow.document.writeln('<title>' + title + '</title>');
        if (options.stylesheetUrl) {
            printWindow.document.writeln('<link href="' + options.stylesheetUrl + '" type="text/css" rel="stylesheet" />');
        }
        if (options.styles) {
            printWindow.document.writeln('<style type="text/css">');
            printWindow.document.writeln(options.styles);
            printWindow.document.writeln('</style>');
        }
        printWindow.document.writeln('</head>');
        printWindow.document.writeln('<body>');
        if (options.containerId) {
            printWindow.document.writeln('<div id="' + options.containerId + '">');
        }
        printWindow.document.writeln($(elem).html());
        if (options.containerId) {
            printWindow.document.writeln('</div>');
        }
        printWindow.document.writeln('</body>');
        printWindow.document.writeln('</html>');
        printWindow.document.close();
        setTimeout(function() { printWindow.print(); }, 1000);
    };

    return {
        makePrice: makePrice,
        totalWidth: totalWidth,
        totalHeight: totalHeight,
        formatNumber: formatNumber,
        cssValue: cssValue,
        printInNewWindow: printInNewWindow
    };

});

Bricks.module("Dates", function($) {

    var Weekdays = { "Sunday": 0, "Monday": 1, "Tuesday": 2, "Wednesday": 3, "Thursday": 4, "Friday": 5, "Saturday": 6 };

    var days = function(days) {
        return days * 24 * 60 * 60 * 1000;
    };

    var weeks = function(weeks) {
        return weeks * days(7);
    }

    var weekdayName = function(date) {
        var names = ["sunday", "monday", "tuesday", "wednesday", "thursday", "friday", "saturday"];
        return names[date.getDay()];
    };

    var firstDayInMonth = function(date) {
        return new Date(date.getFullYear(), date.getMonth(), 1);
    };

    var lastDayInMonth = function(date) {
        var nextMonth;

        if (date.getMonth() == 11) {
            nextMonth = new Date(date.getFullYear() + 1, 0, 1);
        } else {
            nextMonth = new Date(date.getFullYear(), date.getMonth() + 1, 1);
        }

        return new Date(nextMonth.getTime() - days(1));
    };

    var nextWeekday = function(weekday) {
        var options = arguments.length == 2 ? arguments[1] : {};
        var skipToday = typeof options.skipToday !== 'undefined' ? options.skipToday : false;
        var today = new Date();
        var date = new Date(today.getFullYear(), today.getMonth(), today.getDate());
        if (skipToday) {
            date = addDays(date, 1);
        }
        while (date.getDay() != weekday) {
            date = addDays(date, 1);
        }
        return date;
    };

    var addDays = function(date, daysCount) {
        return new Date(date.getTime() + days(daysCount));
    };

    var addMonths = function(date, monthCount) {
        var newDate = new Date(date.getTime());
        var direction = (monthCount < 0 ? -1 : 1);
        for (var i = 0; i < Math.abs(monthCount); i += 1) {
            if (direction === 1 && newDate.getMonth() === 11) {
                newDate = new Date(newDate.getFullYear() + 1, 0, 1);
            } else if (direction === -1 && newDate.getMonth() === 0) {
                newDate = new Date(newDate.getFullYear() - 1, 11, 1);
            } else {
                newDate = new Date(newDate.getFullYear(), newDate.getMonth() + direction, 1);
            }
        }
        var lastDay = lastDayInMonth(newDate);
        if (lastDay.getDate() < date.getDate()) {
            return lastDay;
        }
        return new Date(newDate.getFullYear(), newDate.getMonth(), date.getDate());
    };

    var diffDays = function(fromDate, toDate) {
        var diff = toDate.getTime() - fromDate.getTime();
        return diff / days(1);
    };

    var zeroPad = function(number) {
        if (number < 10) {
            return "0" + number.toString();
        }
        return number.toString();
    };

    var toQueryStringDate = function(date) {
        return zeroPad(date.getMonth() + 1) + '/' + zeroPad(date.getDate()) + '/' + date.getFullYear();
    };

    var fromQueryStringDate = function(qsDate) {
        var parts = qsDate.split('/');
        if (parts.length === 3) {
            try {
                var month = parseInt(parts[0].replace(/^0/, ''), 10) - 1;
                var day = parseInt(parts[1].replace(/^0/, ''), 10);
                var year = parseInt(parts[2], 10);
                return new Date(year, month, day);
            } catch (ex) {
                // Pass
            }
        }
        return null;
    };

    var fromJsonDate = function(jsonDate) {
        if ((jsonDate == null) || (typeof (jsonDate.getFullYear) === 'function') || (typeof (jsonDate) !== 'string')) {
            return jsonDate;
        }
        return eval(jsonDate.replace(/^\/Date\((-?\d+)\)\/$/i, "new Date($1)"));
    };

    return {
        Weekdays: Weekdays,
        days: days,
        weeks: weeks,
        weekdayName: weekdayName,
        nextWeekday: nextWeekday,
        firstDayInMonth: firstDayInMonth,
        lastDayInMonth: lastDayInMonth,
        addDays: addDays,
        addMonths: addMonths,
        diffDays: diffDays,
        zeroPad: zeroPad,
        toQueryStringDate: toQueryStringDate,
        fromQueryStringDate: fromQueryStringDate,
        fromJsonDate: fromJsonDate
    };
});

Bricks.module("Items", function($) {

    var create = function(availableItems, bookingTotalPrice, currency) {
        var container = null;
        var selectedItems = arguments.length === 4 ? arguments[3] : [];

        var getItemId = function(elem) {
            var id = elem.attr('id');
            if (/^itemQuantity_\d+$/.test(id)) {
                return parseInt(id.replace(/^itemQuantity_/, ''), 10);
            }
            return null;
        };

        var getItem = function(itemId) {
            var items = Bricks.filter(availableItems, function(item) { return item.id === itemId });
            return items.length === 1 ? items[0] : null;
        };

        var setSelectedItem = function(item, quantity) {
            if (Bricks.every(selectedItems, function(selectedItem) { return selectedItem.id !== item.id; })) {
                selectedItems.push(item);
                selectedItems[selectedItems.length - 1].quantity = quantity;
            } else {
                for (var i = 0, length = selectedItems.length; i < length; i += 1) {
                    if (selectedItems[i].id === item.id) {
                        selectedItems[i].quantity = quantity;
                    }
                }
            }
        };

        var calculateTotal = function() {
            var totalPrice = bookingTotalPrice;
            Bricks.forEach(selectedItems, function(item) {
                totalPrice += item.unitSellPrice * item.quantity;
            });
            return totalPrice;
        };

        var calculateItemPrice = function(quantitySelector) {
            var tr = quantitySelector.closest('tr');
            try {
                var quantity = parseInt(quantitySelector.val(), 10);
                if (quantitySelector.is(':checkbox')) {
                    quantity = quantitySelector.attr('checked') ? quantitySelector.val() : 0;
                }
                var item = getItem(getItemId(quantitySelector));
                if (item) {
                    setSelectedItem(item, quantity);
                    $('.bricks-items-totalprice').html(Bricks.Html.formatNumber(calculateTotal(), 2, { currency: currency }));
                    tr.find('.bricks-price-column').html(Bricks.Html.formatNumber(item.unitSellPrice * quantity, 2, { currency: currency }));
                }
            } catch (ex) {
            }
        };

        var init = function(itemsContainer) {
            container = itemsContainer;
            container.find('.bricks-quantity-selector').live('change', function() { calculateItemPrice($(this)); }).each(function() { calculateItemPrice($(this)); });
        };

        return {
            init: init
        };
    };

    return {
        create: create
    };

});
Bricks.module("Search", function($) {

    var create = function(arrivalDateDayListId, arrivalDateMonthYearListId) {
        var container = null;

        var makeDayOptions = function(date, maxDay) {
            var html = '';
            for (var i = 1; i <= maxDay; i += 1) {
                html += '<option value="' + Bricks.Dates.zeroPad(date.getDate()) + '" class="' + Bricks.Dates.weekdayName(date) + '">' + date.getDate() + '</options>';
                date = new Date(date.getTime() + Bricks.Dates.days(1));
            }
            return html
        };

        var adjustDayList = function(monthYear) {
            var month = parseInt(monthYear.substr(0, 2).replace(/^0/, ''), 10);
            var year = parseInt(monthYear.substr(3), 10);
            var firstDayInMonth = new Date(year, month - 1, 1);
            var lastDayInMonth = Bricks.Dates.lastDayInMonth(firstDayInMonth);
            var selectedDay = $(container).find("#" + arrivalDateDayListId).val();
            $(container).find("#" + arrivalDateDayListId).html(makeDayOptions(firstDayInMonth, lastDayInMonth.getDate()));
            $(container).find("#" + arrivalDateDayListId).val(selectedDay);
        };

        var init = function(controlContainer, selectedDay, selectedMonthYear) {
            container = controlContainer;
            $(container).find('#' + arrivalDateMonthYearListId).val(selectedMonthYear);            
            adjustDayList(
                $(container).find("#" + arrivalDateMonthYearListId).change(function() {
                    adjustDayList($(this).val());
                }).val()
            );
            $(container).find("#" + arrivalDateDayListId).val(selectedDay);
        };

        return {
            init: init
        };
    };

    return {
        create: create
    };
});
Bricks.module("Lodging", function($) {

    var create = function(languageId) {

        var lodgingNames = null;
        var streetNames = null;

        var getLodgingNames = function(callback) {
            if (lodgingNames == null) {
                $.post('/BricksAjax.axd?controller=lodging&action=lodgingnames', { lan: languageId }, function(data) {
                    lodgingNames = data;
                    callback(lodgingNames);
                }, 'json');
            } else {
                callback(lodgingNames);
            }
        };

        var getStreetNames = function(callback) {
            if (streetNames == null) {
                $.post('/BricksAjax.axd?controller=lodging&action=streetnames', { lan: languageId }, function(data) {
                    streetNames = data;
                    callback(streetNames);
                }, 'json');
            } else {
                callback(streetNames);
            }
        };

        return {
            getLodgingNames: getLodgingNames,
            getStreetNames: getStreetNames
        };
    };

    return {
        create: create
    };
});
Bricks.module("Calendar", function($) {

    var toInvariantDateString = function(date) {
        return date.getFullYear() + '-' + Bricks.Dates.zeroPad(date.getMonth() + 1) + '-' + Bricks.Dates.zeroPad(date.getDate());
    };

    var create = function(searchContext, bookingOptions, options) {
        var container = null;
        if (typeof options.visible === 'undefined') options.visible = true;
        var errorPanel = typeof (options.errorPanel) == 'function' ? options.errorPanel : function() { };
        var loadingPanel = typeof (options.loadingPanel) == 'function' ? options.loadingPanel : function() { };

        var fixDatesOnBookingOptions = function(bookingOptions) {
            // Convert .Net json dates to javascript dates
            return Bricks.map(bookingOptions, function(bookingOption) {
                bookingOption.arrivalDate = Bricks.Dates.fromJsonDate(bookingOption.arrivalDate);
                bookingOption.departureDate = Bricks.Dates.fromJsonDate(bookingOption.departureDate);
                bookingOption.dates = Bricks.map(bookingOption.dates, function(date) { return Bricks.Dates.fromJsonDate(date); });
                return bookingOption;
            });
        }
        bookingOptions = fixDatesOnBookingOptions(bookingOptions);

        var findBookingOption = function(arrivalDateStr) {
            var bookingOption = Bricks.filter(bookingOptions, function(bookingOption) { return (toInvariantDateString(bookingOption.arrivalDate) === arrivalDateStr); });
            if (bookingOption.length === 1) {
                return bookingOption[0];
            }
            return null;
        };

        var getDates = function(arrivalDateStr) {
            var bookingOption = findBookingOption(arrivalDateStr);
            if (bookingOption) {
                return Bricks.map(bookingOption.dates, function(date) { return toInvariantDateString(date); });
            }
            return [];
        };

        var updateCalendars = function(data) {
            loadingPanel('hide');
            errorPanel('hide');
            if (!data.error) {
                container.find('.bricks-calendar-month').hide().remove();
                container.prepend(data.html);
                container.find('.bricks-calendar-month').fadeIn('fast');
                bookingOptions = fixDatesOnBookingOptions(data.bookingOptions);
            } else {
                errorPanel('show');
            }
        };

        var forward = function(monthsToPage) {
            searchContext.arrivalDate = Bricks.Dates.addMonths(searchContext.arrivalDate, monthsToPage);
            loadingPanel('show');
            $.post('/BricksAjax.axd?controller=calendar&action=listmonths', $.extend({ months: options.monthsInCalendar, nextpageurl: options.nextPageUrl, visible: options.visible, weekdays: options.weekdays, optimize: options.optimize }, searchContext.values()), function(data) {
                updateCalendars(data);
            }, 'json');
        };

        var back = function(monthsToPage) {
            searchContext.arrivalDate = Bricks.Dates.addMonths(searchContext.arrivalDate, -monthsToPage);
            loadingPanel('show');
            $.post('/BricksAjax.axd?controller=calendar&action=listmonths', $.extend({ months: options.monthsInCalendar, nextpageurl: options.nextPageUrl, visible: options.visible, weekdays: options.weekdays, optimize: options.optimize }, searchContext.values()), function(data) {
                updateCalendars(data);
            }, 'json');
        };

        var update = function(newSearchContext) {
            searchContext = newSearchContext;
            loadingPanel('show');
            $.post('/BricksAjax.axd?controller=calendar&action=listmonths', $.extend({ months: options.monthsInCalendar, nextpageurl: options.nextPageUrl, visible: options.visible, weekdays: options.weekdays, optimize: options.optimize }, searchContext.values()), function(data) {
                updateCalendars(data);
            }, 'json');
        };

        var getSearchContext = function() {
            return searchContext.copy();
        };

        var init = function(calendarContainer) {
            container = calendarContainer;
            var options = arguments[1] || {};
            var onShowBookingOption = options['onShowBookingOption'] || function() { };
            if (typeof onShowBookingOption !== 'function') onShowBookingOption = function() { };
            var onShowUnavailable = options['onShowUnavailable'] || function() { };
            if (typeof onShowUnavailable !== 'function') onShowUnavailable = function() { };
            var onHideLayer = options['onHideLayer'] || function() { };
            if (typeof onHideLayer !== 'function') onHideLayer = function() { };
            var onBookingOptionClick = options['onBookingOptionClick'] || function() { };
            if (typeof onBookingOptionClick !== 'function') onBookingOptionClick = function() { };

            // Free days
            container.find('.bricks-calendar-free').live('mouseover', function(event) {
                var date = $(this).attr('data-date');
                var bookingOption = findBookingOption(date);
                if (bookingOption) {
                    onShowBookingOption($(this), bookingOption);
                }
                var datesToSelect = getDates(date);
                for (var i = 0, length = datesToSelect.length; i < length; i += 1) {
                    container.find('.bricks-calendar-free[data-date=' + datesToSelect[i] + '], .bricks-calendar-changeday[data-date=' + datesToSelect[i] + ']').addClass('bricks-calendar-selected');
                }
            }).live('mouseout', function(event) {
                container.find('.bricks-calendar-selected').removeClass('bricks-calendar-selected');
                onHideLayer();
            });

            // Change days
            container.find('.bricks-calendar-changeday, .bricks-calendar-option').live('mouseover', function(event) {
                var date = $(this).attr('data-date');
                var bookingOption = findBookingOption(date);
                if (bookingOption) {
                    onShowBookingOption($(this), bookingOption);
                } else {
                    onShowUnavailable($(this));
                }
                var datesToSelect = getDates(date);
                for (var i = 0, length = datesToSelect.length; i < length; i += 1) {
                    container.find('.bricks-calendar-free[data-date=' + datesToSelect[i] + '], .bricks-calendar-changeday[data-date=' + datesToSelect[i] + ']').addClass('bricks-calendar-selected');
                }
            }).live('mouseout', function(event) {
                container.find('.bricks-calendar-selected').removeClass('bricks-calendar-selected');
                onHideLayer();
            });

            container.find('.bricks-calendar-free, .bricks-calendar-changeday, .bricks-calendar-option').live('click', function(event) {
                var date = $(this).attr('data-date');
                var bookingOption = findBookingOption(date);
                if (bookingOption) {
                    onBookingOptionClick(event, $(this), bookingOption);
                    container.find('.bricks-calendar-selected').removeClass('bricks-calendar-selected');
                    window.location.href = bookingOption.bookingUrl;
                }
            });
        };

        return {
            init: init,
            forward: forward,
            back: back,
            update: update,
            getSearchContext: getSearchContext
        };
    };

    return {
        create: create
    };
});
Bricks.module("Navigator", function($) {

    var getUserLanguages = function(callback) {
        $.post('/BricksAjax.axd?controller=browserheader&action=listlanguages', {}, function(languages) {
            callback(Bricks.map(languages, function(language) {
                var separatorIndex = language.indexOf(';');
                if (separatorIndex > -1) {
                    return language.substring(0, separatorIndex).toLowerCase();
                }
                return language.toLowerCase();
            }));
        }, 'json');
    };

    var createCookie = function(name, value, days) {
        if (days) {
            var date = new Date();
            date.setTime(date.getTime() + (days * 24 * 60 * 60 * 1000));
            var expires = "; expires=" + date.toGMTString();
        }
        else var expires = "";
        document.cookie = name + "=" + value + expires + "; path=/";
    }

    var readCookie = function(name) {
        var nameEQ = name + "=";
        var ca = document.cookie.split(';');
        for (var i = 0; i < ca.length; i++) {
            var c = ca[i];
            while (c.charAt(0) == ' ') c = c.substring(1, c.length);
            if (c.indexOf(nameEQ) == 0) return c.substring(nameEQ.length, c.length);
        }
        return null;
    }

    var eraseCookie = function(name) {
        createCookie(name, "", -1);
    }

    return {
        getUserLanguages: getUserLanguages,
        createCookie: createCookie,
        readCookie: readCookie,
        eraseCookie: eraseCookie
    };
});
Bricks.module("SearchBox", function($) {

    function SearchBoxData() {
        var self = this;

        this.countries = function() {
            var result = [];
            Bricks.forEach(self.locations, function(location) {
                if (location.level == 0) {
                    result.push(location);
                }
            });
            return result;
        };
    }

    var create = function(languageId) {

        var getData = function(callback) {
            $.post('/BricksAjax.axd?controller=searchbox&action=getdata', { lan: languageId }, function(data) {
                if ($.isArray(data.facilities) && $.isArray(data.locations)) {
                    var searchBoxData = new SearchBoxData();
                    callback($.extend(searchBoxData, data));
                }
            }, 'json');
        };

        return {
            getData: getData
        };
    };

    return {
        create: create
    };
});
Bricks.module("Validation", function ($) {

    var error = function (elem, errorMessage) {
        return { elem: elem, message: errorMessage };
    };

    var required = function (elem, errorMessage) {
        var dependent = (arguments.length == 3) ? arguments[2] : function () { return null; };
        if (elem.attr('data-default-text')) {
            if (Bricks.DefaultText.val(elem) !== '') {
                return dependent();
            } else {
                return { elem: elem, message: errorMessage };
            }
        }
        return (elem.val() != '') ? dependent() : { elem: elem, message: errorMessage };
    };

    var numeric = function (elem, errorMessage) {
        var dependent = (arguments.length == 3) ? arguments[2] : function () { return null; };
        var pattern = /^ *[1-9][0-9]* *$/;
        var value;
        if (pattern.test(elem.val())) {
            value = parseInt($.trim(elem.val()), 10);
            return (!isNaN(value)) ? dependent() : { elem: elem, message: errorMessage };
        }
        return { elem: elem, message: errorMessage };
    };

    var range = function (elem, minValue, maxValue, errorMessage) {
        var dependent = (arguments.length == 5) ? arguments[4] : function () { return null; };
        var value = parseInt($.trim(elem.val()), 10);
        if (!isNaN(value)) {
            return (minValue <= value && value <= maxValue) ? dependent() : { elem: elem, message: errorMessage };
        }
        return { elem: elem, message: errorMessage };
    };

    var checked = function (elem, errorMessage) {
        var dependent = (arguments.length == 3) ? arguments[2] : function () { return null; };
        if (elem.attr('checked')) {
            return dependent();
        }
        return { elem: elem, message: errorMessage };
    };

    var same = function (elemA, elemB, errorMessage) {
        var dependent = (arguments.length == 4) ? arguments[3] : function () { return null; };
        if (elemA.val() === elemB.val()) {
            return dependent();
        }
        return { elem: elemA, message: errorMessage };
    };

    var email = function (elem, errorMessage) {
        var dependent = (arguments.length == 3) ? arguments[2] : function () { return null; };
        var isEmail = /^[^@]+@\w+([-.]\w+)*\.\w+([-.]\w+)*$/i;
        if (isEmail.test(elem.val())) {
            return dependent();
        }
        return { elem: elem, message: errorMessage };
    };

    var clearErrorMarkers = function () {
        $('.bricks-error-marker').remove();
    };

    var addErrorMarker = function (elem, errorMarker) {
        if (!elem.next().hasClass('bricks-error-marker')) {
            elem.after('<span class="bricks-error-marker">' + errorMarker + '</span>');
        }
    };

    var removeErrorMarker = function (elem) {
        if (elem.next().hasClass('bricks-error-marker')) {
            elem.next().remove();
        }
    };

    return {
        error: error,
        required: required,
        numeric: numeric,
        range: range,
        checked: checked,
        email: email,
        same: same,
        clearErrorMarkers: clearErrorMarkers,
        addErrorMarker: addErrorMarker,
        removeErrorMarker: removeErrorMarker
    };

});
Bricks.module("LodgingList", function($) {

    var create = function() {

        var init = function(container, options) {
            if (arguments.length == 1) {
                options = {};
            }
            var applyBackgroundColors = typeof (options.applyBackgroundColors) === 'boolean' ? options.applyBackgroundColors : true;
            var applyBorderColors = typeof (options.applyBorderColors) === 'boolean' ? options.applyBorderColors : true;

            $(container).find('.bricks-lodging-listitem a').click(function(event) {
                event.stopImmediatePropagation();
            });

            $(container).find('.bricks-lodging-listitem').click(function(event) {
                event.preventDefault();
                var url = $(this).attr('data-url');
                window.location.href = url;
                return false;
            }).mouseover(function(event) {
                $(this).addClass('bricks-mouseover');
            }).mouseout(function(event) {
                $(this).removeClass('bricks-mouseover');
            });

            if (applyBackgroundColors || applyBorderColors) {
                $(container).find('.bricks-seasonprice-colorbox').each(function() {
                    if (applyBackgroundColors) {
                        jQuery(this).css('backgroundColor', jQuery(this).attr('data-color'));
                    }
                    if (applyBorderColors) {
                        jQuery(this).css('borderColor', jQuery(this).attr('data-color'));
                    }
                });
            }
        };

        return {
            init: init
        };
    };

    return {
        create: create
    };
});
Bricks.module("ViewLodging", function($) {

    var create = function() {
        var preloadedImages = false;

        var makeLargeImageHtml = function(thumbnail) {
            return '<img src="' + thumbnail.attr('data-large-image-url') + '" alt="' + thumbnail.attr('alt') + '" title="' + thumbnail.attr('title') + '" />';
        };

        var preloadImages = function(container) {
            preloadedImages = [];
            container.find('.bricks-lodging-image-thumbnails img').each(function() {
                var image = new Image();
                image.src = $(this).attr('data-large-image-url');
                preloadedImages.push(image);
            });
        };

        var init = function(container) {
            var largeImageContainer = container.find(".bricks-lodging-default-image");
            container.find(".bricks-lodging-image-thumbnails img").mouseover(function(event) {
                largeImageContainer.html(makeLargeImageHtml($(this)));
            });

            if (preloadedImages === false) {
                preloadImages(container);
            }

            container.find(".bricks-lodging-more-thumbnail-images a").click(function(event) {
                event.preventDefault();
                $(this).blur();
                var showText = $(this).attr('data-show-text');
                var hideText = $(this).attr('data-hide-text');
                if (container.find(".bricks-extra-thumbnails").is(":visible")) {
                    container.find(".bricks-extra-thumbnails").fadeOut('fast');
                    $(this).addClass("bricks-expand-extra-thumbnails").removeClass("bricks-collapse-extra-thumbnails").html(showText);
                } else {
                    container.find(".bricks-extra-thumbnails").fadeIn('fast');
                    $(this).addClass("bricks-collapse-extra-thumbnails").removeClass("bricks-expand-extra-thumbnails").html(hideText);
                }
                return false;
            });
        };

        return {
            init: init
        };
    };

    return {
        create: create
    };
});
Bricks.module("LodgingImages", function($) {

    var create = function() {
        var preloadedImages = false;

        var makeLargeImageHtml = function(thumbnail) {
            var html = '';
            if (thumbnail.attr('data-gallery-image-url')) {
                html += '<a href="' + thumbnail.attr('data-gallery-image-url') + '" class="bricks-gallery-image-link">';
            }
            html += '<img src="' + thumbnail.attr('data-large-image-url') + '" alt="' + thumbnail.attr('alt') + '" title="' + thumbnail.attr('title') + '" />';
            if (thumbnail.attr('data-gallery-image-url')) {
                html += '</a>';
            }
            return html;
        };

        var preloadImages = function(container) {
            preloadedImages = [];
            container.find('.bricks-lodging-image-thumbnails img').each(function() {
                var image = new Image();
                image.src = $(this).attr('data-large-image-url');
                preloadedImages.push(image);
            });
        };

        var init = function(container) {
            var largeImageContainer = container.find(".bricks-lodging-default-image");
            container.find(".bricks-lodging-image-thumbnails img").mouseover(function(event) {
                largeImageContainer.html(makeLargeImageHtml($(this)));
            });

            if (preloadedImages === false) {
                preloadImages(container);
            }

            container.find(".bricks-lodging-more-thumbnail-images a").click(function(event) {
                event.preventDefault();
                $(this).blur();
                var showText = $(this).attr('data-show-text');
                var hideText = $(this).attr('data-hide-text');
                if (container.find(".bricks-extra-thumbnails").is(":visible")) {
                    container.find(".bricks-extra-thumbnails").fadeOut('fast');
                    $(this).addClass("bricks-expand-extra-thumbnails").removeClass("bricks-collapse-extra-thumbnails").html(showText);
                } else {
                    container.find(".bricks-extra-thumbnails").fadeIn('fast');
                    $(this).addClass("bricks-collapse-extra-thumbnails").removeClass("bricks-expand-extra-thumbnails").html(hideText);
                }
                return false;
            });
        };

        return {
            init: init
        };
    };

    var setupGallery = function(container, autoRewind, options) {

        container.find('.bricks-gallery-image-link').live('click', function(event) {
            event.preventDefault();
            event.stopPropagation();
            var url = $(this).attr('href');
            if (autoRewind) {
                container.find('.bricks-lodging-gallery-images a').filter(':first').click();
            } else {
                container.find('.bricks-lodging-gallery-images a').each(function() {
                    if ($(this).attr('href') == url) {
                        $(this).click();
                    }
                });
            }
        });

        container.find('.bricks-lodging-gallery-images a').lightBox(options);
    };

    return {
        create: create,
        setupGallery: setupGallery
    };
});
Bricks.module("SearchContext", function($) {

    var ensureArray = function(parameters, name) {
        if (typeof parameters[name] !== 'undefined') {
            if ($.isArray(parameters[name])) {
                return parameters[name];
            } else {
                return [parameters[name]];
            }
        }
        return [];
    };

    var tokenize = function(querystring) {
        var tokens = {};
        if (!querystring) return tokens;
        var parts = querystring.split(/&/);
        Bricks.forEach(parts, function(part) {
            var separatorIndex = part.indexOf('=');
            if (separatorIndex > -1) {
                tokens[part.substring(0, separatorIndex)] = part.substring(separatorIndex + 1);
            } else {
                tokens[part] = null;
            }
        });
        return tokens;
    };

    var valuesToQueryString = function(values) {
        var parts = [];
        var withQuestionMark = arguments[1] || false;
        for (var name in values) {
            if (values.hasOwnProperty(name)) {
                parts.push(name + '=' + encodeURIComponent(values[name]));
            }
        }
        if (withQuestionMark) {
            return '?' + parts.join('&');
        }
        return parts.join('&');
    };

    var valuesFromQueryString = function(querystring) {
        if (querystring.indexOf('?') === 0) querystring = querystring.substring(1);
        var tokens = tokenize(querystring);
        var parameters = {};
        var facilityId, value, greaterThanEqual;
        var numbers;
        var room;
        for (var name in tokens) {
            if (tokens.hasOwnProperty(name)) {
                try {
                    if (name === 'dat') {
                        parameters[name] = Bricks.Dates.fromQueryStringDate(decodeURIComponent(tokens[name]));
                    }
                    if (Bricks.some(['dur', 'adu', 'chi', 'inf', 'pet', 'lty', 'lod', 'lut', 'bty', 'rms', 'loc', 'min', 'max', 'pge', 'pgs', 'rnd', 'rng'], function(n) { return n === name; })) {
                        parameters[name] = parseInt(tokens[name], 10);
                    }
                    if (Bricks.some(['sts', 'subloc', 'substs'], function(n) { return n === name; })) {
                        numbers = [];
                        Bricks.forEach(tokens[name].split(/,/), function(part, i) {
                            if (/^[1-9][0-9]*$/.test(part)) {
                                numbers.push(parseInt(part, 10));
                            }
                        });
                        parameters[name] = numbers;
                    }
                    if (name === 'rmx') {
                        parameters[name] = [];
                        Bricks.forEach(decodeURIComponent(tokens[name]).split(/,/), function(part) {
                            var subParts = Bricks.map(part.split(/;/), function(p) { return Bricks.toInt(p); });
                            if (subParts.length === 6) {
                                room = {
                                    lodgingUnitTypeId: subParts[0],
                                    boardTypeId: subParts[1],
                                    adults: subParts[2],
                                    children: subParts[3],
                                    infants: subParts[4],
                                    pets: subParts[5]
                                };
                                parameters[name].push(room);
                            }
                        });
                    }
                    if (Bricks.some(['ord', 'cur', 'tag', 'stn'], function(n) { return n === name; })) {
                        parameters[name] = tokens[name];
                    }
                    if (name.indexOf('fac') === 0) {
                        facilityId = parseInt(name.replace(/^fac/, ""), 10);
                        value = tokens[name];
                        greaterThanEqual = false;
                        if (typeof parameters["fac"] === 'undefined') {
                            parameters["fac"] = [];
                        }
                        if (/^[0-9]+[pP]$/.test(value)) {
                            value = value.substring(0, value.length - 1);
                            greaterThanEqual = true;
                        }
                        parameters["fac"].push({ facilityId: facilityId, value: value, greaterThanEqual: greaterThanEqual });
                    }
                    if (name.indexOf('subfac') === 0) {
                        facilityId = parseInt(name.replace(/^subfac/, ""), 10);
                        value = tokens[name];
                        greaterThanEqual = false;
                        if (typeof parameters["subfac"] === 'undefined') {
                            parameters['subfac'] = [];
                        }
                        if (/^[0-9]+[pP]$/.test(value)) {
                            value = value.substring(0, value.length - 1);
                            greaterThanEqual = true;
                        }
                        parameters['subfac'].push({ facilityId: facilityId, value: value, greaterThanEqual: greaterThanEqual });
                    }
                } catch (ex) {
                    // Pass
                }
            }
        }
        return parameters;
    };

    var create = function(parameters) {
        return new SearchContext(parameters);
    };

    var createFromQueryString = function() {
        var querystring = arguments[0] || window.location.search;
        return new SearchContext(valuesFromQueryString(querystring));
    };

    var createFromForm = function(container) {
        var parameters = {};
        parameters["dat"] = getFormMonthYear(container.find('.bricks-select-monthyear'));
        if (getFormInteger(container.find('.bricks-select-duration')) !== null) {
            parameters["dur"] = getFormInteger(container.find('.bricks-select-duration'));
        }
        if (getFormInteger(container.find('.bricks-select-adults')) !== null) {
            parameters["adu"] = getFormInteger(container.find('.bricks-select-adults'));
        }
        if (getFormInteger(container.find('.bricks-select-children')) !== null) {
            parameters["chi"] = getFormInteger(container.find('.bricks-select-children'));
        }
        if (getFormInteger(container.find('.bricks-select-infants')) !== null) {
            parameters["inf"] = getFormInteger(container.find('.bricks-select-infants'));
        }
        if (getFormInteger(container.find('.bricks-select-pets')) !== null) {
            parameters["pet"] = getFormInteger(container.find('.bricks-select-pets'));
        }
        return new SearchContext(parameters);
    };

    var getFormInteger = function(elem) {
        var value = elem.val();
        if ($.trim(value) === "") return null;
        try {
            return parseInt(value, 10);
        } catch (ex) {
            return null;
        }
    };

    var getFormMonthYear = function(elem) {
        var month = parseInt(elem.val().substr(0, 2).replace(/^0/, ''), 10);
        var year = parseInt(elem.val().substr(3), 10);
        return new Date(year, month, 1);
    };

    function SearchContext(parameters) {
        var that = this;

        this.languageId = (typeof parameters['lan'] !== 'undefined') ? parameters['lan'] : null;
        this.arrivalDate = Bricks.Dates.fromJsonDate(parameters['dat']) || null;
        this.duration = (typeof parameters['dur'] !== 'undefined') ? parameters['dur'] : null;
        this.adults = (typeof parameters['adu'] !== 'undefined') ? parameters['adu'] : null;
        this.children = (typeof parameters['chi'] !== 'undefined') ? parameters['chi'] : null;
        this.infants = (typeof parameters['inf'] !== 'undefined') ? parameters['inf'] : null;
        this.pets = (typeof parameters['pet'] !== 'undefined') ? parameters['pet'] : null;
        this.locationId = (typeof parameters['loc'] !== 'undefined') ? parameters['loc'] : null;
        this.lodgingTypeId = (typeof parameters['lty'] !== 'undefined') ? parameters['lty'] : null;
        this.lodgingId = (typeof parameters['lod'] !== 'undefined') ? parameters['lod'] : null;
        this.lodgingUnitTypeId = (typeof parameters['lut'] !== 'undefined') ? parameters['lut'] : null;
        this.boardTypeId = (typeof parameters['bty'] !== 'undefined') ? parameters['bty'] : null;
        this.currencyCode = (typeof parameters['cur'] !== 'undefined') ? parameters['cur'] : null;
        this.minPrice = (typeof parameters['min'] !== 'undefined') ? parameters['min'] : null;
        this.maxPrice = (typeof parameters['max'] !== 'undefined') ? parameters['max'] : null;
        this.stars = ensureArray(parameters, 'sts');
        this.facilities = ensureArray(parameters, 'fac');
        this.rooms = (typeof parameters['rms'] !== 'undefined') ? parameters['rms'] : null;
        this.roomMatrix = ensureArray(parameters, 'rmx');
        this.orderBy = (typeof parameters['ord'] !== 'undefined') ? parameters['ord'] : null;
        this.page = (typeof parameters['pge'] !== 'undefined') ? parameters['pge'] : null;
        this.pageSize = (typeof parameters['pgs'] !== 'undefined') ? parameters['pgs'] : null;
        this.randomSeed = (typeof parameters['rnd'] !== 'undefined') ? parameters['rnd'] : null;
        this.tag = (typeof parameters['tag'] !== 'undefined') ? parameters['tag'] : null;
        this.searchRangeInDays = (typeof parameters['rng'] !== 'undefined') ? parameters['rng'] : null;
        this.streetName = (typeof parameters['stn'] !== 'undefined') ? parameters['stn'] : null;

        this.sub = {
            locationIds: ensureArray(parameters, 'subloc'),
            stars: ensureArray(parameters, 'substs'),
            facilities: ensureArray(parameters, 'subfac')
        };

        this.departureDate = function() {
            if (that.arrivalDate && that.duration) {
                return Bricks.Dates.addDays(that.arrivalDate, that.duration);
            }
            return null;
        };

        this.facilityValueDate = function() {
            return (that.arrivalDate || new Date());
        };

        this.values = function() {
            var values = {};
            if (that.languageId !== null) values['lan'] = that.languageId;
            if (that.arrivalDate !== null) values['dat'] = Bricks.Dates.toQueryStringDate(that.arrivalDate);
            if (that.duration !== null) values['dur'] = that.duration;
            if (that.adults !== null) values['adu'] = that.adults;
            if (that.children !== null) values['chi'] = that.children;
            if (that.infants !== null) values['inf'] = that.infants;
            if (that.pets !== null) values['pet'] = that.pets;
            if (that.locationId !== null) values['loc'] = that.locationId;
            if (that.lodgingTypeId !== null) values['lty'] = that.lodgingTypeId;
            if (that.lodgingId !== null) values['lod'] = that.lodgingId;
            if (that.lodgingUnitTypeId !== null) values['lut'] = that.lodgingUnitTypeId;
            if (that.boardTypeId !== null) values['bty'] = that.boardTypeId;
            if (that.currencyCode !== null) values['cur'] = that.currencyCode;
            if (that.stars.length) values['sts'] = that.stars.join(",");
            if (that.rooms !== null) values['rms'] = that.rooms;
            if (that.roomMatrix.length) {
                var rmx = [];
                Bricks.forEach(that.roomMatrix, function(room) {
                    rmx.push(room.lodgingUnitTypeId + ";" + room.boardTypeId + ";" + room.adults + ";" + room.children + ";" + room.infants + ";" + room.pets);
                });
                values['rmx'] = rmx.join(",")
            }
            if (that.orderBy !== null) values['ord'] = that.orderBy;
            if (that.page !== null) values['pge'] = that.page;
            if (that.pageSize !== null) values['pgs'] = that.pageSize;
            if (that.randomSeed !== null) values['rnd'] = that.randomSeed;
            if (that.tag !== null) values['tag'] = that.tag;
            if (that.searchRangeInDays !== null) values['rng'] = that.searchRangeInDays;
            if (that.streetName !== null) values['stn'] = that.streetName;

            Bricks.forEach(that.facilities, function(facilityValue) {
                if (facilityValue.value === true) {
                    values["fac" + facilityValue.facilityId.toString()] = 1;
                } else if (facilityValue.value === false) {
                    values["fac" + facilityValue.facilityId.toString()] = 0;
                } else {
                    if (facilityValue.greaterThanEqual) {
                        values["fac" + facilityValue.facilityId.toString()] = facilityValue.value + "p";
                    } else {
                        values["fac" + facilityValue.facilityId.toString()] = facilityValue.value;
                    }
                }
            });
            if (that.minPrice !== null) values['min'] = that.minPrice;
            if (that.maxPrice !== null) values['max'] = that.maxPrice;
            if (that.sub.locationIds.length) values['subloc'] = that.sub.locationIds.join(',');
            if (that.sub.stars.length) values['substs'] = that.sub.stars.join(',');
            Bricks.forEach(that.sub.facilities, function(facilityValue) {
                if (facilityValue.value === true) {
                    values['subfac' + facilityValue.facilityId.toString()] = 1;
                } else if (facilityValue.value === false) {
                    values['subfac' + facilityValue.facilityId.toString()] = 0;
                } else {
                    if (facilityValue.greaterThanEqual) {
                        values['subfac' + facilityValue.facilityId.toString()] = facilityValue.value + "p";
                    } else {
                        values['subfac' + facilityValue.facilityId.toString()] = facilityValue.value;
                    }
                }
            });
            return values;
        };

        this.toQueryString = function() {
            var withQuestionMark = arguments.length == 1 ? arguments[0] : false;
            return valuesToQueryString(that.values(), withQuestionMark);
        };

        this.copy = function() {
            var newSearchContext = new SearchContext(parameters);
            newSearchContext.languageId = that.languageId;
            newSearchContext.arrivalDate = that.arrivalDate;
            newSearchContext.duration = that.duration;
            newSearchContext.adults = that.adults;
            newSearchContext.children = that.children;
            newSearchContext.infants = that.infants;
            newSearchContext.pets = that.pets;
            newSearchContext.locationIds = that.locationIds;
            newSearchContext.lodgingId = that.lodgingId;
            newSearchContext.lodgingTypeId = that.lodgingTypeId;
            newSearchContext.lodgingUnitTypeId = that.lodgingUnitTypeId;
            newSearchContext.boardTypeId = that.boardTypeId;
            newSearchContext.currencyCode = that.currencyCode;
            newSearchContext.stars = [];
            newSearchContext.stars.concat(that.stars);
            newSearchContext.rooms = that.rooms;
            newSearchContext.roomMatrix = [];
            newSearchContext.roomMatrix.concat(that.roomMatrix);
            newSearchContext.orderBy = that.orderBy;
            newSearchContext.page = that.page;
            newSearchContext.pageSize = that.pageSize;
            newSearchContext.randomSeed = that.randomSeed;
            newSearchContext.tag = that.tag;
            newSearchContext.searchRangeInDays = that.searchRangeInDays;
            newSearchContext.streetName = that.streetName;
            newSearchContext.facilities = [];
            newSearchContext.facilities.concat(that.facilities);
            newSearchContext.minPrice = that.minPrice;
            newSearchContext.maxPrice = that.maxPrice;
            newSearchContext.sub.locationIds = [];
            newSearchContext.sub.locationIds.concat(that.sub.locationIds);
            newSearchContext.sub.stars = [];
            newSearchContext.sub.stars.concat(that.sub.stars);
            newSearchContext.sub.facilities = [];
            newSearchContext.sub.facilities.concat(that.sub.facilities);
            return newSearchContext;
        };
    }

    return {
        create: create,
        createFromQueryString: createFromQueryString,
        createFromForm: createFromForm,
        /* Private API methods for testing */
        tokenize: tokenize,
        valuesFromQueryString: valuesFromQueryString,
        valuesToQueryString: valuesToQueryString
    };
});

Bricks.module("DefaultText", function($) {

    var cleanText = function(text) {
        return text.replace(/[\t\r\n]/g, " ");
    };

    var defaultText = function(elem) {
        var text = elem.attr('data-default-text');
        if (text) {
            text = cleanText(text);
        }
        return text;
    };

    var val = function(elem) {
        if (elem.val() === defaultText(elem)) {
            return '';
        }
        return elem.val();
    };

    return {
        cleanText: cleanText,
        defaultText: defaultText,
        val: val
    };
});

(function($) {

    $.fn.defaultText = function() {

        return this.each(function() {
            var $this = $(this);
            var defaultText = Bricks.DefaultText.defaultText($this);

            $this.focus(function() {
                $(this).removeClass('search-input-empty');
                if ($(this).val() === defaultText) {
                    $(this).val('');
                }
            }).blur(function() {
                if ($(this).val() === '' || $(this).val() === defaultText) {
                    $(this).addClass('search-input-empty').val(defaultText);
                }
            });

            if ($(this).val() === '' || $(this).val() === defaultText) {
                $(this).val(defaultText);
                $(this).addClass('search-input-empty');
            } else {
                $(this).removeClass('search-input-empty');
            }
        });
    };

})(jQuery);

