Openstatus
www.openstatus.dev
1"use client";
2
3import * as React from "react";
4
5import { Button } from "@/components/ui/button";
6import {
7 Collapsible,
8 CollapsibleContent,
9 CollapsibleTrigger,
10} from "@/components/ui/collapsible";
11import { cn } from "@/lib/utils";
12
13export function BlockWrapper({
14 className,
15 children,
16 autoOpen,
17 ...props
18}: React.HTMLAttributes<HTMLDivElement> & {
19 autoOpen?: boolean;
20}) {
21 const ref = React.useRef<HTMLDivElement>(null);
22 const [isOpened, setIsOpened] = React.useState(false);
23
24 React.useEffect(() => {
25 if (ref.current && autoOpen) {
26 const height = ref.current.scrollHeight;
27 // NOTE: max-h-48 in tw equals 192px (48 * 4px)
28 if (height <= 192) {
29 setIsOpened(true);
30 }
31 }
32 }, [autoOpen]);
33
34 return (
35 <Collapsible open={isOpened} onOpenChange={setIsOpened}>
36 <div className={cn("relative overflow-hidden", className)} {...props}>
37 <CollapsibleContent
38 forceMount
39 ref={ref}
40 className={cn("overflow-hidden", !isOpened && "max-h-48")}
41 >
42 {children}
43 </CollapsibleContent>
44 {!isOpened ? (
45 <div
46 className={cn(
47 "absolute flex items-center justify-center bg-gradient-to-b from-transparent to-90% to-background p-2",
48 isOpened ? "inset-x-0 bottom-0 h-12" : "inset-0",
49 )}
50 >
51 <CollapsibleTrigger asChild>
52 <Button variant="outline" size="sm">
53 Expand
54 </Button>
55 </CollapsibleTrigger>
56 </div>
57 ) : null}
58 </div>
59 </Collapsible>
60 );
61}