diff --git a/client/src/components/new-recipe/RecipeImageUpload.tsx b/client/src/components/new-recipe/RecipeImageUpload.tsx new file mode 100644 index 0000000..893e266 --- /dev/null +++ b/client/src/components/new-recipe/RecipeImageUpload.tsx @@ -0,0 +1,64 @@ + +import { useEffect, useState } from 'react' +import type { ChangeEvent } from 'react' + +export function RecipeImageUpload() { + const [image, setImage] = useState(null) + const [preview, setPreview] = useState(null) + + useEffect(() => { + if (!image) { + setPreview(null) + return + } + + const url = URL.createObjectURL(image) + setPreview(url) + + return () => URL.revokeObjectURL(url) + }, [image]) + + const handleImageChange = (event: ChangeEvent) => { + const file = event.target.files?.[0] + if (!file) return + + if (!['image/jpeg', 'image/png', 'image/webp'].includes(file.type)) { + alert('Velg et JPG-, PNG- eller WebP-bilde.') + return + } + + if (file.size > 5 * 1024 * 1024) { + alert('Bildet kan ikke være større enn 5 MB.') + return + } + + setImage(file) + } + + return ( +
+ + + +
+ ) +} diff --git a/client/src/components/new-recipe/RecipeStep1.tsx b/client/src/components/new-recipe/RecipeStep1.tsx index 3dd8b21..ed69a9e 100644 --- a/client/src/components/new-recipe/RecipeStep1.tsx +++ b/client/src/components/new-recipe/RecipeStep1.tsx @@ -1,9 +1,13 @@ + +import { useState } from 'react' import type { Dispatch, SetStateAction } from 'react' import Rating from '@mui/material/Rating' import { Button } from '../ui/Button' import { Field } from '../ui/Field' import { Input, Textarea } from '../ui/Input' import { Tag } from '../ui/Tag' +import { ImageUpload } from '../ui/ImageUpload' +import TagDialog from './TagDialog' import type { RecipeFormData } from '../../routes/NewRecipePage' // Sånn at informasjonen blir lagret mellom stegene @@ -13,45 +17,87 @@ type RecipeStep1Props = { onNext: () => void } +const MAX_TAGS = 6 + +const categories = [ + 'Frokost', + 'Lunsj', + 'Middag', + 'Dessert', + 'Snacks', + 'Drikke', +] -const categories = ['Frokost', 'Lunsj', 'Middag', 'Dessert', 'Snacks', 'Drikke'] +const dietaryTags = [ + 'Vegetar', + 'Vegansk', + 'Pescetar', + 'Glutenfri', + 'Laktosefri', + 'Under 30 min', +] -const dietaryTags = ['Vegetar', 'Vegansk', 'Pescetar', 'Glutenfri', 'Laktosefri', 'Annet +'] +export default function RecipeStep1({ + data, + setData, + onNext, +}: RecipeStep1Props) { + const [tagDialogOpen, setTagDialogOpen] = useState(false) -export default function RecipeStep1({ data, setData, onNext }: RecipeStep1Props) { - // Oppdaterer ETT felt i oppskriften, f.eks. update('title', 'Pasta'). - // Erstatter alle setData({ ...data, felt: verdi }) og sørger for at resten beholdes. - const update = (key: K, value: RecipeFormData[K]) => + // Oppdaterer ett felt i oppskriften og beholder resten + const update = ( + key: K, + value: RecipeFormData[K], + ) => { setData((prev) => ({ ...prev, [key]: value })) + } - // Klikk på en valgt tag fjerner den, klikk på en ikke-valgt tag legger den til - const toggleTag = (tag: string) => - update( - 'tags', - data.tags.includes(tag) ? data.tags.filter((item) => item !== tag) : [...data.tags, tag], - ) + // Legger til eller fjerner en tag (maks 6 totalt) + const toggleTag = (tag: string) => { + if (data.tags.includes(tag)) { + update( + 'tags', + data.tags.filter((item) => item !== tag), + ) + } else if (data.tags.length < MAX_TAGS) { + update('tags', [...data.tags, tag]) + } + } + + // Tags som er valgt fra dialogen + const extraTags = data.tags.filter( + (tag) => !dietaryTags.includes(tag), + ) return (
-

Lag din egen oppskrift og del den med andre.

+

+ Lag din egen oppskrift og del den med andre. +

{/* VENSTRE SIDE */}
- + update('imageFile', file)} + /> - +