From 93ff72a052484b36c9ac821b94b632865b4a3550 Mon Sep 17 00:00:00 2001 From: MAZE Date: Wed, 3 Jan 2024 00:03:58 +0330 Subject: [PATCH] feat: implement sharing URL --- .../modals/share-link/share-link.tsx | 39 +++++++++++++++++-- src/hooks/use-copy.ts | 19 +++++++++ 2 files changed, 54 insertions(+), 4 deletions(-) create mode 100644 src/hooks/use-copy.ts diff --git a/src/components/modals/share-link/share-link.tsx b/src/components/modals/share-link/share-link.tsx index 2dfada8..cedd2fc 100644 --- a/src/components/modals/share-link/share-link.tsx +++ b/src/components/modals/share-link/share-link.tsx @@ -1,7 +1,11 @@ -import { IoCopyOutline } from 'react-icons/io5/index'; +import { useMemo } from 'react'; +import { IoCopyOutline, IoCheckmark } from 'react-icons/io5/index'; import { Modal } from '@/components/modal'; +import { useCopy } from '@/hooks/use-copy'; +import { useSoundStore } from '@/store'; + import styles from './share-link.module.css'; interface ShareLinkModalProps { @@ -10,6 +14,33 @@ interface ShareLinkModalProps { } export function ShareLinkModal({ onClose, show }: ShareLinkModalProps) { + const sounds = useSoundStore(state => state.sounds); + const { copy, copying } = useCopy(); + + const selected = useMemo(() => { + return Object.keys(sounds) + .map(sound => ({ + id: sound, + isSelected: sounds[sound].isSelected, + volume: sounds[sound].volume.toFixed(1), + })) + .filter(sound => sound.isSelected); + }, [sounds]); + + const string = useMemo(() => { + const object: Record = {}; + + selected.forEach(sound => { + object[sound.id] = Number(sound.volume); + }); + + return JSON.stringify(object); + }, [selected]); + + const url = useMemo(() => { + return `https://moodist.app/?share=${encodeURIComponent(string)}`; + }, [string]); + return (

Share your sound selection!

@@ -18,9 +49,9 @@ export function ShareLinkModal({ onClose, show }: ShareLinkModalProps) { selection with.

- -
diff --git a/src/hooks/use-copy.ts b/src/hooks/use-copy.ts new file mode 100644 index 0000000..6f3346c --- /dev/null +++ b/src/hooks/use-copy.ts @@ -0,0 +1,19 @@ +import { useState, useCallback } from 'react'; + +export function useCopy(timeout = 1500) { + const [copying, setCopying] = useState(false); + + const copy = useCallback( + (content: string) => { + if (copying) return; + + navigator.clipboard.writeText(content); + setCopying(true); + + setTimeout(() => setCopying(false), timeout); + }, + [copying, timeout], + ); + + return { copy, copying }; +}