refactor: seperate irrelevant logic

This commit is contained in:
MAZE 2023-10-20 17:05:46 +03:30
parent daee7465bc
commit f1688cb53c
4 changed files with 89 additions and 59 deletions

View file

@ -0,0 +1,63 @@
import { useMemo } from 'react';
import { useShallow } from 'zustand/react/shallow';
import { BiSolidHeart } from 'react-icons/bi/index';
import { useSoundStore } from '@/store';
import { Container } from '@/components/container';
import { StoreConsumer } from '@/components/store-consumer';
import { Buttons } from '@/components/buttons';
import { Categories } from '@/components/categories';
import { sounds } from '@/data/sounds';
interface Sound {
src: string;
label: string;
id: string;
icon: React.ReactNode;
}
export function App() {
const categories = useMemo(() => sounds.categories, []);
const favorites = useSoundStore(useShallow(state => state.getFavorites()));
const favoriteSounds = useMemo(() => {
const favoriteSounds = categories
.map(category => category.sounds)
.flat()
.filter(sound => favorites.includes(sound.id));
/**
* Reorder based on the order of favorites
*/
return favorites.map(favorite =>
favoriteSounds.find(sound => sound.id === favorite),
);
}, [favorites, categories]);
const allCategories = useMemo(() => {
const favorites = [];
if (favoriteSounds.length) {
favorites.push({
icon: <BiSolidHeart />,
id: 'favorites',
sounds: favoriteSounds as Array<Sound>,
title: 'Favorites',
});
}
return [...favorites, ...categories];
}, [favoriteSounds, categories]);
return (
<StoreConsumer>
<Container>
<Buttons />
<Categories categories={allCategories} />
</Container>
</StoreConsumer>
);
}

View file

@ -0,0 +1 @@
export { App } from './app';

View file

@ -1,65 +1,31 @@
import { useMemo } from 'react';
import { useShallow } from 'zustand/react/shallow';
import { BiSolidHeart } from 'react-icons/bi/index';
import { AnimatePresence } from 'framer-motion';
import { useSoundStore } from '@/store';
import { Container } from '@/components/container';
import { StoreConsumer } from '../store-consumer';
import { Category } from '@/components/category';
import { Buttons } from '@/components/buttons';
import { sounds } from '@/data/sounds';
export function Categories() {
const categories = useMemo(() => sounds.categories, []);
const favorites = useSoundStore(useShallow(state => state.getFavorites()));
const favoriteSounds = useMemo(() => {
const favoriteSounds = categories
.map(category => category.sounds)
.flat()
.filter(sound => favorites.includes(sound.id));
/**
* Reorder based on the order of favorites
*/
return favorites.map(favorite =>
favoriteSounds.find(sound => sound.id === favorite),
);
}, [favorites, categories]);
return (
<StoreConsumer>
<Container>
<Buttons />
<div>
<AnimatePresence initial={false}>
{!!favoriteSounds.length && (
<Category
functional={false}
icon={<BiSolidHeart />}
id="favorites"
title="Favorites"
sounds={
favoriteSounds as Array<{
src: string;
label: string;
interface CategoriesProps {
categories: Array<{
id: string;
title: string;
icon: React.ReactNode;
}>
}
/>
)}
sounds: Array<{
label: string;
src: string;
icon: React.ReactNode;
id: string;
}>;
}>;
}
export function Categories({ categories }: CategoriesProps) {
return (
<AnimatePresence initial={false}>
{categories.map(category => (
<Category {...category} key={category.id} />
<Category
functional={category.id !== 'favorites'}
{...category}
key={category.id}
/>
))}
</AnimatePresence>
</div>
</Container>
</StoreConsumer>
);
}

View file

@ -2,13 +2,13 @@
import Layout from '@/layouts/layout.astro';
import { Hero } from '@/components/hero';
import { Categories } from '@/components/categories';
import { App } from '@/components/app';
---
<Layout title="Welcome to Astro.">
<main>
<Hero />
<Categories client:load />
<App client:load />
</main>
</Layout>