function ProductViewModel(product) { var self = this; var firtsSku = null; var apiEazyZoomProduct = null; var firstImages = []; if (product.items.length > 0) { if (product.items[0].sellers != null && product.items[0].sellers.length > 0) { firtsSku = product.items[0]; } } const activeOption = setInterval(function () { if ($('.option.active')) { $('.option.active').click(); clearInterval(activeOption); } }, 100); this.quantity = ko.observable(1); this.name = ko.observable(product.productName); product.items.forEach(function (sku) { if (sku.images != null) { firstImages.push(sku.images[0]); } }); this.images = ko.observable(firstImages); this.listPrice = ko.observable(firtsSku.sellers[0].commertialOffer.ListPrice); this.price = ko.observable(firtsSku.sellers[0].commertialOffer.Price); this.isTax = ko.observable(firtsSku.sellers[0].commertialOffer.Tax); this.reference = ko.observable(firtsSku.referenceId[0].Value); this.percent = ko.observable(0); if (this.price() != this.listPrice()) { this.percent((100 - this.price() / (this.listPrice() / 100)).toFixed(0)); } this.listPriceFormated = ko.observable(currency(this.listPrice())); this.priceFormated = ko.observable(currency(this.price())); this.availablequantity = ko.observable(firtsSku.sellers[0].AvailableQuantity); this.product = ko.observable(product); this.benefits = ko.observable(product['Beneficios Clave']); this.imageSelected = ko.observable(firtsSku.images[0].imageUrl); this.optionsSelected = ko.observable({}); this.colorSelected = ko.observable(''); this.optionsAvailable = ko.observable([]); this.skuSelected = ko.observable({}); this.errorMessage = ko.observable(''); this.addingToCart = ko.observable(false); this.needQuantity = ko.observable(0); this.materialAreaNeeded = ko.observable(0); this.extrapercent = ko.observable(5); this.detailsEnabled = ko.observable(false); this.detailsDisbled = ko.observable(true); this.includePercent = ko.observable(true); this.promoLocura = ko.observable({}); this.initZoomProduct = function () { var $easyzoomProduct = $('.product-zoom'); $easyzoomProduct = $easyzoomProduct.easyZoom(); apiEazyZoomProduct = $easyzoomProduct.data('easyZoom'); var $easyzoom = $('.product-zoom-resume'); $easyzoom = $easyzoom.easyZoom(); apiEazyZoom = $easyzoom.data('easyZoom'); }; this.setFirstOptions = function (productParam) { setTimeout(() => { const currentProduct = typeof productParam === 'object' ? productParam : self.product(); if (!currentProduct) return; const availableItems = currentProduct.items.filter(item => { const seller = item.sellers.find(s => s.sellerDefault === true); if (!seller || !seller.commertialOffer) return false; return seller.commertialOffer.IsAvailable && seller.commertialOffer.AvailableQuantity > 0; }); if (availableItems.length === 0) return; const firstAvailableColor = availableItems[0].Color?.[0] || ''; const availableDimensions = availableItems .filter(item => item.Color?.[0] === firstAvailableColor) .map(item => item.Dimensiones?.[0]) .filter(Boolean); if (firstAvailableColor) { self.optionsSelected({ 'Color': firstAvailableColor, 'Dimensiones': availableDimensions[0] || '' }); self.colorSelected(firstAvailableColor); const selectedSku = availableItems.find(item => item.Color?.[0] === firstAvailableColor && item.Dimensiones?.[0] === availableDimensions[0] ); if (selectedSku) { self.skuSelected(selectedSku); self.listPrice(selectedSku.sellers[0].commertialOffer.ListPrice); self.price(selectedSku.sellers[0].commertialOffer.Price); self.availablequantity(selectedSku.sellers[0].commertialOffer.AvailableQuantity); self.listPriceFormated(currency(self.listPrice())); self.priceFormated(currency(self.price())); self.images(selectedSku.images); self.imageSelected(selectedSku.images[0].imageUrl); if (self.price() !== self.listPrice()) { self.percent((100 - self.price() / (self.listPrice() / 100)).toFixed(0)); } } self.selectOption('Color', { name: firstAvailableColor }); if (availableDimensions[0]) { self.selectOption('Dimensiones', availableDimensions[0]); } self.validatePromo(self.quantity()); } }, 500); }; this.validatePromo = function (quantity) { var activePromos = localStorage.getItem("seasonPromo"); if (!activePromos) return; let product = this.product(); let categoriesIds = product.categoriesIds; let department = categoriesIds[categoriesIds.length - 1].replaceAll("/", ""); let sku = this.skuSelected(); if (Object.keys(sku).length > 0) { let skuReference = sku.referenceId[0].Value; //fetch('../files/promos-cyberdays.json') fetch('../files/promos-liquidacion.json') .then((response) => response.json()) .then((data) => { $.each(data, function (key, item) { if (department === item.category) { $.each(item.categoryPromos, function (key, categoryPromo) { if (skuReference === categoryPromo.productReference) { let quantityMax = categoryPromo.maxQuantity; let discountMax = categoryPromo.maxDiscount; self.percent(discountMax); $.each(categoryPromo.productPromos, function (key, productPromo) { let minVal = productPromo.range.minVal; let maxVal = productPromo.range.maxVal; let discount = productPromo.discount; if (maxVal) { if (maxVal >= quantity && quantity >= minVal) { if (maxVal === quantity && quantity === minVal) { $(".message-discount").removeClass("active"); $(".message-discount span").remove(); $(".message-discount").addClass("active"); if (quantityMax === 0) { $(".message-discount").append(`¡Genial! tienes ${discount}% de descuento.`); } else { $(".message-discount").append(`¡Genial! tienes ${discount}% de descuento. te faltan ${quantityMax - quantity} para obtener un ${discountMax}% de descuento`); } } else { $(".message-discount").removeClass("active"); $(".message-discount span").remove(); $(".message-discount").addClass("active"); if (categoryPromo.limits) { $.each(categoryPromo.limits, function (key, limit) { if (quantity < limit[0]) { quantityMax = limit[0]; discountMax = limit[1]; $(".message-discount").append(`¡Genial! tienes ${discount}% de descuento. te faltan ${quantityMax - quantity} para obtener un ${discountMax}% de descuento`); return false; } }); } else { $(".message-discount").append(`¡Genial! tienes ${discount}% de descuento. te faltan ${quantityMax - quantity} para obtener un ${discountMax}% de descuento`); } } return false; } else { $(".message-discount").removeClass("active"); $(".message-discount span").remove(); $(".message-discount").addClass("active"); $(".message-discount").append(`Para obtener ${discount}% de descuento debes agregar ${minVal - quantity} más`); }; } else { if (quantity >= minVal) { $(".message-discount").removeClass("active"); $(".message-discount span").remove(); $(".message-discount").addClass("active"); $(".message-discount").append(`¡Genial! tienes ${discount}% de descuento.`); return false; } } }); } }); return false; } }); }); } if (product.productClusters && Object.keys(product.productClusters).find(function (cluster) { return cluster === "399"; })) { $('.flags-product .promo-liquidacion').fadeIn(); } else { $('.flags-product .promo-liquidacion').fadeOut(); } }; this.resetAll = function (product) { const firstAvailableItem = product.items.find(item => { const seller = item.sellers.find(s => s.sellerDefault === true); if (!seller || !seller.commertialOffer) return false; return seller.commertialOffer.IsAvailable && seller.commertialOffer.AvailableQuantity > 0; }); if (firstAvailableItem) { const firstAvailableColor = firstAvailableItem.Color?.[0] || ''; const firstAvailableDimension = firstAvailableItem.Dimensiones?.[0] || ''; self.optionsSelected({ 'Color': firstAvailableColor, 'Dimensiones': firstAvailableDimension }); self.colorSelected(firstAvailableColor); self.errorMessage(''); self.addingToCart(false); self.quantity(1); self.benefits(product['Beneficios Clave']); self.name(product.productName); self.product(product); self.listPrice(firstAvailableItem.sellers[0].commertialOffer.ListPrice); self.price(firstAvailableItem.sellers[0].commertialOffer.Price); self.availablequantity(firstAvailableItem.sellers[0].AvailableQuantity); self.isTax(firstAvailableItem.sellers[0].commertialOffer.Tax); self.listPriceFormated(currency(self.listPrice())); self.priceFormated(currency(self.price())); if (self.price() !== self.listPrice()) { self.percent((100 - self.price()) / (self.listPrice() / 100).toFixed(0)); } else { self.percent(0); } self.reference(firstAvailableItem.referenceId[0].Value); self.images(firstAvailableItem.images); self.showImage(firstAvailableItem); if (firstAvailableColor) { self.selectOption('Color', { name: firstAvailableColor }); if (firstAvailableDimension) { self.selectOption('Dimensiones', firstAvailableDimension); } } } }; this.getProperty = function (item) { return typeof item === 'object' ? item[0] : item; }; this.selectOption = function (key, option, repeat) { var options = self.optionsSelected(); var searchSku = null; options[key] = typeof option === 'object' ? option.name : option; self.optionsSelected(options); self.hasEmptyFields(); switch (key) { case 'Color': self.colorSelected(option.name); if (self.optionsSelected()['Dimensiones'] != '') { var dimensionsOptions = []; self.product().items.forEach(function (item, index) { if (self.getProperty(item['Color']) === self.optionsSelected()['Color'] && self.getProperty(item['Dimensiones']) === self.optionsSelected()['Dimensiones']) { searchSku = item; searchSku['indexSku'] = index; } else if (self.getProperty(item['Color']) === self.optionsSelected()['Color']) { searchSku = item; searchSku['indexSku'] = index; } if (self.getProperty(item['Color']) === self.optionsSelected()['Color']) { dimensionsOptions.push(self.getProperty(item['Dimensiones'])); } }); dimensionsOptions.sort((a, b) => (a < b ? 1 : -1)); self.optionsAvailable(dimensionsOptions); if (!repeat) { self.selectOption(key, option, true); } } else { searchSku = self.product().items.find(function (item, index) { item['indexSku'] = index; return self.getProperty(item['Color']) === self.optionsSelected()['Color']; }); } break; case 'Dimensiones': if (self.optionsSelected()['Color'] != '') { self.product().items.forEach(function (item, index) { if (self.getProperty(item['Color']) === self.optionsSelected()['Color'] && self.getProperty(item['Dimensiones']) === self.optionsSelected()['Dimensiones']) { searchSku = item; searchSku['indexSku'] = index; } }); } else { searchSku = self.product().items.find(function (item, index) { item['indexSku'] = index; return self.getProperty(item['Dimensiones']) === self.optionsSelected()['Dimensiones']; }); } break; } if (searchSku) { $(document).trigger("skusele", [searchSku]); } if (searchSku != null) { self.listPrice(searchSku.sellers[0].commertialOffer.ListPrice); self.price(searchSku.sellers[0].commertialOffer.Price); if (self.price() != self.listPrice()) { self.percent((100 - self.price() / (self.listPrice() / 100)).toFixed(0)); } else { self.percent(0); } self.isTax(searchSku.sellers[0].commertialOffer.Tax); self.listPriceFormated(currency(self.listPrice())); self.priceFormated(currency(self.price())); self.skuSelected(searchSku); self.showImage(searchSku); self.name(searchSku.name); self.reference(searchSku.referenceId[0].Value); self.images(searchSku.images); sliderResume.slideTo(searchSku.indexSku); self.validatePromo(self.quantity()); setTimeout(function () { const index = Array.from(document.querySelectorAll('.option-mobile').values()).findIndex(element => element.classList.contains("active")); document.querySelector(".swiper-wrapper-mobile").scroll({ top: 0, left: index * 30, behavior: 'smooth' }); }, 500); } }; this.isSelected = function (key, value) { var className = ''; if (self.optionsSelected()[key] === value) className = 'active '; var productItem = self.product().items.find(function (item) { return self.getProperty(item[key]) === value; }); if (productItem && productItem.sellers[0].commertialOffer.AvailableQuantity === 0) className += 'unavailable'; return className; }; this.incrementQuantity = function () { var previousCount = parseInt(self.quantity()); if (Object.entries(self.skuSelected()).length !== 0) { var maxStock = 0; self.skuSelected().sellers.forEach(function (e) { maxStock += e.commertialOffer.AvailableQuantity; }); if (!maxStock) { self.errorMessage("Sin unidades disponibles para esta variación"); } else if (previousCount >= maxStock) { self.errorMessage("Solo hay " + maxStock + (1 == maxStock ? " unidad" : " unidades")); } else { self.quantity(previousCount + 1); } } else { self.errorMessage("Seleccione una variación primero"); } self.validatePromo(self.quantity()); }; this.decrementQuantity = function () { var previousCount = parseInt(self.quantity()); if (previousCount > 1) { if (self.errorMessage() != "") { self.errorMessage(""); } self.quantity(previousCount - 1); } self.validatePromo(self.quantity()); }; this.checkVariants = function (value, key) { self.selectOption(key.field.name, value); }; this.hasEmptyFields = function () { var options = self.optionsSelected(); for (var key in options) { if (options[key] === '' || options[key] === null || options[key] === undefined) { switch (key) { case "Dimensiones": self.errorMessage('Debe seleccionar una dimensión'); break; default: self.errorMessage('Debe seleccionar un ' + key); } return true; } } self.errorMessage(''); return false; }; this.isFullCol = function (type) { switch (type) { case 'Color': return 'col-sm-12'; case 'Dimensiones': return 'col-xs-6 col-sm-6'; } }; this.isLastVariant = function (index) { return index === self.product().skuSpecifications.length - 1; }; this.showImage = function (sku) { if (sku != null) { if (sku.imageUrl != null) { self.imageSelected(sku.imageUrl); } else { self.imageSelected(sku.images[0].imageUrl); } try { if ($('.product-zoom').length > 0 && apiEazyZoomProduct) { apiEazyZoomProduct.swap(self.imageSelected()); } if ($('.product-zoom-resume').length > 0 && apiEazyZoom) { apiEazyZoom.swap(self.imageSelected()); } } catch (error) { console.warn('Error al actualizar el zoom de la imagen:', error); } } }; this.needQuantity.subscribe(function (newValue) { self.calculator(newValue, self.extrapercent()); self.detailsEnabled(true); self.detailsDisbled(false); }); this.includePercent.subscribe(function (newValue) { !newValue ? self.calculator(self.needQuantity(), 0) : self.calculator(self.needQuantity(), self.extrapercent()); }); this.startOperation = function () { }; this.calculator = function (necessaryArea, aditionalAreaPercent) { if (product['Aplica conversion'][0].toLowerCase() === 'si') { let factor = necessaryArea / parseFloat(product['Factor de conversion M2'][0]); if (this.includePercent) { var area = Math.ceil((factor + factor * aditionalAreaPercent / 100)); } self.materialAreaNeeded(area); self.quantity(area); } }; var listPromoLocura = [ "85903", "85351", "85774", "86023", "85871", "85800" ]; if (listPromoLocura.includes(product.productReference)) { $('#promo-locura').fadeIn(); } else { $('#promo-locura').fadeOut(); } this.initZoomProduct(); this.setFirstOptions(); this.validatePromo(self.quantity()); }