diff --git a/web/i18n/en/general.json b/web/i18n/en/general.json index 6ea5e8a0..5a371ff8 100644 --- a/web/i18n/en/general.json +++ b/web/i18n/en/general.json @@ -1,3 +1,4 @@ { - "cobalt": "cobalt" + "cobalt": "cobalt", + "gotit": "got it" } diff --git a/web/src/components/dialog/DialogHolder.svelte b/web/src/components/dialog/DialogHolder.svelte new file mode 100644 index 00000000..b5496d65 --- /dev/null +++ b/web/src/components/dialog/DialogHolder.svelte @@ -0,0 +1,28 @@ + + + + + diff --git a/web/src/components/dialog/SmallDialog.svelte b/web/src/components/dialog/SmallDialog.svelte new file mode 100644 index 00000000..8ee30862 --- /dev/null +++ b/web/src/components/dialog/SmallDialog.svelte @@ -0,0 +1,55 @@ + + + + + + + + + diff --git a/web/src/components/save/buttons/DownloadButton.svelte b/web/src/components/save/buttons/DownloadButton.svelte index 96510462..718a9041 100644 --- a/web/src/components/save/buttons/DownloadButton.svelte +++ b/web/src/components/save/buttons/DownloadButton.svelte @@ -3,14 +3,30 @@ import API from "$lib/api"; import { device } from "$lib/device"; + import { t } from "$lib/i18n/translations"; + import { createDialog } from "$lib/dialogs"; + import type { DialogInfo } from "$lib/types/dialog"; + export let url: string; $: buttonText = ">>"; $: buttonAltText = $t('a11y.save.download'); $: isDisabled = false; + let defaultErrorPopup = { + id: "save-error", + type: "small", + title: "", + bodySubText: "", + buttons: [{ + text: $t("general.gotit"), + color: "gray", + action: () => {}, + }] + } + const changeDownloadButton = (state: string) => { isDisabled = true; switch (state) { @@ -59,14 +75,20 @@ changeDownloadButton("error"); restoreDownloadButton(); - return alert("couldn't access the api"); + return createDialog({ + ...defaultErrorPopup as DialogInfo, + bodyText: "couldn't access the api" + }) } if (response.status === "error" || response.status === "rate-limit") { changeDownloadButton("error"); restoreDownloadButton(); - return alert(`error from api: ${response.text}`); + return createDialog({ + ...defaultErrorPopup as DialogInfo, + bodyText: response.text + }) } if (response.status === "redirect") { @@ -90,7 +112,10 @@ changeDownloadButton("error"); restoreDownloadButton(); - return alert("couldn't probe the stream"); + return createDialog({ + ...defaultErrorPopup as DialogInfo, + bodyText: "couldn't probe the stream" + }) } } }; diff --git a/web/src/lib/dialogs.ts b/web/src/lib/dialogs.ts new file mode 100644 index 00000000..a186be04 --- /dev/null +++ b/web/src/lib/dialogs.ts @@ -0,0 +1,23 @@ +import { readable, type Updater } from "svelte/store"; +import type { DialogInfo } from "$lib/types/dialog"; + +let update: (_: Updater) => void; + +export default readable( + [], + (_, _update) => { update = _update } +); + +export function createDialog(newData: DialogInfo) { + update((popups) => { + popups.push(newData); + return popups; + }); +} + +export function killDialog() { + update((popups) => { + popups.pop() + return popups; + }); +} diff --git a/web/src/lib/types/dialog.ts b/web/src/lib/types/dialog.ts new file mode 100644 index 00000000..b473acd1 --- /dev/null +++ b/web/src/lib/types/dialog.ts @@ -0,0 +1,14 @@ +export type DialogButton = { + text: string, + color: string, + action: () => unknown | Promise +} + +export type DialogInfo = { + id: string, + type: "small", + title: string, + bodyText: string, + bodySubText: string, + buttons: DialogButton[] +} diff --git a/web/src/routes/+layout.svelte b/web/src/routes/+layout.svelte index 2ba680c5..35306b81 100644 --- a/web/src/routes/+layout.svelte +++ b/web/src/routes/+layout.svelte @@ -8,6 +8,7 @@ import Sidebar from "$components/sidebar/Sidebar.svelte"; import NotchSticker from "$components/misc/NotchSticker.svelte"; + import DialogHolder from "$components/dialog/DialogHolder.svelte"; $: reduceMotion = $settings.appearance.reduceMotion @@ -33,6 +34,7 @@ {#if device.is.iPhone && app.is.installed} {/if} +
@@ -302,6 +304,15 @@ font-size: 11px; } + :global(dialog) { + max-height: 100%; + max-width: 100%; + padding: var(--padding); + border-radius: var(--border-radius); + border: none; + pointer-events: all; + } + :global(.subtext) { font-size: 12.5px; font-weight: 500;