Toast

Toastは、ユーザーに一時的なメッセージを通知するコンポーネントです。
アクション部分はsnippet action()で差し替えられ、6方向の表示位置に対応しています。
位置に応じてスライド方向が変化するアニメーションで表示されます。

プロパティ

Toastは、以下のプロパティをサポートしています。

名前 デフォルト値 説明
position string top-center 表示位置を指定できます。top-right, top-left, bottom-right, bottom-left, top-center, bottom-center のいずれかを選択できます。
duration number 3000 自動で閉じるまでの時間をミリ秒で指定します。
keepOpen boolean false trueを指定することでトーストを自動で閉じなくします。
hideCloseButton boolean false trueを指定すると閉じるボタンを非表示にします。
transitionParams FlyParams {duration: 200, x: 0, y: 0} アニメーションの時間・水平方向移動距離・垂直方向移動距離を指定できます。
closeButtonClass string 閉じるアイコンのクラスを指定できます。
open boolean true トーストの開閉状態を制御します。
onClose () => void トーストが閉じられたときに呼ばれるハンドラです。

インストールの手順

以下のコンポーネントのコードを、使いたいプロジェクトにコピー&ペーストします。
パスは実際のプロジェクトの構成にあわせて更新します。

items/Toast.svelte
        <!--
@component
## 概要
- 一時的なメッセージを表示するためのコンポーネントです

## 機能
- 表示位置を6方向から選択できます
- 指定した時間で自動的に閉じる、もしくは手動で閉じられます
- スロットでアクションボタンを差し込めます

## Props
- position: トーストの表示位置を指定します
- duration: 自動で閉じるまでの時間を指定します
- keepOpen: trueを指定することで自動で閉じなくできます
- hideCloseButton: trueを指定することで閉じるボタンを非表示にすることができます
- transitionParams: アニメーションの時間・水平方向の移動量・垂直方向の移動量を指定できます
- closeButtonClass: 閉じるボタンのクラスを指定します

## Usage
```svelte
<Toast duration={3000}>保存しました</Toast>
```
-->

<script module lang="ts">
  import type { Snippet } from 'svelte';
  import type { ClassValue } from 'svelte/elements';
  import type { FlyParams } from 'svelte/transition';
  import { cva, type VariantProps } from 'class-variance-authority';

  export const toastVariants = cva('flex items-center gap-2 p-6 bg-base-container-default border border-base-stroke-default rounded-md shadow-lg', {
    variants: {
      position: {
        'top-right': 'fixed top-4 right-4 z-50',
        'top-left': 'fixed top-4 left-4 z-50',
        'bottom-right': 'fixed right-4 bottom-4 z-50',
        'bottom-left': 'fixed bottom-4 left-4 z-50',
        'top-center': 'fixed inset-x-4 top-4 z-50 mx-auto',
        'bottom-center': 'fixed inset-x-4 bottom-4 z-50 mx-auto',
      },
    },
  });

  export type ToastVariants = VariantProps<typeof toastVariants>;

  export interface ToastProps extends ToastVariants {
    /** クラス */
    class?: ClassValue;
    /** 自動で閉じるまでの時間(ミリ秒) */
    duration?: number;
    /** trueを指定で自動で閉じなくする */
    keepOpen?: boolean;
    /** trueを指定で閉じるボタンを非表示 */
    hideCloseButton?: boolean;
    /** 開閉状態 */
    open?: boolean;
    /** アニメーションのprops */
    transitionParams?: FlyParams;
    /** 閉じるボタンのクラス */
    closeButtonClass?: ClassValue;
    /** 本文 */
    children?: Snippet<[]>;
    /** アクションボタン用スロット */
    action?: Snippet<[]>;
    /** 閉じたときのハンドラ */
    onClose?: () => void;
  }
</script>

<script lang="ts">
  import Button from '$lib/components/ui/atoms/Button.svelte';
  import { X } from '@lucide/svelte';
  import { fly } from 'svelte/transition';

  let { class: className, position, duration = 3000, keepOpen = false, hideCloseButton = false, open = $bindable(false), transitionParams = { duration: 200, x: 0, y: 0 }, closeButtonClass, children, action, onClose }: ToastProps = $props();

  let timerId: ReturnType<typeof setTimeout> | null = null;

  let toastVariantClass = $derived(toastVariants({ position, class: className }));

  $effect(() => {
    if (open && !keepOpen) {
      timerId = setTimeout(close, duration);
    }
    return () => {
      if (timerId) clearTimeout(timerId);
    };
  });

  function close() {
    if (timerId) clearTimeout(timerId);
    open = false;
    onClose?.();
  }
</script>

<div transition:fly={transitionParams} class={toastVariantClass}>
  <div class="flex-1 min-w-0">
    {@render children?.()}
  </div>
  {#if action || !hideCloseButton}
    <div class="flex items-center shrink-0 gap-2">
      {@render action?.()}
      {#if !hideCloseButton}
        <Button class={closeButtonClass} size="small" variant="secondary" isSquare tone="ghost" onclick={close} aria-label="close">
          <X size="1rem" />
        </Button>
      {/if}
    </div>
  {/if}
</div>

      

依存コンポーネント

Toastを使うときは、以下のコンポーネントもダウンロードが必要です。

使い方


サンプル

Auto Close

durationに指定した時間が経過後に自動でToastを閉じます。

Auto Close with Action

自動で閉じるほか、 閉じるボタンによって閉じることができます。

Persistent

keepOpentrue にすると、操作されるまで表示され続けます。

Positions

6方向の表示位置に対応しています。