Skip to content

Commit

Permalink
feat: initial commit
Browse files Browse the repository at this point in the history
  • Loading branch information
macci001 committed Dec 24, 2024
1 parent 5494fa2 commit d3ad47a
Show file tree
Hide file tree
Showing 16 changed files with 883 additions and 0 deletions.
24 changes: 24 additions & 0 deletions packages/components/toast/README.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,24 @@
# @nextui-org/toast

Toast Component helps to provide feedback on user-actions.

> This is an internal utility, not intended for public usage.
## Installation

```sh
yarn add @nextui-org/toast
# or
npm i @nextui-org/toast
```

## Contribution

Yes please! See the
[contributing guidelines](https://github.com/nextui-org/nextui/blob/master/CONTRIBUTING.md)
for details.

## License

This project is licensed under the terms of the
[MIT license](https://github.com/nextui-org/nextui/blob/master/LICENSE).
60 changes: 60 additions & 0 deletions packages/components/toast/package.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,60 @@
{
"name": "@nextui-org/toast",
"version": "2.0.0",
"description": "adding toast",
"keywords": [
"toast"
],
"author": "Junior Garcia <jrgarciadev@gmail.com>",
"homepage": "https://nextui.org",
"license": "MIT",
"main": "src/index.ts",
"sideEffects": false,
"files": [
"dist"
],
"publishConfig": {
"access": "public"
},
"repository": {
"type": "git",
"url": "git+https://github.com/nextui-org/nextui.git",
"directory": "packages/components/toast"
},
"bugs": {
"url": "https://github.com/nextui-org/nextui/issues"
},
"scripts": {
"build": "tsup src --dts",
"build:fast": "tsup src",
"dev": "pnpm build:fast --watch",
"clean": "rimraf dist .turbo",
"typecheck": "tsc --noEmit",
"prepack": "clean-package",
"postpack": "clean-package restore"
},
"peerDependencies": {
"@nextui-org/system": ">=2.0.0",
"@nextui-org/theme": ">=2.0.0",
"react": ">=18",
"react-dom": ">=18"
},
"dependencies": {
"@nextui-org/react-utils": "workspace:*",
"@nextui-org/shared-utils": "workspace:*",
"@nextui-org/shared-icons": "workspace:*",
"@react-aria/button": "3.9.5",
"@react-aria/toast": "3.0.0-beta.15",
"@react-aria/utils": "3.24.1",
"@react-stately/toast": "3.0.0-beta.5"
},
"devDependencies": {
"@nextui-org/system": "workspace:*",
"@nextui-org/theme": "workspace:*",
"@nextui-org/button": "workspace:*",
"clean-package": "2.2.0",
"react": "^18.0.0",
"react-dom": "^18.0.0"
},
"clean-package": "../../../clean-package.config.json"
}
13 changes: 13 additions & 0 deletions packages/components/toast/src/index.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
import Toast from "./toast";
import {ToastProvider} from "./toast-provider";

// export types
export type {ToastProps} from "./toast";

// export hooks
export {useToast} from "./use-toast";
export {addToast} from "./toast-provider";

// export component
export {Toast};
export {ToastProvider};
60 changes: 60 additions & 0 deletions packages/components/toast/src/toast-provider.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,60 @@
import {ToastOptions, ToastQueue, useToastQueue} from "@react-stately/toast";
import {ToastVariantProps} from "@nextui-org/theme";

import {ToastRegion} from "./toast-region";
import {ToastType} from "./use-toast";

let globalToastQueue: ToastQueue<ToastType> | null = null;

interface ToastProviderProps {
maxVisibleToasts?: number;
}

export const getToastQueue = (maxVisibleToasts: number) => {
if (!globalToastQueue) {
globalToastQueue = new ToastQueue({
maxVisibleToasts,
});
}

return globalToastQueue;
};

export const ToastProvider = ({maxVisibleToasts = 5}: ToastProviderProps) => {
const toastQueue = useToastQueue(getToastQueue(maxVisibleToasts));

if (toastQueue.visibleToasts.length == 0) {
return null;
}

return <>{<ToastRegion toastQueue={toastQueue} />}</>;
};

export const addToast = ({
title,
description,
priority,
timeout,
...config
}: {
title: string;
description: string;
} & ToastOptions &
ToastVariantProps) => {
if (!globalToastQueue) {
return;
}

const content: ToastType = {
title,
description,
config: config,
};

const options: Partial<ToastOptions> = {
timeout,
priority,
};

globalToastQueue.add(content, options);
};
31 changes: 31 additions & 0 deletions packages/components/toast/src/toast-region.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,31 @@
import {useRef} from "react";
import {useToastRegion, AriaToastRegionProps} from "@react-aria/toast";
import {QueuedToast, ToastState} from "@react-stately/toast";

import Toast from "./toast";
import {ToastType} from "./use-toast";

interface ToastRegionProps<T> extends AriaToastRegionProps {
toastQueue: ToastState<T>;
}

export function ToastRegion<T extends ToastType>({toastQueue, ...props}: ToastRegionProps<T>) {
const ref = useRef(null);
const {regionProps} = useToastRegion(props, toastQueue, ref);

return (
<>
<div
{...regionProps}
ref={ref}
className="fixed bottom-0 left-0 w-screen flex flex-col items-center justify-center"
>
{toastQueue.visibleToasts.map((toast: QueuedToast<ToastType>) => {
return (
<Toast key={toast.key} state={toastQueue} toast={toast} {...toast.content.config} />
);
})}
</div>
</>
);
}
54 changes: 54 additions & 0 deletions packages/components/toast/src/toast.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,54 @@
import {forwardRef} from "@nextui-org/system";
import {Button, ButtonProps} from "@nextui-org/button";
import {CloseIcon} from "@nextui-org/shared-icons";

import {Progress} from "../../../core/react/src";

import {UseToastProps, useToast} from "./use-toast";

export interface ToastProps extends UseToastProps {}

const Toast = forwardRef<"div", ToastProps>((props, ref) => {
const {
Component,
Icon,
domRef,
endContent,
closeProgressBarValue,
getToastProps,
getContentProps,
getTitleProps,
getDescriptionProps,
getProgressBarProps,
getCloseButtonProps,
getIconProps,
} = useToast({
...props,
ref,
});

return (
<Component ref={domRef} {...getToastProps()}>
<main {...getContentProps()}>
<Icon {...getIconProps()} />
<div>
<div {...getTitleProps()}>{props.toast.content.title}</div>
<div {...getDescriptionProps()}>{props.toast.content.description}</div>
</div>
</main>
<Button {...(getCloseButtonProps() as ButtonProps)} isIconOnly variant="bordered">
<CloseIcon />
</Button>
{endContent}
<Progress
{...getProgressBarProps()}
aria-label="toast-close-indicator"
value={closeProgressBarValue}
/>
</Component>
);
});

Toast.displayName = "NextUI.Toast";

export default Toast;
Loading

0 comments on commit d3ad47a

Please sign in to comment.