Información para main

This commit is contained in:
2025-12-14 16:10:19 +01:00
commit ce0b6827bf
+515
View File
@@ -0,0 +1,515 @@
<!DOCTYPE html>
<html lang="es">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>POS Food Truck</title>
<style>
body {
font-family: Arial, sans-serif;
margin: 0;
padding: 0;
height: 100vh;
overflow: hidden; /* pantalla fija */
}
/* Header con logos */
header {
background: #e63946;
color: white;
padding: 1rem;
display: flex; /* flexbox */
align-items: center; /* centra verticalmente */
justify-content: space-between; /* izq - centro - der */
}
header h1 {
flex: 1;
text-align: center;
margin: 0;
}
header .logo {
width: 60px;
height: auto;
}
.menu {
height: calc(100vh - 80px);
padding: 1rem;
display: flex;
flex-direction: column;
}
.menu-header {
display: flex;
justify-content: space-between;
align-items: center;
margin-bottom: 1rem;
}
.menu-header h2 { margin: 0; }
.menu-header button {
margin-left: 0.5rem;
background: #457b9d;
color: white;
border: none;
padding: 0.5rem 1rem;
cursor: pointer;
}
.menu-header button:hover { background: #1d3557; }
/* Grid responsivo */
.products {
flex: 1;
display: grid;
grid-template-columns: repeat(auto-fit, minmax(200px, 1fr));
gap: 1rem;
overflow-y: auto;
}
.item {
border: 1px solid #ccc;
border-radius: 8px;
padding: 0.5rem;
text-align: center;
display: flex;
flex-direction: column;
justify-content: space-between;
align-items: center;
width: 12em;
height: 12em;
align-items:center;
}
.item img {
width: 7em;
height: 7em;
object-fit: cover;
border-radius: 5px;
cursor: pointer;
}
.controls {
display: flex; /* inicialmente oculto, se muestra al tocar imagen */
margin-top: 0.5rem;
justify-content: center;
align-items: center;
gap: 0.5rem;
}
.controls span { font-weight: bold; }
.controls button {
background: #457b9d;
color: white;
border: none;
padding: 0.25rem 0.5rem;
cursor: pointer;
}
.controls button:hover { background: #1d3557; }
/* Popup factura */
.popup {
display: none;
position: fixed;
top: 0; left: 0;
width: 100%; height: 100%;
background: rgba(0,0,0,0.5);
justify-content: center;
align-items: center;
}
.popup-content {
background: white;
padding: 2rem;
border-radius: 10px;
width: 300px;
max-height: 80vh;
overflow-y: auto;
box-shadow: 0 8px 24px rgba(0,0,0,0.2);
}
.popup-content h3 { margin-top: 0; }
.close {
background: #e63946;
color: white;
border: none;
padding: 0.5rem;
cursor: pointer;
float: right;
}
.confirm {
margin-top: 1rem;
background: #2a9d8f;
color: white;
border: none;
padding: 0.5rem 1rem;
cursor: pointer;
width: 100%;
border-radius: 6px;
}
.confirm:hover { background: #23867b; }
.payment-options {
display: flex;
gap: 1rem;
margin: 0.5rem 0 0.25rem;
}
.payment-options label {
cursor: pointer;
user-select: none;
}
#paymentDetails img {
display: block;
margin-top: 0.5rem;
}
#paymentDetails input[type="number"] {
width: 100%;
padding: 0.5rem;
box-sizing: border-box;
border: 1px solid #ccc;
border-radius: 6px;
}
#changeText {
font-weight: bold;
margin-top: 0.5rem;
}
</style>
</head>
<body>
<header>
<img src="imagenes/logombirria.png" alt="Logo Izquierdo" class="logo">
<h1>PICADITAS MASTER BIRRIA</h1>
<img src="imagenes/logombirria.png" alt="Logo Derecho" class="logo">
</header>
<div class="menu">
<div class="menu-header">
<h2>Menú</h2>
<div>
<button onclick="generateInvoice()">Generar Factura</button>
<!-- Botón de compartir eliminado. Compartimos al confirmar pago -->
</div>
</div>
<div class="products" id="menuProducts"></div>
</div>
<!-- Popup Factura -->
<div class="popup" id="popup">
<div class="popup-content">
<button class="close" onclick="closePopup()">X</button>
<div id="invoice"></div>
<!-- Nombre del cliente -->
<h3>Datos del cliente</h3>
<input type="text" id="clientName" placeholder="Nombre del cliente" style="width:100%; padding:0.5rem; margin-bottom:1rem;">
<!-- Selección de forma de pago -->
<h3>Forma de pago</h3>
<div class="payment-options">
<label><input type="radio" name="payment" value="yappy" onclick="showPayment()"> Yappy</label>
<label><input type="radio" name="payment" value="efectivo" onclick="showPayment()"> Efectivo</label>
</div>
<div id="paymentDetails" style="margin-top:0.5rem;"></div>
<button class="confirm" onclick="confirmPayment()">Confirmar pago y compartir</button>
</div>
</div>
<!--<div class="popup" id="popup">
<div class="popup-content">
<button class="close" onclick="closePopup()">X</button>
<div id="invoice"></div>
<h3>Forma de pago</h3>
<div class="payment-options">
<label><input type="radio" name="payment" value="yappy" onclick="showPayment()"> Yappy</label>
<label><input type="radio" name="payment" value="efectivo" onclick="showPayment()"> Efectivo</label>
</div>
<div id="paymentDetails" style="margin-top:0.5rem;"></div>
<button class="confirm" onclick="confirmPayment()">Confirmar pago y compartir</button>
</div>
</div>-->
<script src="https://cdn.jsdelivr.net/npm/html2canvas@1.4.1/dist/html2canvas.min.js"></script>
<script>
// Productos actuales
const products = [
{ id: 1, name: "HAMBURGUESA SENCILLA", price: 4, img: "imagenes/hsimple.jpg" , qty: 0},
{ id: 2, name: "HAMBURGUESA COMPLETA", price: 6, img: "imagenes/hcompleta.jpg", qty: 0 },
{ id: 3, name: "CHORIPAN ARGENTINO", price: 5, img: "imagenes/choripan.jpg" , qty: 0},
{ id: 4, name: "HOT DOG TRADICIONAL", price: 2.5, img: "imagenes/pizza.png", qty: 0 },
{ id: 5, name: "HOT DOG ESPECIAL", price: 3.5, img: "imagenes/hotdog.png" , qty: 0},
{ id: 6, name: "10 ALITAS GRANDES", price: 10, img: "imagenes/nachos.png" , qty: 0},
{ id: 7, name: "15 ALITAS GRANDES", price: 16.5, img: "imagenes/empanada.png", qty: 0 },
{ id: 8, name: "20 ALITAS GRANDES", price: 20, img: "imagenes/alitas.png" , qty: 0},
{ id: 9, name: "PICADITA PEQUEÑA", price: 3.5, img: "imagenes/helado.png", qty: 0 },
{ id: 10, name: "PICADITA GRANDE", price: 5, img: "imagenes/helado.png", qty: 0 },
{ id: 11, name: "PICADITA FAMILIAR", price: 15, img: "imagenes/helado.png", qty: 0 }
];
// Renderizado del menú
function renderMenu() {
const menu = document.getElementById("menuProducts");
menu.innerHTML = "";
products.forEach(p => {
const div = document.createElement("div");
div.className = "item";
div.innerHTML = `
<h3 style="font-size: 0.8em; margin-block-start: 0.5em; margin-block-end: 0.5em;">${p.name}</h3>
<img src="${p.img}" alt="${p.name}" onclick="toggleControls(${p.id})">
<p style="margin-block-start: 0.5em; margin-block-end: 0.5em;">$${p.price.toFixed(2)}</p>
<div class="controls" id="controls-${p.id}">
<button onclick="updateQty(${p.id}, -1)">-</button>
<span id="qty-${p.id}">${p.qty}</span>
<button onclick="updateQty(${p.id}, 1)">+</button>
</div>
`;
menu.appendChild(div);
});
}
function toggleControls(id) {
const controls = document.getElementById(`controls-${id}`);
controls.style.display = controls.style.display === "flex" ? "none" : "flex";
}
function updateQty(id, change) {
const product = products.find(p => p.id === id);
product.qty = Math.max(0, product.qty + change);
document.getElementById(`qty-${id}`).textContent = product.qty;
}
// Generar factura (abre popup)
function generateInvoice() {
const invoice = document.getElementById('invoice');
invoice.innerHTML = "<h3>Factura</h3>";
let total = 0;
products.forEach(item => {
if (item.qty > 0) {
total += item.price * item.qty;
invoice.innerHTML += `<p>${item.name} x${item.qty} - $${(item.price * item.qty).toFixed(2)}</p>`;
}
});
invoice.innerHTML += `<hr><p><strong>Total: $${total.toFixed(2)}</strong></p>`;
document.getElementById("popup").style.display = "flex";
window.invoiceTotal = total;
// Reset campos
document.getElementById("clientName").value = "";
const radios = document.querySelectorAll('input[name="payment"]');
radios.forEach(r => r.checked = false);
document.getElementById("paymentDetails").innerHTML = "";
}
function showPayment() {
const selected = document.querySelector('input[name="payment"]:checked').value;
const details = document.getElementById("paymentDetails");
details.innerHTML = "";
if (selected === "yappy") {
details.innerHTML = `
<p>Realizar pago vía <strong>Yappy</strong></p>
<p>Número: <strong>61988350</strong></p>
<img src="imagenes/yappy.png" alt="Yappy" style="width:100px;">
`;
} else if (selected === "efectivo") {
details.innerHTML = `
<p>Ingrese monto recibido:</p>
<input type="number" id="cashInput" placeholder="Monto recibido" oninput="calcChange()">
<p id="changeText"></p>
`;
}
}
function calcChange() {
const received = parseFloat(document.getElementById("cashInput").value);
const total = window.invoiceTotal || 0;
if (!isNaN(received)) {
const change = received - total;
document.getElementById("changeText").textContent =
change >= 0 ? `Cambio: $${change.toFixed(2)}` : "Monto insuficiente";
} else {
document.getElementById("changeText").textContent = "";
}
}
async function confirmPayment() {
const selected = document.querySelector('input[name="payment"]:checked');
const clientName = document.getElementById("clientName").value.trim();
if (!selected) {
alert("Seleccione una forma de pago.");
return;
}
if (!clientName) {
alert("Ingrese el nombre del cliente.");
return;
}
let paymentInfo = "";
if (selected.value === "efectivo") {
const received = parseFloat(document.getElementById("cashInput")?.value);
if (isNaN(received) || received < window.invoiceTotal) {
alert("Monto insuficiente para cubrir el total.");
return;
}
const change = received - window.invoiceTotal;
paymentInfo = `Pago en efectivo: recibido $${received.toFixed(2)}, cambio $${change.toFixed(2)}`;
} else {
paymentInfo = "Pago vía Yappy (61988350)";
}
// Añadir nombre y forma de pago al invoice antes de compartir
const invoice = document.getElementById('invoice');
invoice.innerHTML += `<hr><p><strong>Cliente:</strong> ${clientName}</p>`;
invoice.innerHTML += `<p><strong>Forma de pago:</strong> ${paymentInfo}</p>`;
// Generar imagen y compartir
const canvas = await html2canvas(invoice);
const blob = await new Promise(resolve => canvas.toBlob(resolve, "image/png"));
const file = new File([blob], "pedido.png", { type: "image/png" });
if (navigator.share) {
try {
await navigator.share({
files: [file],
title: "Pedido Food Truck",
text: `Pedido de ${clientName} - ${paymentInfo}`
});
} catch (err) {
console.warn("Compartir cancelado o falló:", err);
}
} else {
// Fallback: descarga
const url = URL.createObjectURL(blob);
const a = document.createElement("a");
a.href = url;
a.download = "pedido.png";
a.click();
URL.revokeObjectURL(url);
}
// Limpiar cantidades
products.forEach(p => p.qty = 0);
renderMenu();
// Cerrar popup
closePopup();
alert(`Pago confirmado ✅\nCliente: ${clientName}\n${paymentInfo}`);
}
/*function generateInvoice() {
const invoice = document.getElementById('invoice');
invoice.innerHTML = "<h3>Factura</h3>";
let total = 0;
products.forEach(item => {
if (item.qty > 0) {
total += item.price * item.qty;
invoice.innerHTML += `<p>${item.name} x${item.qty} - $${(item.price * item.qty).toFixed(2)}</p>`;
}
});
invoice.innerHTML += `<hr><p><strong>Total: $${total.toFixed(2)}</strong></p>`;
document.getElementById("popup").style.display = "flex";
window.invoiceTotal = total;
// Limpiar selección previa de pago
const radios = document.querySelectorAll('input[name="payment"]');
radios.forEach(r => r.checked = false);
document.getElementById("paymentDetails").innerHTML = "";
}
function showPayment() {
const selected = document.querySelector('input[name="payment"]:checked').value;
const details = document.getElementById("paymentDetails");
details.innerHTML = "";
if (selected === "yappy") {
details.innerHTML = `
<p>Realizar pago vía <strong>Yappy</strong></p>
<p>Número: <strong>61988350</strong></p>
<img src="imagenes/yappy.png" alt="Yappy" style="width:100px;">
`;
} else if (selected === "efectivo") {
details.innerHTML = `
<p>Ingrese monto recibido:</p>
<input type="number" id="cashInput" placeholder="Monto recibido" oninput="calcChange()">
<p id="changeText"></p>
`;
}
}
function calcChange() {
const received = parseFloat(document.getElementById("cashInput").value);
const total = window.invoiceTotal || 0;
if (!isNaN(received)) {
const change = received - total;
document.getElementById("changeText").textContent =
change >= 0 ? `Cambio: $${change.toFixed(2)}` : "Monto insuficiente";
} else {
document.getElementById("changeText").textContent = "";
}
}
// Confirmar pago y compartir en el mismo gesto
async function confirmPayment() {
const selected = document.querySelector('input[name="payment"]:checked');
if (!selected) {
alert("Seleccione una forma de pago.");
return;
}
// Validación según forma de pago
let paymentInfo = "";
if (selected.value === "efectivo") {
const received = parseFloat(document.getElementById("cashInput")?.value);
if (isNaN(received) || received < window.invoiceTotal) {
alert("Monto insuficiente para cubrir el total.");
return;
}
const change = received - window.invoiceTotal;
paymentInfo = `Pago en efectivo: recibido $${received.toFixed(2)}, cambio $${change.toFixed(2)}`;
} else {
paymentInfo = "Pago vía Yappy (61988350)";
}
// Generar imagen y compartir (dentro del mismo click para evitar el error del gesto)
const invoice = document.getElementById('invoice');
const canvas = await html2canvas(invoice);
const blob = await new Promise(resolve => canvas.toBlob(resolve, "image/png"));
const file = new File([blob], "pedido.png", { type: "image/png" });
if (navigator.share) {
try {
await navigator.share({
files: [file],
title: "Pedido Food Truck",
text: "Aquí está tu pedido"
});
} catch (err) {
// Si el usuario cancela el compartir o hay error, continuamos con el flujo
console.warn("Compartir cancelado o falló:", err);
}
} else {
// Fallback: descargar imagen
const url = URL.createObjectURL(blob);
const a = document.createElement("a");
a.href = url;
a.download = "pedido.png";
a.click();
URL.revokeObjectURL(url);
}
// Limpiar cantidades
products.forEach(p => p.qty = 0);
renderMenu();
// Cerrar popup
closePopup();
// Aviso de confirmación
alert(`Pago confirmado ✅\n${paymentInfo}`);
}*/
function closePopup() {
document.getElementById("popup").style.display = "none";
}
// Inicializar
renderMenu();
</script>
</body>
</html>