Skip to content

Commit 0354b37

Browse files
committed
added tooltips and refactored linkedslider
1 parent b0d0d89 commit 0354b37

12 files changed

+1529
-163
lines changed

components/ui/button.tsx

Lines changed: 13 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -1,8 +1,8 @@
1-
import * as React from "react"
2-
import { Slot } from "@radix-ui/react-slot"
3-
import { cva, type VariantProps } from "class-variance-authority"
1+
import { Slot } from "@radix-ui/react-slot";
2+
import { cva, type VariantProps } from "class-variance-authority";
3+
import * as React from "react";
44

5-
import { cn } from "@/lib/utils"
5+
import { cn } from "@/lib/utils";
66

77
const buttonVariants = cva(
88
"inline-flex items-center justify-center rounded-md text-sm font-medium ring-offset-background transition-colors focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-ring focus-visible:ring-offset-2 disabled:pointer-events-none disabled:opacity-50",
@@ -30,27 +30,27 @@ const buttonVariants = cva(
3030
variant: "default",
3131
size: "default",
3232
},
33-
}
34-
)
33+
},
34+
);
3535

3636
export interface ButtonProps
3737
extends React.ButtonHTMLAttributes<HTMLButtonElement>,
3838
VariantProps<typeof buttonVariants> {
39-
asChild?: boolean
39+
asChild?: boolean;
4040
}
4141

4242
const Button = React.forwardRef<HTMLButtonElement, ButtonProps>(
4343
({ className, variant, size, asChild = false, ...props }, ref) => {
44-
const Comp = asChild ? Slot : "button"
44+
const Comp = asChild ? Slot : "button";
4545
return (
4646
<Comp
4747
className={cn(buttonVariants({ variant, size, className }))}
4848
ref={ref}
4949
{...props}
5050
/>
51-
)
52-
}
53-
)
54-
Button.displayName = "Button"
51+
);
52+
},
53+
);
54+
Button.displayName = "Button";
5555

56-
export { Button, buttonVariants }
56+
export { Button, buttonVariants };

components/ui/input.tsx

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -12,13 +12,13 @@ const Input = React.forwardRef<HTMLInputElement, InputProps>(
1212
type={type}
1313
className={cn(
1414
"flex h-10 w-full rounded-md border border-input bg-background px-3 py-2 text-sm ring-offset-background file:border-0 file:bg-transparent file:text-sm file:font-medium placeholder:text-muted-foreground focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-ring focus-visible:ring-offset-2 disabled:cursor-not-allowed disabled:opacity-50",
15-
className
15+
className,
1616
)}
1717
ref={ref}
1818
{...props}
1919
/>
2020
);
21-
}
21+
},
2222
);
2323
Input.displayName = "Input";
2424

components/ui/label.tsx

Lines changed: 9 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -1,12 +1,12 @@
1-
import * as React from "react"
2-
import * as LabelPrimitive from "@radix-ui/react-label"
3-
import { cva, type VariantProps } from "class-variance-authority"
1+
import * as LabelPrimitive from "@radix-ui/react-label";
2+
import { cva, type VariantProps } from "class-variance-authority";
3+
import * as React from "react";
44

5-
import { cn } from "@/lib/utils"
5+
import { cn } from "@/lib/utils";
66

77
const labelVariants = cva(
8-
"text-sm font-medium leading-none peer-disabled:cursor-not-allowed peer-disabled:opacity-70"
9-
)
8+
"text-sm font-medium leading-none peer-disabled:cursor-not-allowed peer-disabled:opacity-70",
9+
);
1010

1111
const Label = React.forwardRef<
1212
React.ElementRef<typeof LabelPrimitive.Root>,
@@ -18,7 +18,7 @@ const Label = React.forwardRef<
1818
className={cn(labelVariants(), className)}
1919
{...props}
2020
/>
21-
))
22-
Label.displayName = LabelPrimitive.Root.displayName
21+
));
22+
Label.displayName = LabelPrimitive.Root.displayName;
2323

24-
export { Label }
24+
export { Label };

components/ui/linkedslider.tsx

Lines changed: 82 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,82 @@
1+
import { QuestionMarkCircledIcon } from "@radix-ui/react-icons";
2+
import { ChangeEvent, useId } from "react";
3+
4+
import { Button } from "@/components/ui/button";
5+
import { Input } from "@/components/ui/input";
6+
import { Label } from "@/components/ui/label";
7+
import {
8+
Popover,
9+
PopoverContent,
10+
PopoverTrigger,
11+
} from "@/components/ui/popover";
12+
import { Slider } from "@/components/ui/slider";
13+
14+
interface LinkedSliderProps {
15+
className?: string;
16+
label: string;
17+
description?: string;
18+
min: number;
19+
max: number;
20+
step: number;
21+
value: number;
22+
onChange: (value: number) => void;
23+
}
24+
25+
/**
26+
* A slider, input, and label that are linked together.
27+
* @param props
28+
* @returns
29+
*/
30+
const LinkedSlider = ({
31+
className,
32+
label,
33+
description,
34+
min,
35+
max,
36+
step,
37+
value,
38+
onChange,
39+
}: LinkedSliderProps) => {
40+
const inputId = useId();
41+
42+
return (
43+
<div className={className}>
44+
<div className="space-x-2">
45+
<Label htmlFor={inputId}>{label}</Label>
46+
<Popover>
47+
<PopoverTrigger>
48+
<Button variant="ghost" size="icon">
49+
<QuestionMarkCircledIcon className="h-4 w-4" />
50+
</Button>
51+
</PopoverTrigger>
52+
<PopoverContent>{description}</PopoverContent>
53+
</Popover>
54+
</div>
55+
<div className="flex flex-row space-x-2">
56+
<Slider
57+
value={[value]}
58+
min={min}
59+
max={max}
60+
step={step}
61+
onValueChange={(values: number[]) => {
62+
onChange(values[0]);
63+
}}
64+
/>
65+
<Input
66+
id={inputId}
67+
type="number"
68+
min={min}
69+
max={max}
70+
step={step}
71+
value={value}
72+
onChange={(e: ChangeEvent<HTMLInputElement>) => {
73+
onChange(parseInt(e.target.value));
74+
}}
75+
className="max-w-[100px]"
76+
/>
77+
</div>
78+
</div>
79+
);
80+
};
81+
82+
export { LinkedSlider };

components/ui/popover.tsx

Lines changed: 29 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,29 @@
1+
import * as PopoverPrimitive from "@radix-ui/react-popover";
2+
import * as React from "react";
3+
4+
import { cn } from "@/lib/utils";
5+
6+
const Popover = PopoverPrimitive.Root;
7+
8+
const PopoverTrigger = PopoverPrimitive.Trigger;
9+
10+
const PopoverContent = React.forwardRef<
11+
React.ElementRef<typeof PopoverPrimitive.Content>,
12+
React.ComponentPropsWithoutRef<typeof PopoverPrimitive.Content>
13+
>(({ className, align = "center", sideOffset = 4, ...props }, ref) => (
14+
<PopoverPrimitive.Portal>
15+
<PopoverPrimitive.Content
16+
ref={ref}
17+
align={align}
18+
sideOffset={sideOffset}
19+
className={cn(
20+
"z-50 w-72 rounded-md border bg-popover p-4 text-popover-foreground shadow-md outline-none data-[state=open]:animate-in data-[state=closed]:animate-out data-[state=closed]:fade-out-0 data-[state=open]:fade-in-0 data-[state=closed]:zoom-out-95 data-[state=open]:zoom-in-95 data-[side=bottom]:slide-in-from-top-2 data-[side=left]:slide-in-from-right-2 data-[side=right]:slide-in-from-left-2 data-[side=top]:slide-in-from-bottom-2",
21+
className,
22+
)}
23+
{...props}
24+
/>
25+
</PopoverPrimitive.Portal>
26+
));
27+
PopoverContent.displayName = PopoverPrimitive.Content.displayName;
28+
29+
export { Popover, PopoverContent, PopoverTrigger };

components/ui/slider.tsx

Lines changed: 7 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,7 @@
1-
import * as React from "react"
2-
import * as SliderPrimitive from "@radix-ui/react-slider"
1+
import * as SliderPrimitive from "@radix-ui/react-slider";
2+
import * as React from "react";
33

4-
import { cn } from "@/lib/utils"
4+
import { cn } from "@/lib/utils";
55

66
const Slider = React.forwardRef<
77
React.ElementRef<typeof SliderPrimitive.Root>,
@@ -11,7 +11,7 @@ const Slider = React.forwardRef<
1111
ref={ref}
1212
className={cn(
1313
"relative flex w-full touch-none select-none items-center",
14-
className
14+
className,
1515
)}
1616
{...props}
1717
>
@@ -20,7 +20,7 @@ const Slider = React.forwardRef<
2020
</SliderPrimitive.Track>
2121
<SliderPrimitive.Thumb className="block h-5 w-5 rounded-full border-2 border-primary bg-background ring-offset-background transition-colors focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-ring focus-visible:ring-offset-2 disabled:pointer-events-none disabled:opacity-50" />
2222
</SliderPrimitive.Root>
23-
))
24-
Slider.displayName = SliderPrimitive.Root.displayName
23+
));
24+
Slider.displayName = SliderPrimitive.Root.displayName;
2525

26-
export { Slider }
26+
export { Slider };

components/ui/textarea.tsx

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -11,13 +11,13 @@ const Textarea = React.forwardRef<HTMLTextAreaElement, TextareaProps>(
1111
<textarea
1212
className={cn(
1313
"flex min-h-[80px] w-full rounded-md border border-input bg-transparent px-3 py-2 text-sm ring-offset-background placeholder:text-muted-foreground focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-ring focus-visible:ring-offset-2 disabled:cursor-not-allowed disabled:opacity-50",
14-
className
14+
className,
1515
)}
1616
ref={ref}
1717
{...props}
1818
/>
1919
);
20-
}
20+
},
2121
);
2222
Textarea.displayName = "Textarea";
2323

0 commit comments

Comments
 (0)