feat(storefront): barra de navegación desktop con categorías, personajes, ayuda y ubicación
- Desktop xl+: las 6 categorías raíz directo en la barra con desplegable de subcategorías; lg-xl mantiene "Departamentos"; "Personajes" (colecciones) y "Ayuda" a la derecha; hamburguesa solo en mobile. - "Enviar a <nombre> · <ciudad>" (location-store persistido) que precarga departamento/ciudad en el checkout; "Hola X / Mi cuenta" y "Cambios y devoluciones" en xl+. - Header compacto al hacer scroll en lg+ (histéresis 160/40px). - Fix de menús (también en DepartmentsMegaMenu, ya presente en prod): el click de mouse ya no cierra el menú recién abierto por hover (keepOpenAfterHover) y el hover solo reacciona a pointerType "mouse", así el mouseleave sintético de touch no autocierra en tablets. Revisado por el subagente frontend-critic (3 hallazgos, todos corregidos y re-verificados) + Playwright contra build de producción local: sin solapes a 1024/1280/1440/1920, click real, touch, mobile 390/320 sin cambios. Co-Authored-By: Claude Opus 5.5 <[email protected]> Claude-Session: https://claude.ai/code/session_018r19s4H8MBGegqToqw5guP
This commit is contained in:
1 parent
503f56977d
commit
e6f031a366
4 files changed
+399
-33
No files matched your search
@@ -3,12 +3,13 @@
|
||||
import Image from "next/image";
|
||||
import Link from "next/link";
|
||||
import { ArrowLeft, Landmark, MapPin, MessageCircle, Truck } from "lucide-react";
|
||||
import { type FormEvent, useState } from "react";
|
||||
import { type FormEvent, useEffect, useState } from "react";
|
||||
import { Button } from "@/components/ui/button";
|
||||
import { Input } from "@/components/ui/input";
|
||||
import { ciudadesPorDepartamento, departamentos } from "@/lib/data/colombia";
|
||||
import { formatMoney } from "@/lib/utils";
|
||||
import { useCartStore } from "@/store/cart-store";
|
||||
import { useLocationStore } from "@/store/location-store";
|
||||
|
||||
const SELECT_CLASS =
|
||||
"h-12 w-full rounded-full border border-slate-200 bg-white px-5 text-sm text-slate-950 outline-none transition focus:border-cyan-500 focus:ring-4 focus:ring-cyan-300/30 disabled:opacity-50";
|
||||
@@ -72,12 +73,24 @@ export function CheckoutClient() {
|
||||
const [docType, setDocType] = useState<"CC" | "CE" | "NIT" | "TI" | "PP">("CC");
|
||||
const [docNumber, setDocNumber] = useState("");
|
||||
|
||||
// Ciudad elegida en el header ("Enviar a ... · Cali"): precarga el
|
||||
// departamento/ciudad solo si el cliente todavia no eligio nada aca.
|
||||
const savedDepartmentId = useLocationStore((state) => state.departmentId);
|
||||
const savedCityId = useLocationStore((state) => state.cityId);
|
||||
const locationHydrated = useLocationStore((state) => state.hasHydrated);
|
||||
const saveLocation = useLocationStore((state) => state.setLocation);
|
||||
useEffect(() => {
|
||||
if (!locationHydrated || !savedDepartmentId || !savedCityId) return;
|
||||
setForm((current) => (current.departmentId ? current : { ...current, departmentId: savedDepartmentId, cityId: savedCityId }));
|
||||
}, [locationHydrated, savedDepartmentId, savedCityId]);
|
||||
|
||||
const itemsSubtotal = items.reduce((sum, item) => sum + (item.product.price ?? 0) * item.quantity, 0);
|
||||
const currency = items[0]?.product.currency;
|
||||
|
||||
async function submitAddress(event: FormEvent) {
|
||||
event.preventDefault();
|
||||
if (!cartId || !selectedCiudad || !selectedDepartamento) return;
|
||||
saveLocation(selectedDepartamento.id, selectedCiudad.id);
|
||||
setLoading(true);
|
||||
setError(null);
|
||||
try {
|
||||
|
||||
Reference in new issue
Block a user