diff --git a/package.json b/package.json
index 24f816555..5f02243d8 100644
--- a/package.json
+++ b/package.json
@@ -66,6 +66,7 @@
"lodash.without": "^4.4.0",
"memoize-one": "^5.1.1",
"prop-types": "^15.7.2",
+ "react-confetti": "^6.1.0",
"react-imask": "^6.2.2",
"react-resize-detector": "^4.2.3",
"react-select-plus": "1.2.0",
diff --git a/src/components/Confetti/Confetti.stories.js b/src/components/Confetti/Confetti.stories.js
new file mode 100644
index 000000000..267eb6fc0
--- /dev/null
+++ b/src/components/Confetti/Confetti.stories.js
@@ -0,0 +1,110 @@
+import { array, boolean, number } from '@storybook/addon-knobs';
+import React, { useState } from 'react';
+import Button from '../Button/Button';
+import ButtonToolbar from '../Button/ButtonToolbar';
+
+import Modal from '../Modal/Modal';
+import ModalBody from '../Modal/ModalBody';
+import ModalFooter from '../Modal/ModalFooter';
+import ModalHeader from '../Modal/ModalHeader';
+import ConfettiDropper from './Confetti';
+
+export default {
+ title: 'Confetti',
+ component: ConfettiDropper,
+ parameters: {
+ sourceLink: 'Modal/Modal.js',
+ },
+};
+
+export const SimpleExample = () => {
+ const [open, setOpen] = useState(false);
+ return (
+ <>
+
+
+
+ setOpen(false)}>Modal title
+ Congrats!!!!
+
+
+
+
+
+
+
+ >
+ );
+};
+
+export const HeartsExample = () => {
+ const [open, setOpen] = useState(false);
+ return (
+ <>
+
+
+ {
+ ctx.save();
+ ctx.beginPath();
+ const dim = 20;
+ const offset = dim / 5;
+ ctx.moveTo(offset + 0, offset + dim / 2);
+ ctx.lineTo(offset + dim / 2, offset + dim);
+ ctx.lineTo(offset + dim, offset + dim / 2);
+ ctx.moveTo(offset, offset + dim / 2);
+ const radius = Math.sqrt((dim * dim) / 4 + (dim * dim) / 4) / 2;
+ ctx.arc(
+ offset + dim / 4,
+ offset + dim / 4,
+ radius,
+ (Math.PI * 3) / 4,
+ (Math.PI * 7) / 4
+ );
+ ctx.arc(
+ offset + (3 * dim) / 4,
+ offset + dim / 4,
+ radius,
+ (Math.PI * 5) / 4,
+ Math.PI / 4
+ );
+ ctx.closePath();
+ ctx.fill();
+ ctx.restore();
+ }}
+ recycle={false}
+ />
+ setOpen(false)}>Modal title
+ ♥♥♥♥♥♥♥♥ Congrats!!!! ♥♥♥♥♥♥♥♥
+
+
+
+
+
+
+
+ >
+ );
+};
diff --git a/src/components/Confetti/Confetti.tsx b/src/components/Confetti/Confetti.tsx
new file mode 100644
index 000000000..3918e681d
--- /dev/null
+++ b/src/components/Confetti/Confetti.tsx
@@ -0,0 +1,31 @@
+import React, { FC, useCallback, useState } from 'react';
+import Confetti from 'react-confetti';
+
+export interface ConfettiProps {
+ fullWidth?: boolean;
+}
+
+const ConfettiDropper: FC = ({
+ fullWidth = true,
+ ...props
+}) => {
+ props = {
+ ...(fullWidth && { style: { position: 'fixed' }, height: window.innerHeight }),
+ ...props
+ }
+ const [width, setWidth] = useState(0);
+
+ const div = useCallback((node) => {
+ if (node !== null) {
+ // set width to width of div or screen
+ setWidth(fullWidth ? window.innerWidth : node.getBoundingClientRect().width);
+ }
+ }, [fullWidth]);
+ return (
+
+
+
+ );
+};
+
+export default ConfettiDropper;