mirror of
				https://github.com/remvze/moodist.git
				synced 2025-11-04 03:27:03 -05:00 
			
		
		
		
	feat: add icon for sounds
This commit is contained in:
		
							parent
							
								
									17d1b23c8f
								
							
						
					
					
						commit
						199400446c
					
				@ -1,27 +1,12 @@
 | 
				
			|||||||
import { BiSolidTree } from 'react-icons/bi/index';
 | 
					 | 
				
			||||||
import { FaCity } from 'react-icons/fa/index';
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
import { Container } from '@/components/container';
 | 
					import { Container } from '@/components/container';
 | 
				
			||||||
import { Category } from '@/components/category';
 | 
					import { Category } from '@/components/category';
 | 
				
			||||||
import { PlayButton } from '@/components/play-button';
 | 
					import { PlayButton } from '@/components/play-button';
 | 
				
			||||||
import { PlayProvider } from '@/contexts/play';
 | 
					import { PlayProvider } from '@/contexts/play';
 | 
				
			||||||
 | 
					
 | 
				
			||||||
interface CategoriesProps {
 | 
					import { sounds } from '@/data/sounds';
 | 
				
			||||||
  categories: Array<{
 | 
					 | 
				
			||||||
    id: string;
 | 
					 | 
				
			||||||
    title: string;
 | 
					 | 
				
			||||||
    sounds: Array<{
 | 
					 | 
				
			||||||
      label: string;
 | 
					 | 
				
			||||||
      src: string;
 | 
					 | 
				
			||||||
    }>;
 | 
					 | 
				
			||||||
  }>;
 | 
					 | 
				
			||||||
}
 | 
					 | 
				
			||||||
 | 
					
 | 
				
			||||||
export function Categories({ categories }: CategoriesProps) {
 | 
					export function Categories() {
 | 
				
			||||||
  const idToIcon: { [id: string]: React.ReactNode } = {
 | 
					  const { categories } = sounds;
 | 
				
			||||||
    nature: <BiSolidTree />,
 | 
					 | 
				
			||||||
    urban: <FaCity />,
 | 
					 | 
				
			||||||
  };
 | 
					 | 
				
			||||||
 | 
					
 | 
				
			||||||
  return (
 | 
					  return (
 | 
				
			||||||
    <PlayProvider>
 | 
					    <PlayProvider>
 | 
				
			||||||
@ -30,11 +15,7 @@ export function Categories({ categories }: CategoriesProps) {
 | 
				
			|||||||
 | 
					
 | 
				
			||||||
        <div>
 | 
					        <div>
 | 
				
			||||||
          {categories.map(category => (
 | 
					          {categories.map(category => (
 | 
				
			||||||
            <Category
 | 
					            <Category {...category} key={category.id} />
 | 
				
			||||||
              {...category}
 | 
					 | 
				
			||||||
              icon={idToIcon[category.id] || idToIcon.nature}
 | 
					 | 
				
			||||||
              key={category.id}
 | 
					 | 
				
			||||||
            />
 | 
					 | 
				
			||||||
          ))}
 | 
					          ))}
 | 
				
			||||||
        </div>
 | 
					        </div>
 | 
				
			||||||
      </Container>
 | 
					      </Container>
 | 
				
			||||||
 | 
				
			|||||||
@ -6,7 +6,7 @@ interface CategoryProps {
 | 
				
			|||||||
  icon: React.ReactNode;
 | 
					  icon: React.ReactNode;
 | 
				
			||||||
  title: string;
 | 
					  title: string;
 | 
				
			||||||
  id: string;
 | 
					  id: string;
 | 
				
			||||||
  sounds: Array<{ label: string; src: string }>;
 | 
					  sounds: Array<{ label: string; src: string; icon: React.ReactNode }>;
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
export function Category({ icon, sounds, title }: CategoryProps) {
 | 
					export function Category({ icon, sounds, title }: CategoryProps) {
 | 
				
			||||||
 | 
				
			|||||||
@ -4,7 +4,7 @@
 | 
				
			|||||||
  flex-direction: column;
 | 
					  flex-direction: column;
 | 
				
			||||||
  align-items: center;
 | 
					  align-items: center;
 | 
				
			||||||
  justify-content: center;
 | 
					  justify-content: center;
 | 
				
			||||||
  padding: 30px 20px;
 | 
					  padding: 20px;
 | 
				
			||||||
  border: 1px solid var(--color-neutral-200);
 | 
					  border: 1px solid var(--color-neutral-200);
 | 
				
			||||||
  border-radius: 8px;
 | 
					  border-radius: 8px;
 | 
				
			||||||
  background: linear-gradient(var(--color-neutral-100), transparent);
 | 
					  background: linear-gradient(var(--color-neutral-100), transparent);
 | 
				
			||||||
@ -30,7 +30,46 @@
 | 
				
			|||||||
    box-shadow: 0 10px 20px #818cf833;
 | 
					    box-shadow: 0 10px 20px #818cf833;
 | 
				
			||||||
  }
 | 
					  }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					  & .icon {
 | 
				
			||||||
 | 
					    position: relative;
 | 
				
			||||||
 | 
					    z-index: 2;
 | 
				
			||||||
 | 
					    display: flex;
 | 
				
			||||||
 | 
					    width: 40px;
 | 
				
			||||||
 | 
					    height: 40px;
 | 
				
			||||||
 | 
					    align-items: center;
 | 
				
			||||||
 | 
					    justify-content: center;
 | 
				
			||||||
 | 
					    font-size: var(--font-base);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    &::after {
 | 
				
			||||||
 | 
					      position: absolute;
 | 
				
			||||||
 | 
					      z-index: -1;
 | 
				
			||||||
 | 
					      top: 0;
 | 
				
			||||||
 | 
					      left: 0;
 | 
				
			||||||
 | 
					      width: 100%;
 | 
				
			||||||
 | 
					      height: 100%;
 | 
				
			||||||
 | 
					      border-radius: 50%;
 | 
				
			||||||
 | 
					      background-color: var(--color-neutral-50);
 | 
				
			||||||
 | 
					      content: '';
 | 
				
			||||||
 | 
					    }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    &::before {
 | 
				
			||||||
 | 
					      position: absolute;
 | 
				
			||||||
 | 
					      z-index: -2;
 | 
				
			||||||
 | 
					      top: -1px;
 | 
				
			||||||
 | 
					      left: -1px;
 | 
				
			||||||
 | 
					      width: calc(100% + 2px);
 | 
				
			||||||
 | 
					      height: calc(100% + 2px);
 | 
				
			||||||
 | 
					      border-radius: 50%;
 | 
				
			||||||
 | 
					      background: linear-gradient(
 | 
				
			||||||
 | 
					        var(--color-neutral-300),
 | 
				
			||||||
 | 
					        var(--color-neutral-100)
 | 
				
			||||||
 | 
					      );
 | 
				
			||||||
 | 
					      content: '';
 | 
				
			||||||
 | 
					    }
 | 
				
			||||||
 | 
					  }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
  & h3 {
 | 
					  & h3 {
 | 
				
			||||||
 | 
					    margin-top: 12px;
 | 
				
			||||||
    cursor: default;
 | 
					    cursor: default;
 | 
				
			||||||
    font-family: var(--font-heading);
 | 
					    font-family: var(--font-heading);
 | 
				
			||||||
    font-size: var(--font-sm);
 | 
					    font-size: var(--font-sm);
 | 
				
			||||||
@ -41,7 +80,7 @@
 | 
				
			|||||||
  & input {
 | 
					  & input {
 | 
				
			||||||
    width: 100%;
 | 
					    width: 100%;
 | 
				
			||||||
    max-width: 120px;
 | 
					    max-width: 120px;
 | 
				
			||||||
    margin-top: 12px;
 | 
					    margin-top: 6px;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
    /********** Range Input Styles **********/
 | 
					    /********** Range Input Styles **********/
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
				
			|||||||
@ -10,9 +10,10 @@ import styles from './sound.module.css';
 | 
				
			|||||||
interface SoundProps {
 | 
					interface SoundProps {
 | 
				
			||||||
  label: string;
 | 
					  label: string;
 | 
				
			||||||
  src: string;
 | 
					  src: string;
 | 
				
			||||||
 | 
					  icon: React.ReactNode;
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
export function Sound({ label, src }: SoundProps) {
 | 
					export function Sound({ icon, label, src }: SoundProps) {
 | 
				
			||||||
  const { isPlaying, play } = usePlay();
 | 
					  const { isPlaying, play } = usePlay();
 | 
				
			||||||
  const [isSelected, setIsSelected] = useLocalStorage(
 | 
					  const [isSelected, setIsSelected] = useLocalStorage(
 | 
				
			||||||
    `${label}-is-selected`,
 | 
					    `${label}-is-selected`,
 | 
				
			||||||
@ -52,6 +53,8 @@ export function Sound({ label, src }: SoundProps) {
 | 
				
			|||||||
      onClick={toggle}
 | 
					      onClick={toggle}
 | 
				
			||||||
      onKeyDown={toggle}
 | 
					      onKeyDown={toggle}
 | 
				
			||||||
    >
 | 
					    >
 | 
				
			||||||
 | 
					      <div className={styles.icon}>{icon}</div>
 | 
				
			||||||
 | 
					
 | 
				
			||||||
      <h3 id={label}>{label}</h3>
 | 
					      <h3 id={label}>{label}</h3>
 | 
				
			||||||
      <input
 | 
					      <input
 | 
				
			||||||
        aria-labelledby={label}
 | 
					        aria-labelledby={label}
 | 
				
			||||||
 | 
				
			|||||||
@ -3,7 +3,7 @@ import { Sound } from '@/components/sound';
 | 
				
			|||||||
import styles from './sounds.module.css';
 | 
					import styles from './sounds.module.css';
 | 
				
			||||||
 | 
					
 | 
				
			||||||
interface SoundsProps {
 | 
					interface SoundsProps {
 | 
				
			||||||
  sounds: Array<{ label: string; src: string }>;
 | 
					  sounds: Array<{ label: string; src: string; icon: React.ReactNode }>;
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
export function Sounds({ sounds }: SoundsProps) {
 | 
					export function Sounds({ sounds }: SoundsProps) {
 | 
				
			||||||
 | 
				
			|||||||
@ -1,43 +1,62 @@
 | 
				
			|||||||
 | 
					import { BiSolidTree, BiWater } from 'react-icons/bi/index';
 | 
				
			||||||
 | 
					import { FaCity, FaCloudShowersHeavy, FaWater } from 'react-icons/fa/index';
 | 
				
			||||||
 | 
					import { PiBirdFill } from 'react-icons/pi/index';
 | 
				
			||||||
 | 
					import { MdOutlineThunderstorm } from 'react-icons/md/index';
 | 
				
			||||||
 | 
					import { GiCricket } from 'react-icons/gi/index';
 | 
				
			||||||
 | 
					import { BsSoundwave } from 'react-icons/bs/index';
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					const defaultIcon = <BsSoundwave />;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
export const sounds: {
 | 
					export const sounds: {
 | 
				
			||||||
  categories: Array<{
 | 
					  categories: Array<{
 | 
				
			||||||
    id: string;
 | 
					    id: string;
 | 
				
			||||||
    title: string;
 | 
					    title: string;
 | 
				
			||||||
    sounds: Array<{ label: string; src: string }>;
 | 
					    icon: React.ReactNode;
 | 
				
			||||||
 | 
					    sounds: Array<{ label: string; src: string; icon: React.ReactNode }>;
 | 
				
			||||||
  }>;
 | 
					  }>;
 | 
				
			||||||
} = {
 | 
					} = {
 | 
				
			||||||
  categories: [
 | 
					  categories: [
 | 
				
			||||||
    {
 | 
					    {
 | 
				
			||||||
 | 
					      icon: <BiSolidTree />,
 | 
				
			||||||
      id: 'nature',
 | 
					      id: 'nature',
 | 
				
			||||||
      sounds: [
 | 
					      sounds: [
 | 
				
			||||||
        {
 | 
					        {
 | 
				
			||||||
 | 
					          icon: <FaCloudShowersHeavy />,
 | 
				
			||||||
          label: 'Rain',
 | 
					          label: 'Rain',
 | 
				
			||||||
          src: '/sounds/rain.mp3',
 | 
					          src: '/sounds/rain.mp3',
 | 
				
			||||||
        },
 | 
					        },
 | 
				
			||||||
        {
 | 
					        {
 | 
				
			||||||
 | 
					          icon: <PiBirdFill />,
 | 
				
			||||||
          label: 'Birds',
 | 
					          label: 'Birds',
 | 
				
			||||||
          src: '/sounds/birds.mp3',
 | 
					          src: '/sounds/birds.mp3',
 | 
				
			||||||
        },
 | 
					        },
 | 
				
			||||||
        {
 | 
					        {
 | 
				
			||||||
 | 
					          icon: <BiWater />,
 | 
				
			||||||
          label: 'River',
 | 
					          label: 'River',
 | 
				
			||||||
          src: '/sounds/river.mp3',
 | 
					          src: '/sounds/river.mp3',
 | 
				
			||||||
        },
 | 
					        },
 | 
				
			||||||
        {
 | 
					        {
 | 
				
			||||||
 | 
					          icon: <MdOutlineThunderstorm />,
 | 
				
			||||||
          label: 'Thunder',
 | 
					          label: 'Thunder',
 | 
				
			||||||
          src: '/sounds/thunder.mp3',
 | 
					          src: '/sounds/thunder.mp3',
 | 
				
			||||||
        },
 | 
					        },
 | 
				
			||||||
        {
 | 
					        {
 | 
				
			||||||
 | 
					          icon: <GiCricket />,
 | 
				
			||||||
          label: 'Crickets',
 | 
					          label: 'Crickets',
 | 
				
			||||||
          src: '/sounds/crickets.mp3',
 | 
					          src: '/sounds/crickets.mp3',
 | 
				
			||||||
        },
 | 
					        },
 | 
				
			||||||
        {
 | 
					        {
 | 
				
			||||||
 | 
					          icon: <FaWater />,
 | 
				
			||||||
          label: 'Waves',
 | 
					          label: 'Waves',
 | 
				
			||||||
          src: '/sounds/waves.mp3',
 | 
					          src: '/sounds/waves.mp3',
 | 
				
			||||||
        },
 | 
					        },
 | 
				
			||||||
        {
 | 
					        {
 | 
				
			||||||
 | 
					          icon: defaultIcon,
 | 
				
			||||||
          label: 'Seagulls',
 | 
					          label: 'Seagulls',
 | 
				
			||||||
          src: '/sounds/seagulls.mp3',
 | 
					          src: '/sounds/seagulls.mp3',
 | 
				
			||||||
        },
 | 
					        },
 | 
				
			||||||
        {
 | 
					        {
 | 
				
			||||||
 | 
					          icon: defaultIcon,
 | 
				
			||||||
          label: 'Campfire',
 | 
					          label: 'Campfire',
 | 
				
			||||||
          src: '/sounds/campfire.mp3',
 | 
					          src: '/sounds/campfire.mp3',
 | 
				
			||||||
        },
 | 
					        },
 | 
				
			||||||
@ -45,17 +64,21 @@ export const sounds: {
 | 
				
			|||||||
      title: 'Nature',
 | 
					      title: 'Nature',
 | 
				
			||||||
    },
 | 
					    },
 | 
				
			||||||
    {
 | 
					    {
 | 
				
			||||||
 | 
					      icon: <FaCity />,
 | 
				
			||||||
      id: 'urban',
 | 
					      id: 'urban',
 | 
				
			||||||
      sounds: [
 | 
					      sounds: [
 | 
				
			||||||
        {
 | 
					        {
 | 
				
			||||||
 | 
					          icon: defaultIcon,
 | 
				
			||||||
          label: 'Airport',
 | 
					          label: 'Airport',
 | 
				
			||||||
          src: '/sounds/airport.mp3',
 | 
					          src: '/sounds/airport.mp3',
 | 
				
			||||||
        },
 | 
					        },
 | 
				
			||||||
        {
 | 
					        {
 | 
				
			||||||
 | 
					          icon: defaultIcon,
 | 
				
			||||||
          label: 'Cafe',
 | 
					          label: 'Cafe',
 | 
				
			||||||
          src: '/sounds/cafe.mp3',
 | 
					          src: '/sounds/cafe.mp3',
 | 
				
			||||||
        },
 | 
					        },
 | 
				
			||||||
        {
 | 
					        {
 | 
				
			||||||
 | 
					          icon: defaultIcon,
 | 
				
			||||||
          label: 'Rain on Window',
 | 
					          label: 'Rain on Window',
 | 
				
			||||||
          src: '/sounds/rain-on-window.mp3',
 | 
					          src: '/sounds/rain-on-window.mp3',
 | 
				
			||||||
        },
 | 
					        },
 | 
				
			||||||
		Loading…
	
	
			
			x
			
			
		
	
		Reference in New Issue
	
	Block a user