Zapamatované oblíbené
V této aplikaci si můžete označit oblíbené kapely hvězdičkou. Klikněte ale na Spustit a hvězdičky jsou pryč: stav žije jen tak dlouho jako stránka. V kurzu JavaScriptu jste si takové věci ukládali do localStorage. V Reactu na to potřebujete dva kroky.
Ukládání. Zápis do localStorage se děje mimo React, takže je to práce pro efekt. Má se spustit pokaždé, když se oblíbené změní, a jeho závislostí je proto oblibene. localStorage uchovává jen text, takže pole se do něj uloží jako JSON:
useEffect(() => {
localStorage.setItem("oblibene", JSON.stringify(oblibene));
}, [oblibene]);Čtení. Při spuštění aplikace mají oblíbené přijít z localStorage, aby je ukázalo hned první vykreslení. Hodnota, se kterou stav začíná, je argument useState. React ho ale použije jen při prvním vykreslení, takže číst a převádět JSON při každém vykreslení by byla zbytečná práce. Dejte proto useState místo hodnoty funkci. React ji zavolá jen jednou, pro první vykreslení, a stav začne tím, co vrátí:
const [oblibene, setOblibene] = useState(() => {
const ulozene = localStorage.getItem("oblibene");
return ulozene === null ? [] : JSON.parse(ulozene);
});getItem() vrátí null, když nic uložené není, třeba když někdo aplikaci otevře poprvé. Oblíbené pak začnou jako prázdné pole.
Stejně jako v kurzu JavaScriptu každé kliknutí na Spustit stránku spustí znovu, jako by se znovu načetla, a stránka najde, co si uložila při dřívějších spuštěních. Tlačítko Smazat uložená data v konzoli to smaže.
Typické chyby:
- Pole uložené bez
JSON.stringify():localStoragez něj udělá text2,4, kterýJSON.parse()zpátky nepřečte. - Čtení bez kontroly na
null:JSON.parse(null)vrátínullaoblibene.includes()pak skončí chybouTypeError.
Jak psát:
Pokyny
Ukládejte oblíbené: přidejte efekt se závislostmi [oblibene], který je uloží do localStorage pod klíčem oblibene jako JSON.
Při spuštění aplikace je načtěte: dejte useState funkci, která vrátí uložené oblíbené, nebo [], když nic uložené není. Vyzkoušejte to: označte dvě kapely a klikněte na Spustit. Hvězdičky zůstanou.