Compare commits

1 Commits

6 changed files with 116 additions and 10 deletions

View File

@@ -0,0 +1,49 @@
<script lang="ts">
import type { ToastType } from "$lib/ToastService/types";
import { onMount } from "svelte";
const { toast, destroyer }: {
toast: ToastType,
destroyer: () => void
} = $props();
const alertClass = $derived.by(() => {
switch (toast.type) {
case "success":
return 'alert-success';
case "warning":
return 'alert-warning';
case "error":
return 'alert-error';
case "info":
return 'alert-info';
default:
return '';
}
});
let timeMs = $state(0);
let expireTime = 50000;
let progressMax = 100;
let segmentTime = Math.round(expireTime / progressMax);
const progressValue = $derived(Math.round(timeMs / segmentTime));
function increment() {
timeMs += segmentTime;
if (timeMs >= expireTime) destroyer();
}
onMount(() => {
const interval = setInterval(increment, segmentTime);
return () => clearInterval(interval);
});
</script>
<div class="w-[60vw]">
<div class="absolute w-full flex flex-col px-2">
<progress class="progress h-1 w-full" value={progressValue} max="100"></progress>
</div>
<div class={["alert", alertClass]}>
<span>{toast.content}</span>
</div>
</div>

View File

@@ -0,0 +1,27 @@
<script lang="ts">
import type { ServiceState, ToastType } from "$lib/ToastService/types";
import { setContext } from "svelte";
import Toast from "./Toast.svelte";
const { children } = $props();
let serviceState: ServiceState = $state({ toasts: {}, nextId: 0 });
function addToast(toast: ToastType) {
serviceState.toasts[serviceState.nextId++] = toast;
}
setContext('toastservice', addToast);
function destroyToast(id: string) {
delete serviceState.toasts[id];
}
</script>
{@render children()}
<div class="toast toast-top toast-center z-80">
{#each Object.entries(serviceState.toasts) as [i, toast] (i)}
<Toast {toast} destroyer={() => destroyToast(i)}/>
{/each}
</div>

View File

@@ -0,0 +1,13 @@
export type ToastType = {
type: 'info' | 'success' | 'warning' | 'error',
content: string,
}
export type InternalToasts = {
[key: string]: ToastType,
}
export type ServiceState = {
toasts: InternalToasts,
nextId: number,
}

View File

@@ -0,0 +1,8 @@
import { getContext } from "svelte";
import type { ToastType } from "$lib/ToastService/types";
export function useToast(): { fireToast: (toast: ToastType) => void } {
return {
fireToast: getContext('toastservice')
};
}

View File

@@ -1,7 +1,10 @@
<script lang="ts">
import '../app.css';
import ToastProvider from "$lib/ToastService/ToastProvider.svelte";
let { children } = $props();
</script>
<ToastProvider>
{@render children()}
</ToastProvider>

View File

@@ -2,9 +2,12 @@
import { scale } from 'svelte/transition';
import { goto } from "$app/navigation";
import BSlideOverlay from "$lib/BSlideOverlay.svelte";
import { useToast } from "$lib/ToastService/useToast";
let { data } = $props();
const { fireToast } = useToast();
let showOverlay = $state(false);
let startingCharge = $state(false);
@@ -13,12 +16,12 @@
startingCharge = true;
try {
// TODO: StartCharge fetch request
const response = await fetch(`/api/public/1/chargecontroller/${data.qrcode}/start_charge/`, {
method: 'POST',
headers: {
'Accept': 'application/json',
}
});
// const response = await fetch(`/api/public/1/chargecontroller/${data.qrcode}/start_charge/`, {
// method: 'POST',
// headers: {
// 'Accept': 'application/json',
// }
// });
console.log("nop");
await goto(`/${data.qrcode}/status`);
} finally {
@@ -31,6 +34,9 @@
<div class="row-start-5 col-start-1 flex flex-col justify-center items-center">
<div class="pointer-events-auto">
<button class="btn btn-primary btn-lg uppercase" onclick={() => showOverlay = true}>Attivare la Ricarica</button>
<button class="btn btn-secondary" onclick={() => fireToast({type: 'success', content: 'Messaggio Ricevuto!'})}>
TEST
</button>
</div>
</div>
<BSlideOverlay bind:show={showOverlay} closable={!startingCharge}>