<SatelliteToast/>
A flexible, reusable toast notification component designed to suit diverse UX needs.
Default Toast
The default toast implementation with all properties set to their initial values, featuring a dark theme.
1"use client"
2import { useRef } from "react";
3import { SatelliteToast, type ToastNotification } from "./satellite-toast";
4
5export default function App() {
6 const toastRef = useRef<{ showNotification: (options: Omit<ToastNotification, "id">) => void }>(null);
7
8 const showToast = () => {
9 if (toastRef.current) {
10 toastRef.current.showNotification({
11 title: "Satellite Toast",
12 content: "This is the default Satellite Toast. Ain't it great?"
13 });
14 }
15 };
16
17 return (
18 <div>
19 <button onClick={showToast}>Show Toast</button>
20 <SatelliteToast ref={toastRef}
21 />
22 </div>
23 );
24}
Toast Alignment, Spacing, Max Width
LTR toasts display on the right side of the viewport, and RTL toasts display on the left. The 'position' prop can place toasts on the opposite side, but this is discouraged because slide-in and slide-out animations are designed for their respective horizontal alignments. When toasts are aligned to the top, 'firstContainerVerticalStartMarginAdjustment' must be adjusted to compensate for the height of the type icon container, as its size is not accounted for when calculating spacing.
1"use client"
2import { useRef } from "react";
3import { SatelliteToast, type ToastNotification } from "./satellite-toast";
4
5export default function App() {
6 const toastRef = useRef<{ showNotification: (options: Omit<ToastNotification, "id">) => void }>(null);
7
8 const showToast = () => {
9 if (toastRef.current) {
10 toastRef.current.showNotification({
11 title: "Anaïs Nin",
12 content: "We don't see things as they are, we see them as we are.",
13 position: "top-right"
14 });
15 }
16 };
17
18 return (
19 <div>
20 <button onClick={showToast}>Show Toast</button>
21 <SatelliteToast ref={toastRef}
22 maxWidth="100%"
23 horizontalMarginAdjustment="15px"
24 verticalGapAdjustment="56px"
25 firstContainerVerticalStartMarginAdjustment="32px"
26 />
27 </div>
28 );
29}
RTL (Right-to-Left)
Enables right-to-left display for the toast, mirroring both its layout and animations. RTL toasts are meant to be displayed on the left side of the screen, ensuring alignment matches the animation flow.
1"use client"
2import { useRef } from "react";
3import { SatelliteToast, type ToastNotification } from "./satellite-toast";
4
5export default function App() {
6 const toastRef = useRef<{ showNotification: (options: Omit<ToastNotification, "id">) => void }>(null);
7
8 const showToast = () => {
9 if (toastRef.current) {
10 toastRef.current.showNotification({
11 title: "אוסקר ווילד",
12 content: "יש רק שתי טרגדיות בעולם הזה. האחת היא לא לקבל את מה שרוצים והשנייה היא לקבל.",
13 isRTL: true,
14 position: "bottom-left"
15 });
16 }
17 };
18
19 return (
20 <div>
21 <button onClick={showToast}>Show Toast</button>
22 <SatelliteToast ref={toastRef}
23 />
24 </div>
25 );
26}
Timer Animation
The toast body boasts a timer bar whose appearance is controlled by the 'timerAnimationType' prop. It accepts one of the following values: 'shrink' (default), which contracts the bar symmetrically toward the center from both ends, or 'deplete', which reduces the bar length linearly from one side in a manner similar to a conventional progress indicator.
1"use client"
2import { useRef } from "react";
3import { SatelliteToast, type ToastNotification } from "./satellite-toast";
4
5export default function App() {
6 const toastRef = useRef<{ showNotification: (options: Omit<ToastNotification, "id">) => void }>(null);
7
8 const showToast = () => {
9 if (toastRef.current) {
10 toastRef.current.showNotification({
11 title: "Satellite Toast",
12 content: "Look at the timer bar. It's depleting!",
13 timerAnimationType: "deplete"
14 });
15 }
16 };
17
18 return (
19 <div>
20 <button onClick={showToast}>Show Toast</button>
21 <SatelliteToast ref={toastRef}
22 />
23 </div>
24 );
25}
Longevity
The lifetime of a toast is defined by the 'longevity' prop, which sets how long (in milliseconds) the notification remains visible before auto‑dismissal. By default, 'longevity' is 5000 ms (5 seconds).
1"use client"
2import { useRef } from "react";
3import { SatelliteToast, type ToastNotification } from "./satellite-toast";
4
5export default function App() {
6 const toastRef = useRef<{ showNotification: (options: Omit<ToastNotification, "id">) => void }>(null);
7
8 const showToast = () => {
9 if (toastRef.current) {
10 toastRef.current.showNotification({
11 title: "Long-Lived Toast",
12 content: "This toast remains visible for 15 seconds.",
13 longevity: 15000
14 });
15 }
16 };
17
18 return (
19 <div>
20 <button onClick={showToast}>Show Toast</button>
21 <SatelliteToast ref={toastRef}
22 />
23 </div>
24 );
25}
Colors
The toast color scheme is fully customizable, ensuring it can be adapted even for the most unconventional use cases.
1"use client"
2import { useRef } from "react";
3import { SatelliteToast, type ToastNotification } from "./satellite-toast";
4
5export default function App() {
6 const toastRef = useRef<{ showNotification: (options: Omit<ToastNotification, "id">) => void }>(null);
7
8 const showToast = () => {
9 if (toastRef.current) {
10 toastRef.current.showNotification({
11 title: "JM Barrie",
12 content: "Would you like an adventure now, or would you like to have your tea first?",
13 accentColor: "#ffffff",
14 backgroundColor: "#00a6fb",
15 textColor: "#242424",
16 titleFontColor: "#242424",
17 contentFontColor: "#242424",
18 bodyBorderColor: "#00a6fb",
19 typeIconContainerBorderColor: "#616161",
20 typeIconColor: "#00a6fb",
21 closeIconBgColor: "#000",
22 closeIconFgColor: "#ffffff",
23 closeIconHoverBgColor: "#242424",
24 closeIconHoverFgColor: "#fff",
25 closeIconOutlineColor: "#303030",
26 timerBgColor: "#333",
27 timerColor: "#00a6fb",
28 satelliteColor: "#363636"
29 });
30 }
31 };
32
33 return (
34 <div>
35 <button onClick={showToast}>Show Toast</button>
36 <SatelliteToast ref={toastRef}
37 />
38 </div>
39 );
40}
Rounding, Typography, Border Width
Toast rounding, font styling, and outline widths are fully customizable, allowing precise control over typography and component shape.
1"use client"
2import { useRef } from "react";
3import { SatelliteToast, type ToastNotification } from "./satellite-toast";
4
5export default function App() {
6 const toastRef = useRef<{ showNotification: (options: Omit<ToastNotification, "id">) => void }>(null);
7
8 const showToast = () => {
9 if (toastRef.current) {
10 toastRef.current.showNotification({
11 title: "Louise Bourgeois",
12 content: "Art is a guaranty of sanity.",
13 titleFontSize: "0.875rem",
14 titleFontWeight: "400",
15 contentFontSize: "1.3rem",
16 contentFontWeight: "900",
17 bodyBorderRadius: "4px",
18 typeIconContainerBorderRadius: "16px",
19 closeIconBorderRadius: "2px",
20 bodyBorderWidth: "10px",
21 typeIconContainerBorderWidth: "6px",
22 closeIconOutlineWidth: "24px"
23 });
24 }
25 };
26
27 return (
28 <div>
29 <button onClick={showToast}>Show Toast</button>
30 <SatelliteToast ref={toastRef}
31 />
32 </div>
33 );
34}
Custom Icon
Replaces the default satellite icon with a custom SVG.
1"use client"
2import { useRef } from "react";
3import { SatelliteToast, type ToastNotification } from "./satellite-toast";
4
5export default function App() {
6 const toastRef = useRef<{ showNotification: (options: Omit<ToastNotification, "id">) => void }>(null);
7
8 const showToast = () => {
9 if (toastRef.current) {
10 toastRef.current.showNotification({
11 title: "Campfire Toast",
12 content: "This toast has a custom campfire icon.",
13 customIcon: `<svg xmlns="http://www.w3.org/2000/svg" width="24" height="24" viewBox="0 0 24 24" fill="currentColor" class="icon icon-tabler icons-tabler-filled icon-tabler-campfire"><path stroke="none" d="M0 0h24v24H0z" fill="none"/><path d="M19.757 16.03a1 1 0 0 1 .597 1.905l-.111 .035l-16 4a1 1 0 0 1 -.597 -1.905l.111 -.035l16 -4z" /><path d="M3.03 16.757a1 1 0 0 1 1.098 -.749l.115 .022l16 4a1 1 0 0 1 -.37 1.962l-.116 -.022l-16 -4a1 1 0 0 1 -.727 -1.213z" /><path d="M13.553 2.106c-4.174 2.086 -6.553 5.358 -6.553 8.894a5 5 0 0 0 10 0c0 -1.047 -.188 -1.808 -.606 -2.705l-.169 -.345l-.33 -.647c-.621 -1.24 -.895 -2.338 -.895 -4.303a1 1 0 0 0 -1.447 -.894z" /></svg>`
14 });
15 }
16 };
17
18 return (
19 <div>
20 <button onClick={showToast}>Show Toast</button>
21 <SatelliteToast ref={toastRef}
22 />
23 </div>
24 );
25}
Satellite Layer
By setting `satelliteInFront` to `false`, the satellite animation is rendered behind the main toast body, altering the visual depth.
1"use client"
2import { useRef } from "react";
3import { SatelliteToast, type ToastNotification } from "./satellite-toast";
4
5export default function App() {
6 const toastRef = useRef<{ showNotification: (options: Omit<ToastNotification, "id">) => void }>(null);
7
8 const showToast = () => {
9 if (toastRef.current) {
10 toastRef.current.showNotification({
11 title: "Back",
12 content: "The satellite animation is now behind the planet.",
13 satelliteInFront: false
14 });
15 }
16 };
17
18 return (
19 <div>
20 <button onClick={showToast}>Show Toast</button>
21 <SatelliteToast ref={toastRef}
22 />
23 </div>
24 );
25}
Background Bars
The component allows disabling the animated background bars for a cleaner, more minimalist appearance by setting `disableBackgroundBars` to `true`.
1"use client"
2import { useRef } from "react";
3import { SatelliteToast, type ToastNotification } from "./satellite-toast";
4
5export default function App() {
6 const toastRef = useRef<{ showNotification: (options: Omit<ToastNotification, "id">) => void }>(null);
7
8 const showToast = () => {
9 if (toastRef.current) {
10 toastRef.current.showNotification({
11 title: "Miyamoto Musashi",
12 content: "It's wrong to be inflexible.",
13 disableBackgroundBars: true
14 });
15 }
16 };
17
18 return (
19 <div>
20 <button onClick={showToast}>Show Toast</button>
21 <SatelliteToast ref={toastRef}
22 />
23 </div>
24 );
25}
More Customization Options
It is possible to disable the satellite orbit animation, adjust the type icon container offset, and customize the toast’s padding for a tailored layout.
1"use client"
2import { useRef } from "react";
3import { SatelliteToast, type ToastNotification } from "./satellite-toast";
4
5export default function App() {
6 const toastRef = useRef<{ showNotification: (options: Omit<ToastNotification, "id">) => void }>(null);
7
8 const showToast = () => {
9 if (toastRef.current) {
10 toastRef.current.showNotification({
11 title: "Lao Tzu",
12 content: "When I let go of what I am, I become what I might be.",
13 bars: 100,
14 showSatelliteAnimation: false,
15 animationDuration: 720,
16 iconXOffset: "-61px",
17 iconYOffset: "-10px",
18 paddingLTR: "1.375rem 2.75rem 1.375rem 2.75rem",
19 paddingRTL: "1.375rem 2.75rem 1.375rem 2.75rem"
20 });
21 }
22 };
23
24 return (
25 <div>
26 <button onClick={showToast}>Show Toast</button>
27 <SatelliteToast ref={toastRef}
28 />
29 </div>
30 );
31}
Enjoying SatelliteToast?
If you find this component useful, please consider giving it a star on GitHub.
Credit
The existence of this project, at least in its current form, wouldn’t've been possible without the following:
Below are the credit entries for both the toast and the documentation: