mirror of
https://github.com/remvze/moodist.git
synced 2025-12-17 08:54:13 +00:00
feat: implement sharing URL
This commit is contained in:
parent
ef81f198ba
commit
93ff72a052
2 changed files with 54 additions and 4 deletions
|
|
@ -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 { Modal } from '@/components/modal';
|
||||||
|
|
||||||
|
import { useCopy } from '@/hooks/use-copy';
|
||||||
|
import { useSoundStore } from '@/store';
|
||||||
|
|
||||||
import styles from './share-link.module.css';
|
import styles from './share-link.module.css';
|
||||||
|
|
||||||
interface ShareLinkModalProps {
|
interface ShareLinkModalProps {
|
||||||
|
|
@ -10,6 +14,33 @@ interface ShareLinkModalProps {
|
||||||
}
|
}
|
||||||
|
|
||||||
export function ShareLinkModal({ onClose, show }: 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<string, number> = {};
|
||||||
|
|
||||||
|
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 (
|
return (
|
||||||
<Modal show={show} onClose={onClose}>
|
<Modal show={show} onClose={onClose}>
|
||||||
<h1 className={styles.heading}>Share your sound selection!</h1>
|
<h1 className={styles.heading}>Share your sound selection!</h1>
|
||||||
|
|
@ -18,9 +49,9 @@ export function ShareLinkModal({ onClose, show }: ShareLinkModalProps) {
|
||||||
selection with.
|
selection with.
|
||||||
</p>
|
</p>
|
||||||
<div className={styles.inputWrapper}>
|
<div className={styles.inputWrapper}>
|
||||||
<input type="text" value="https://moodist.app/?share=test" />
|
<input readOnly type="text" value={url} />
|
||||||
<button>
|
<button onClick={() => copy(url)}>
|
||||||
<IoCopyOutline />
|
{copying ? <IoCheckmark /> : <IoCopyOutline />}
|
||||||
</button>
|
</button>
|
||||||
</div>
|
</div>
|
||||||
</Modal>
|
</Modal>
|
||||||
|
|
|
||||||
19
src/hooks/use-copy.ts
Normal file
19
src/hooks/use-copy.ts
Normal file
|
|
@ -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 };
|
||||||
|
}
|
||||||
Loading…
Add table
Reference in a new issue