BottomSheet
bottomsheet-1779361465732.tsx
'use client';
import { useState } from 'react';
interface BottomSheetProps {
isOpen: boolean;
onClose: () => void;
}
const BottomSheet = ({ isOpen, onClose }: BottomSheetProps) => {
const [isDragging, setIsDragging] = useState(false);
const [offset, setOffset] = useState(0);
const handleDrag = (e: React.TouchEvent<HTMLDivElement> | React.MouseEvent<HTMLDivElement>) => {
if (e.type === 'touchmove') {
const touch = e.touches[0];
setOffset(touch.clientY);
} else if (e.type === 'mousemove') {
setOffset(e.clientY);
}
};
const handleDragEnd = () => {
if (offset > window.innerHeight / 2) {
onClose();
}
setIsDragging(false);
};
return (
<>
{isOpen && (
<div
className="fixed top-0 left-0 z-50 w-full h-full bg-zinc-900 bg-opacity-50"
onClick={onClose}
/>
)}
<div
className={`fixed bottom-0 w-full max-h-screen overflow-hidden bg-zinc-950 transition-transform duration-300 ease-out ${
isOpen ? 'translate-y-0' : 'translate-y-full'
}`}
style={{
boxShadow: '0px -10px 20px rgba(0, 0, 0, 0.2)',
WebkitBoxShadow: '0px -10px 20px rgba(0, 0, 0, 0.2)',
}}
>
<div
className="h-6 w-full bg-zinc-950 cursor-pointer"
onTouchStart={() => setIsDragging(true)}
onTouchMove={(e) => handleDrag(e)}
onTouchEnd={handleDragEnd}
onMouseDown={() => setIsDragging(true)}
onMouseMove={(e) => handleDrag(e)}
onMouseUp={handleDragEnd}
>
<div className="h-1 w-20 mx-auto bg-c9a84c rounded-full" />
</div>
<div className="p-4">
<h2 className="text-lg font-bold text-c9a84c mb-2">Bottom Sheet Title</h2>
<p className="text-sm text-zinc-400">
Lorem ipsum dolor sit amet, consectetur adipiscing elit. Sed sit amet nulla auctor, vestibulum magna sed, convallis ex.
</p>
</div>
</div>
</>
);
};
export default BottomSheet;Component info
CategoryOverlays
Frameworkreact
TierFREE
Views0
Copies0
About
Mobile-style bottom sheet drawer
More from Overlays
import React, { useState } from 'react';
import './SlideDrawer.css';
interface SlideDrawerProps {
isOpen: boolean;
onClose: () => void;
children: React.ReactNode;
}
const SlideDrawer: React.FC<SlideDrawerProps> = ({ isOpen, onClose, children SlideDrawer
Overlays
import React, { useState } from 'react';
interface ContextMenuProps {
children: React.ReactNode;
}
const ContextMenu: React.FC<ContextMenuProps> = ({ children }) => {
const [showMenu, setShowMenu] = useState(false);
const [x, setX] = useStateContextMenu
Overlays
'use client';
import React, { useState } from 'react';
interface AlertDialogProps {
isOpen: boolean;
onClose: () => void;
onConfirm: () => void;
title: string;
description: string;
}
const AlertDialog: React.FC<AlertDialogProps> = ({
iAlertDialog
Overlays
'use client';
import { useState, useEffect } from 'react';
interface Command {
id: number;
title: string;
description: string;
}
const commands: Command[] = [
{ id: 1, title: 'New File', description: 'Create a new file' },
{ id: 2, titleCommandPalette
Overlays