<script lang="ts"> import { deleteArchives, updateArchives } from '$gql/Mutations'; import { archivesQuery } from '$gql/Queries'; import type { ArchiveFragment } from '$gql/graphql'; import { ArchiveSortLabel } from '$lib/Enums'; import { ArchiveFilterContext, initFilterContext } from '$lib/Filter'; import { initPaginationContext } from '$lib/Pagination'; import { initSelectionContext } from '$lib/Selection'; import { initSortContext } from '$lib/Sort'; import Card from '$lib/components/Card.svelte'; import Empty from '$lib/components/Empty.svelte'; import Guard from '$lib/components/Guard.svelte'; import Head from '$lib/components/Head.svelte'; import RefreshButton from '$lib/components/RefreshButton.svelte'; import Cards from '$lib/containers/Cards.svelte'; import Column from '$lib/containers/Column.svelte'; import Pagination from '$lib/pagination/Pagination.svelte'; import Pill from '$lib/pills/Pill.svelte'; import Selectable from '$lib/selection/Selectable.svelte'; import SelectionOverlay from '$lib/selection/SelectionOverlay.svelte'; import DeleteSelection from '$lib/toolbar/DeleteSelection.svelte'; import FilterOrganized from '$lib/toolbar/FilterOrganized.svelte'; import MarkOrganized from '$lib/toolbar/MarkOrganized.svelte'; import MarkSelection from '$lib/toolbar/MarkSelection.svelte'; import Search from '$lib/toolbar/Search.svelte'; import SelectItems from '$lib/toolbar/SelectItems.svelte'; import SelectSort from '$lib/toolbar/SelectSort.svelte'; import SelectionControls from '$lib/toolbar/SelectionControls.svelte'; import Toolbar from '$lib/toolbar/Toolbar.svelte'; import { getContextClient } from '@urql/svelte'; import { filesize } from 'filesize'; import type { PageData } from './$types'; let client = getContextClient(); export let data: PageData; $: result = archivesQuery(client, { pagination: data.pagination, filter: data.filter, sort: data.sort }); $: archives = $result.data?.archives; const selection = initSelectionContext<ArchiveFragment>('Archive', (a) => a.name); $: if (archives) { $selection.view = archives.edges; $pagination.total = archives.count; } const pagination = initPaginationContext(); $: $pagination.update = data.pagination; const filter = initFilterContext<ArchiveFilterContext>(); $: $filter = new ArchiveFilterContext(data.filter); const sort = initSortContext(data.sort, ArchiveSortLabel); $: $sort.update = data.sort; function refresh() { result.reexecute({ requestPolicy: 'network-only' }); } </script> <Head section="Archives" /> <Column> <Toolbar> <SelectionControls slot="start"> <MarkSelection> <MarkOrganized mutation={updateArchives} /> </MarkSelection> <DeleteSelection mutation={deleteArchives} warning="Deleting an archive will also delete its archive file on disk as well as all comics that belong to it." /> </SelectionControls> <svelte:fragment slot="center"> <Search name="Archives" bind:field={$filter.include.controls.path.contains} /> <FilterOrganized /> <SelectSort /> <SelectItems /> </svelte:fragment> <RefreshButton slot="end" on:click={refresh} /> </Toolbar> {#if archives} <Pagination /> <main> <Cards> {#each archives.edges as { id, name, cover, size, pageCount }, index (id)} <Selectable {index} {id} let:handle let:selected> <Card ellipsis={false} href={id.toString()} details={{ title: name, cover: cover }} on:click={handle} > <SelectionOverlay position="left" {selected} slot="overlay" /> <div class="flex gap-1 text-xs"> <Pill name={`${pageCount} pages`}> <span class="icon-[material-symbols--note] mr-0.5" slot="icon" /> </Pill> <Pill name={filesize(size, { base: 2 })}> <span class="icon-[material-symbols--hard-drive] mr-0.5" slot="icon" /> </Pill> </div> </Card> </Selectable> {:else} <Empty /> {/each} </Cards> </main> <Pagination /> {:else} <Guard {result} /> {/if} </Column>