195 lines
No EOL
7.2 KiB
JavaScript
195 lines
No EOL
7.2 KiB
JavaScript
// Statisk produktkatalog - bruker hardkodede data for å fokusere på MVC-arkitektur
|
|
// fremfor backend-integrasjon i denne fasen av prosjektet
|
|
const products = [
|
|
{
|
|
id: 1,
|
|
name: "Trådløse Hodetelefoner",
|
|
price: 99.99,
|
|
description: "Høykvalitets trådløse hodetelefoner med støydemping og 30 timer batteritid.",
|
|
image: "🎧", // Bruker emoji for enkelhet - unngår bildefilhåndtering
|
|
category: "Elektronikk"
|
|
},
|
|
{
|
|
id: 2,
|
|
name: "Smartklokke",
|
|
price: 199.99,
|
|
description: "Funksjonsrik smartklokke med treningssporing, pulsmåler og GPS.",
|
|
image: "⌚",
|
|
category: "Elektronikk"
|
|
},
|
|
{
|
|
id: 3,
|
|
name: "Kaffetrakter",
|
|
price: 79.99,
|
|
description: "Programmerbar kaffetrakter med termokanne og automatisk bryggtimer.",
|
|
image: "☕",
|
|
category: "Hjem"
|
|
},
|
|
{
|
|
id: 4,
|
|
name: "Ryggsekk",
|
|
price: 49.99,
|
|
description: "Slitesterke laptop-ryggsekk med flere rom og vannavstøtende materiale.",
|
|
image: "🎒",
|
|
category: "Livsstil"
|
|
},
|
|
{
|
|
id: 5,
|
|
name: "Skrivebordslampe",
|
|
price: 39.99,
|
|
description: "LED skrivebordslampe med justerbar lysstyrke og USB-ladeport.",
|
|
image: "💡",
|
|
category: "Hjem"
|
|
},
|
|
{
|
|
id: 6,
|
|
name: "Trådløs Mus",
|
|
price: 29.99,
|
|
description: "Ergonomisk trådløs mus med presis sporing og lang batteritid.",
|
|
image: "🖱️",
|
|
category: "Elektronikk"
|
|
}
|
|
];
|
|
|
|
// Handlekurv lagres i minnet som et array - enkelt å arbeide med og testbar
|
|
// Hver handlekurvvare inneholder productId, quantity og en referanse til produktobjektet
|
|
let cart = [];
|
|
|
|
// Getter-funksjoner for produktdata - gir kontrollert tilgang til data
|
|
// og muliggjør fremtidig validering eller transformasjon
|
|
function getAllProducts() {
|
|
return products;
|
|
}
|
|
|
|
// Konverterer id til integer fordi URL-parametere alltid er strings
|
|
// Bruker find() for å returnere første match eller undefined hvis ikke funnet
|
|
function getProductById(id) {
|
|
return products.find(product => product.id === parseInt(id));
|
|
}
|
|
|
|
// Legger til produkt i handlekurv med intelligent sammenslåing
|
|
// quantity = 1 som standard fordi de fleste klikk legger til én vare
|
|
function addToCart(productId, quantity = 1) {
|
|
const product = getProductById(productId);
|
|
// Kritisk validering - forhindrer at ugyldig produkter legges til
|
|
// Returnerer false for å signalisere feil til kallende kode
|
|
if (!product) return false;
|
|
|
|
// Sjekker om produktet allerede finnes for å unngå duplikater
|
|
// Øker quantity istedenfor å lage nye poster - bedre brukeropplevelse
|
|
const existingItem = cart.find(item => item.productId === productId);
|
|
|
|
if (existingItem) {
|
|
// Øker eksisterende quantity - intuitivt for brukeren
|
|
existingItem.quantity += quantity;
|
|
} else {
|
|
// Lager ny handlekurvpost med både ID og fullt produktobjekt
|
|
// product-referansen unngår gjentatte oppslag senere
|
|
cart.push({
|
|
productId: productId, // For identifikasjon og sammenligning
|
|
quantity: quantity, // Hvor mange brukeren vil ha
|
|
product: product // Full produktinfo for visning
|
|
});
|
|
}
|
|
|
|
// Persisterer umiddelbart for å unngå tap av data
|
|
saveCartToStorage();
|
|
return true; // Signaliserer suksess til UI-lag
|
|
}
|
|
|
|
// Fjerner hele produktlinjen fra handlekurv uavhengig av quantity
|
|
// Bruker filter() for å lage nytt array - funksjonell programmering
|
|
function removeFromCart(productId) {
|
|
cart = cart.filter(item => item.productId !== productId);
|
|
saveCartToStorage(); // Persister endring umiddelbart
|
|
}
|
|
|
|
// Oppdaterer antall av eksisterende handlekurvvare
|
|
// Håndterer edge case hvor quantity blir 0 eller negativ
|
|
function updateCartQuantity(productId, quantity) {
|
|
const item = cart.find(item => item.productId === productId);
|
|
if (item) {
|
|
// Forretningsregel: quantity <= 0 betyr fjern produktet helt
|
|
// Mer intuitivt enn å ha 0 varer i handlekurven
|
|
if (quantity <= 0) {
|
|
removeFromCart(productId);
|
|
} else {
|
|
item.quantity = quantity;
|
|
saveCartToStorage();
|
|
}
|
|
}
|
|
// Ingen else - ignorerer oppdateringer til ikke-eksisterende varer
|
|
}
|
|
|
|
// Returnerer hele handlekurv-arrayet for visning
|
|
// Andre komponenter kan ikke direkte mutere cart-variabelen
|
|
function getCart() {
|
|
return cart;
|
|
}
|
|
|
|
// Beregner total pris for alle varer i handlekurv
|
|
// Bruker reduce() for elegant summering av pris * quantity
|
|
function getCartTotal() {
|
|
return cart.reduce((total, item) => {
|
|
return total + (item.product.price * item.quantity);
|
|
}, 0); // Starter med 0 som akkumulator
|
|
}
|
|
|
|
// Teller totalt antall individuelle varer (ikke unike produkter)
|
|
// Eksempel: 2 hodetelefoner + 3 kaffetraktere = 5 varer totalt
|
|
function getCartItemCount() {
|
|
return cart.reduce((count, item) => count + item.quantity, 0);
|
|
}
|
|
|
|
// Tømmer hele handlekurven - brukes ved utsjekking eller manuell tømming
|
|
// Setter cart til tomt array istedenfor å mutere eksisterende
|
|
function clearCart() {
|
|
cart = [];
|
|
saveCartToStorage(); // Persister tom handlekurv
|
|
}
|
|
|
|
// Lagrer handlekurv til nettleserens localStorage for persistering
|
|
// Try-catch fordi localStorage kan feile i private browsing eller ved kvotaoverskridelse
|
|
function saveCartToStorage() {
|
|
try {
|
|
// Konverterer JavaScript-objekt til JSON-string for lagring
|
|
localStorage.setItem('webstore_cart', JSON.stringify(cart));
|
|
} catch (error) {
|
|
// Logger feil men lar appen fortsette å fungere
|
|
// Graceful degradation - handlekurv fungerer fortsatt i denne sesjonen
|
|
console.error('Feil ved lagring av handlekurv til localStorage:', error);
|
|
}
|
|
}
|
|
|
|
// Laster handlekurv fra localStorage og rekonstruerer produktreferanser
|
|
// Håndterer scenarioer hvor lagret data kan være korrupt eller utdatert
|
|
function loadCartFromStorage() {
|
|
try {
|
|
const savedCart = localStorage.getItem('webstore_cart');
|
|
// Sjekker om data finnes før parsing - første gangs brukere har tom localStorage
|
|
if (savedCart) {
|
|
const parsedCart = JSON.parse(savedCart);
|
|
// Rekonstruerer produktreferanser fordi localStorage kun lagrer JSON
|
|
// Fallback til "Ukjent Produkt" hvis produktet er fjernet fra katalogen
|
|
return parsedCart.map(item => ({
|
|
...item,
|
|
// Kritisk: Sikrer at produktreferanse alltid finnes
|
|
// Håndterer tilfeller hvor produktkatalog endres mellom sesjoner
|
|
product: products.find(p => p.id === item.productId) ||
|
|
{ id: item.productId, name: 'Ukjent Produkt', price: 0 }
|
|
}));
|
|
}
|
|
} catch (error) {
|
|
// JSON parsing kan feile hvis data er korrupt
|
|
// Logger feil og returnerer tom array som fallback
|
|
console.error('Feil ved lasting av handlekurv fra localStorage:', error);
|
|
}
|
|
// Returnerer tom array som sikker fallback
|
|
return [];
|
|
}
|
|
|
|
// Initialiserer handlekurv ved appstart
|
|
// Setter cart-variabelen basert på lagret data eller tom array
|
|
function initializeCart() {
|
|
cart = loadCartFromStorage();
|
|
} |