// Context import { LoadingStatusContext } from 'shared/context/loading-status-context.mjs' // Hooks import { useState, useEffect, Fragment, useContext } from 'react' import { useTranslation } from 'next-i18next' import { useBackend } from 'shared/hooks/use-backend.mjs' import { useRouter } from 'next/router' // Components import { BackToAccountButton } from './shared.mjs' import { PlusIcon, TrashIcon, LeftIcon } from 'shared/components/icons.mjs' import { PageLink, WebLink, Link } from 'shared/components/link.mjs' import { DisplayRow } from './shared.mjs' import { StringInput } from 'shared/components/inputs.mjs' import { DynamicMdx } from 'shared/components/mdx/dynamic.mjs' export const ns = ['account', 'status'] export const types = ['design', 'pattern', 'set', 'cset', 'doc', 'custom'] export const Bookmark = ({ bookmark }) => { const { t } = useTranslation(ns) return bookmark ? (
{bookmark.title} {bookmark.url.length > 30 ? bookmark.url.slice(0, 30) + '...' : bookmark.url} {t(`${bookmark.type}Bookmark`)}
{t('bookmarks')}
) : null } // Component for the 'new/apikey' page export const NewBookmark = () => { // Hooks const { setLoadingStatus } = useContext(LoadingStatusContext) const router = useRouter() const backend = useBackend() const { t, i18n } = useTranslation(ns) const docs = {} for (const option of ['title', 'location', 'type']) { docs[option] = ( ) } // State const [title, setTitle] = useState('') const [url, setUrl] = useState('') const createBookmark = async () => { setLoadingStatus([true, 'processingUpdate']) const result = await backend.createBookmark({ title, url, type: 'custom', }) if (result.success) { setLoadingStatus([true, 'nailedIt', true, true]) router.push('/account/bookmarks') } else setLoadingStatus([true, 'backendError', true, false]) } return (
val.length > 0} placeholder={t('account')} /> val.length > 0} placeholder={'https://freesewing.org/account'} />
) } // Component for the account/bookmarks page export const Bookmarks = () => { // Hooks const backend = useBackend() const { t } = useTranslation(ns) const { setLoadingStatus, LoadingProgress } = useContext(LoadingStatusContext) // State const [bookmarks, setBookmarks] = useState([]) const [selected, setSelected] = useState({}) const [refresh, setRefresh] = useState(0) // Helper var to see how many are selected const selCount = Object.keys(selected).length // Effects useEffect(() => { const getBookmarks = async () => { const result = await backend.getBookmarks() if (result.success) setBookmarks(result.data.bookmarks) } getBookmarks() }, [refresh]) // Helper method to toggle single selection const toggleSelect = (id) => { const newSelected = { ...selected } if (newSelected[id]) delete newSelected[id] else newSelected[id] = 1 setSelected(newSelected) } // Helper method to toggle select all const toggleSelectAll = () => { if (selCount === bookmarks.length) setSelected({}) else { const newSelected = {} for (const bookmark of bookmarks) newSelected[bookmark.id] = 1 setSelected(newSelected) } } // Helper to delete one or more bookmarks const removeSelectedBookmarks = async () => { let i = 0 for (const id in selected) { i++ await backend.removeBookmark(id) setLoadingStatus([ true, , ]) } setSelected({}) setRefresh(refresh + 1) setLoadingStatus([true, 'nailedIt', true, true]) } const perType = {} for (const type of types) perType[type] = bookmarks.filter((b) => b.type === type) return (

{t('newBookmark')}

{bookmarks.length > 0 ? ( ) : null} {types.map((type) => perType[type].length > 0 ? (

{t(`${type}Bookmark`)}

{bookmarks .filter((bookmark) => bookmark.type === type) .map((bookmark, i) => ( ))}
{t('title')} {t('location')}
toggleSelect(bookmark.id)} /> 30 ? bookmark.url.slice(0, 30) + '...' : bookmark.url } />
) : null )}
) }