Advertisement
oscarviedma

Código JavaScript Catálogo Productos WA GS OV

Mar 30th, 2024 (edited)
1,611
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
  1.   let carrito = [];
  2.   let carritoTotal = 0;
  3.   let datosFiltrados = [];
  4.  
  5.   const preloader = document.getElementById('preloader');
  6.   preloader.style.display = 'block';
  7.  
  8.   let datosProductos = [];
  9.   const contenedorProductos = document.getElementById('contenedor-productos');
  10.   const mensajeNoEncontrado = document.getElementById('mensaje-no-encontrado');
  11.   contenedorProductos.style.opacity = '0';
  12.  
  13.   function formatearPrecio(precio) {
  14.     return precio.toLocaleString('en-US');
  15.     // return precio.toLocaleString('es-ES', { style: 'currency', currency: 'EUR' });
  16.     // return precio.toLocaleString('es-MX', { style: 'currency', currency: 'MXN' });
  17.     // return precio.toLocaleString('es-CO', { style: 'currency', currency: 'COP' });
  18.   }
  19.  
  20.   fetch('https://script.google.com/macros/s/AKfycbzxho78Qr07ADOpzdfF-acJxTztln4aZnQUoptrYHJcNNLMPS1Z_oIzrTfbQbC6Bwlc/exec')
  21.     .then(response => response.json())
  22.     .then(data => {
  23.       datosProductos = data;
  24.       datosFiltrados = data;
  25.       renderizarProductos(datosFiltrados);
  26.       preloader.style.display = 'none';
  27.       contenedorProductos.style.opacity = '1';
  28.       document.getElementById('contenedor-buscador').style.display = '';
  29.       generarCategorias(data);
  30.     })
  31.     .catch(error => {
  32.       console.error('Error al obtener el JSON:', error);
  33.       preloader.style.display = 'none';
  34.     });
  35.  
  36.   function renderizarProductos(productos) {
  37.     contenedorProductos.innerHTML = '';
  38.     if (productos.length === 0) {
  39.       mensajeNoEncontrado.style.display = 'block';
  40.     } else {
  41.       mensajeNoEncontrado.style.display = 'none';
  42.       productos.forEach((producto, index) => {
  43.         var productoDiv = document.createElement('div');
  44.         productoDiv.className = 'producto';
  45.  
  46.         productoDiv.innerHTML = `
  47.             <div class="imagen">
  48.                 <img src="${producto.imagen}" alt="Imagen del producto">
  49.             </div>
  50.             <div class="info">
  51.                 <h4 class="titulo">${producto.titulo}</h4>
  52.                 <h3 class="precio">$${formatearPrecio(producto.precio)} USD</h3>
  53.                 <div class="metadatos" id="atributo${index}">
  54.                     ${producto.atributos && Object.keys(producto.atributos).length > 0 ?
  55.                       Object.entries(producto.atributos).map(([nombreAtributo, valores]) => {
  56.                         const nombreAtributoLowerCase = nombreAtributo.toLowerCase();
  57.                         if (valores.filter(Boolean).length > 0) {
  58.                           return `<div class="meta">
  59.                                       <label for="${nombreAtributoLowerCase}${index}">${nombreAtributo}:</label>
  60.                                       <select id="${nombreAtributoLowerCase}${index}">
  61.                                           <option value="" selected="selected" disabled="disabled">Seleccionar ${nombreAtributo}</option>
  62.                                           ${valores.map(valor => `<option value="${valor}">${valor}</option>`).join('')}
  63.                                       </select>
  64.                                   </div>`;
  65.                         } else {
  66.                           return '';
  67.                         }
  68.                       }).join('') : ''}
  69.                 </div>
  70.                 <button class="agregar" data-info='${JSON.stringify({ nombre: producto.titulo, precio: producto.precio, atributos: producto.atributos, index: index })}'>Agregar al carrito</button>
  71.             </div>
  72.         `;
  73.  
  74.         contenedorProductos.appendChild(productoDiv);
  75.       });
  76.     }
  77.  
  78.     inicializarFuncionalidad();
  79.   }
  80.  
  81.   function generarCategorias(productos) {
  82.     // Inicialmente, asume que no hay categorías válidas (excluyendo 'Todos').
  83.     let categoriasValidasEncontradas = false;
  84.  
  85.     let categorias = ['Todos'];
  86.     productos.forEach(producto => {
  87.       if (producto.categorias && producto.categorias.length > 0) {
  88.         // Aquí se asume que `producto.categorias` es un array de las categorías de cada producto.
  89.         producto.categorias.forEach(categoria => {
  90.           if (categoria && !categorias.includes(categoria)) {
  91.             categorias.push(categoria);
  92.             categoriasValidasEncontradas = true; // Marca que se encontró al menos una categoría válida.
  93.           }
  94.         });
  95.       }
  96.     });
  97.  
  98.     const contenedorCategorias = document.getElementById('categorias-contenedor');
  99.     contenedorCategorias.innerHTML = '';
  100.  
  101.     // Oculta el contenedor de categorías si no se encontraron categorías válidas.
  102.     if (!categoriasValidasEncontradas) {
  103.       contenedorCategorias.style.display = 'none';
  104.     } else {
  105.       // Si hay categorías válidas, muestra el contenedor y genera los botones.
  106.       contenedorCategorias.style.display = '';
  107.       categorias.forEach((categoria, index) => {
  108.         let botonCategoria = document.createElement('button');
  109.         botonCategoria.textContent = categoria;
  110.         // Asigna la clase 'active' por defecto al botón 'Todos'
  111.         if (categoria === 'Todos') {
  112.           botonCategoria.classList.add('active');
  113.         }
  114.         botonCategoria.onclick = () => filtrarPorCategoria(categoria, botonCategoria);
  115.         contenedorCategorias.appendChild(botonCategoria);
  116.       });
  117.     }
  118.   }
  119.  
  120.   // Agrega la funcionalidad de búsqueda aquí
  121.   document.getElementById('buscar-producto').addEventListener('input', function(e) {
  122.     const busqueda = e.target.value.toLowerCase();
  123.     datosFiltrados = datosProductos.filter(producto => producto.titulo.toLowerCase().includes(busqueda));
  124.     renderizarProductos(datosFiltrados);
  125.     document.getElementById('limpiar-busqueda').style.display = busqueda ? '' : 'none';
  126.      
  127.     // Reinicializar la funcionalidad del carrito después de la búsqueda
  128.     reinicializarFuncionalidad();
  129.   });
  130.  
  131.   // Agregar el evento de clic al botón de limpiar.
  132.   document.getElementById('limpiar-busqueda').addEventListener('click', function() {
  133.     document.getElementById('buscar-producto').value = '';
  134.     this.style.display = 'none';
  135.     datosFiltrados = datosProductos;
  136.     renderizarProductos(datosFiltrados);
  137.  
  138.     // Reinicializar la funcionalidad del carrito después de limpiar la búsqueda
  139.     reinicializarFuncionalidad();
  140.   });
  141.  
  142.   // Filtrar por categorias
  143.   function filtrarPorCategoria(categoriaSeleccionada, botonClickeado) {
  144.     if (categoriaSeleccionada === 'Todos') {
  145.       renderizarProductos(datosProductos);
  146.     } else {
  147.       const productosFiltrados = datosProductos.filter(producto => producto.categorias.includes(categoriaSeleccionada));
  148.       renderizarProductos(productosFiltrados);
  149.     }
  150.  
  151.     // Actualización de la clase 'active'
  152.     const botonesCategoria = document.querySelectorAll('#categorias-contenedor button');
  153.     botonesCategoria.forEach(boton => {
  154.       boton.classList.remove('active');
  155.     });
  156.     botonClickeado.classList.add('active');
  157.  
  158.     // Reinicializar la funcionalidad del carrito después del filtrado
  159.     reinicializarFuncionalidad();
  160.   }
  161.  
  162.   function reinicializarFuncionalidad() {
  163.     eliminarEventosAgregarAlCarrito();
  164.     inicializarFuncionalidad();
  165.   }
  166.  
  167.   function eliminarEventosAgregarAlCarrito() {
  168.     const productos = document.querySelectorAll('.producto');
  169.     productos.forEach(producto => {
  170.       const agregarButton = producto.querySelector('.agregar');
  171.       agregarButton.removeEventListener('click', agregarProductoAlCarrito);
  172.     });
  173.   }
  174.  
  175.   function inicializarFuncionalidad() {
  176.     const productos = document.querySelectorAll('.producto');
  177.     const carritoLista = document.getElementById('carrito-lista');
  178.     const total = document.getElementById('total');
  179.     const carritoContainer = document.getElementById('carrito-container');
  180.     const carritoIcon = document.getElementById('carrito-icon');
  181.     const carritoContador = document.getElementById('carrito-contador');
  182.     const cerrarCarrito = document.getElementById('cerrar-carrito');
  183.     const carritoVacioMensaje = document.getElementById('carrito-vacio-mensaje');
  184.     const vaciarCarritoButton = document.getElementById('vaciar-carrito');
  185.  
  186.     carritoIcon.addEventListener('click', function () {
  187.       const carritoVisible = carritoContainer.style.right === '0px';
  188.       carritoContainer.style.right = carritoVisible ? '-350px' : '0px';
  189.  
  190.       if (carritoVisible) {
  191.         carritoVacioMensaje.style.display = 'none';
  192.       }
  193.     });
  194.  
  195.     cerrarCarrito.addEventListener('click', function () {
  196.       carritoContainer.style.right = '-350px';
  197.     });
  198.    
  199.     // Función para desplazar el carrito
  200.     function desplazarCarrito() {
  201.       const anchoPantalla = window.innerWidth || document.documentElement.clientWidth || document.body.clientWidth;
  202.  
  203.       if (anchoPantalla > 768) {
  204.         carritoContainer.style.right = '0px';
  205.         carritoVacioMensaje.style.display = 'none';
  206.       }
  207.     }
  208.    
  209.     // Función para mostrar u ocultar el mensaje de carrito vacío
  210.     function mostrarMensajeCarritoVacio() {
  211.       if (carrito.length === 0) {
  212.         carritoVacioMensaje.style.display = 'block';
  213.       } else {
  214.         carritoVacioMensaje.style.display = 'none';
  215.       }
  216.     }
  217.  
  218.     // Agregar producto al carrito
  219.     function agregarProductoAlCarrito(info) {
  220.       const { nombre, precio, atributos, index } = JSON.parse(info || '{}');
  221.  
  222.       // Validar atributos seleccionados
  223.       if (!validarAtributosSeleccionados(index)) {
  224.         return;
  225.       }
  226.  
  227.       // Obtener dinámicamente los valores de los atributos seleccionados
  228.       let nombreConVariantes = `${nombre}`;
  229.       for (const [nombreAtributo, valorSeleccionado] of Object.entries(atributos)) {
  230.         const selectElement = document.getElementById(`${nombreAtributo.toLowerCase()}${index}`);
  231.         const valorSeleccionado = selectElement ? selectElement.value : null;
  232.  
  233.         if (valorSeleccionado) {
  234.           nombreConVariantes += ` - ${nombreAtributo}: ${valorSeleccionado}`;
  235.         }
  236.  
  237.         // Añadir la clase de vibración al icono del carrito
  238.         const carritoIcon = document.getElementById('carrito-icon');
  239.         carritoIcon.classList.add('shaking');
  240.  
  241.         setTimeout(() => {
  242.           // Eliminar la clase de vibración después de 500 milisegundos (ajusta según sea necesario)
  243.           carritoIcon.classList.remove('shaking');
  244.         }, 500);
  245.       }
  246.  
  247.       const producto = { nombre: nombreConVariantes, precio };
  248.       carrito.push(producto);
  249.  
  250.       const listItem = document.createElement('li');
  251.       listItem.textContent = `${nombreConVariantes} - $${formatearPrecio(producto.precio)}`;
  252.       const eliminarButton = document.createElement('a');
  253.       eliminarButton.innerHTML = '&amp;#xe051;';
  254.       eliminarButton.classList.add('eliminar');
  255.       eliminarButton.addEventListener('click', () => eliminarProductoDelCarrito(producto, listItem));
  256.       listItem.appendChild(eliminarButton);
  257.       carritoLista.appendChild(listItem);
  258.  
  259.       // Actualizar el total
  260.       carritoTotal += precio;
  261.       total.textContent = formatearPrecio(carritoTotal);
  262.  
  263.       // Actualizar el contador del carrito
  264.       carritoContador.textContent = carrito.length;
  265.  
  266.       // Desplazar automáticamente al carrito
  267.       desplazarCarrito();
  268.  
  269.       // Mostrar u ocultar el mensaje de carrito vacío
  270.       mostrarMensajeCarritoVacio();
  271.     }
  272.  
  273.     // Eliminar producto del carrito
  274.     function eliminarProductoDelCarrito(producto, listItem) {
  275.       const index = carrito.indexOf(producto);
  276.       if (index !== -1) {
  277.         carrito.splice(index, 1);
  278.         carritoLista.removeChild(listItem);
  279.         carritoTotal -= producto.precio;
  280.         total.textContent = formatearPrecio(carritoTotal);
  281.  
  282.         // Actualizar el contador del carrito
  283.         carritoContador.textContent = carrito.length;
  284.  
  285.         // Mostrar u ocultar el mensaje de carrito vacío
  286.         mostrarMensajeCarritoVacio();
  287.       }
  288.     }
  289.  
  290.     // Evento para agregar producto al carrito
  291.     productos.forEach((producto, index) => {
  292.       const agregarButton = producto.querySelector('.agregar');
  293.       const info = agregarButton.getAttribute('data-info');
  294.  
  295.       agregarButton.addEventListener('click', () => {
  296.         agregarProductoAlCarrito(info);
  297.       });
  298.     });
  299.  
  300.     // Inicialmente, mostrar el mensaje de carrito vacío
  301.     mostrarMensajeCarritoVacio();
  302.   }
  303.  
  304.   // Evento para enviar detalles del carrito a WhatsApp
  305.   document.addEventListener('DOMContentLoaded', (event) => {
  306.     const enviarWhatsAppButton = document.getElementById('enviar-whatsapp');
  307.     enviarWhatsAppButton.addEventListener('click', () => {
  308.       // Este es el código que "permanece igual"
  309.       const carritoTexto = carrito.map(producto => {
  310.         return `${producto.nombre} - $${formatearPrecio(producto.precio)}`;
  311.       }).join('\n'); // Usamos \n para separar líneas en WhatsApp
  312.  
  313.       const mensajeWhatsApp = '*Mi Pedido:*\n' + carritoTexto + '\n*TOTAL: $' + formatearPrecio(carritoTotal) + '*';
  314.       const whatsappURL = `https://wa.me/529512345678?text=${encodeURIComponent(mensajeWhatsApp)}`;
  315.       window.open(whatsappURL, '_blank');
  316.     });
  317.  
  318.   });
  319.  
  320.   function validarAtributosSeleccionados(index) {
  321.     const selects = document.querySelectorAll(`#atributo${index} select`);
  322.     for (const select of selects) {
  323.       if (select.value === "") {
  324.         alert("Por favor, selecciona todas las opciones antes de agregar al carrito.");
  325.         return false;
  326.       }
  327.     }
  328.     return true;
  329.   }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement