-
Star
(176)
You must be signed in to star a gist -
Fork
(27)
You must be signed in to fork a gist
-
-
Save mjbalcueva/1fbcb1be9ef68a82c14d778b686a04fa to your computer and use it in GitHub Desktop.
| "use client" | |
| import * as React from "react" | |
| import { buttonVariants } from "@/components/ui/button" | |
| import { ScrollArea } from "@/components/ui/scroll-area" | |
| import { Select, SelectContent, SelectItem, SelectTrigger, SelectValue } from "@/components/ui/select" | |
| import { cn } from "@/lib/utils" | |
| import { ChevronLeft, ChevronRight } from "lucide-react" | |
| import { DayPicker, DropdownProps } from "react-day-picker" | |
| export type CalendarProps = React.ComponentProps<typeof DayPicker> | |
| function Calendar({ className, classNames, showOutsideDays = true, ...props }: CalendarProps) { | |
| return ( | |
| <DayPicker | |
| showOutsideDays={showOutsideDays} | |
| className={cn("p-3", className)} | |
| classNames={{ | |
| months: "flex flex-col sm:flex-row space-y-4 sm:space-x-4 sm:space-y-0", | |
| month: "space-y-4", | |
| caption: "flex justify-center pt-1 relative items-center", | |
| caption_label: "text-sm font-medium", | |
| caption_dropdowns: "flex justify-center gap-1", | |
| nav: "space-x-1 flex items-center", | |
| nav_button: cn( | |
| buttonVariants({ variant: "outline" }), | |
| "h-7 w-7 bg-transparent p-0 opacity-50 hover:opacity-100" | |
| ), | |
| nav_button_previous: "absolute left-1", | |
| nav_button_next: "absolute right-1", | |
| table: "w-full border-collapse space-y-1", | |
| head_row: "flex", | |
| head_cell: "text-muted-foreground rounded-md w-9 font-normal text-[0.8rem]", | |
| row: "flex w-full mt-2", | |
| cell: "text-center text-sm p-0 relative [&:has([aria-selected])]:bg-accent first:[&:has([aria-selected])]:rounded-l-md last:[&:has([aria-selected])]:rounded-r-md focus-within:relative focus-within:z-20", | |
| day: cn(buttonVariants({ variant: "ghost" }), "h-9 w-9 p-0 font-normal aria-selected:opacity-100"), | |
| day_selected: | |
| "bg-primary text-primary-foreground hover:bg-primary hover:text-primary-foreground focus:bg-primary focus:text-primary-foreground", | |
| day_today: "bg-accent text-accent-foreground", | |
| day_outside: "text-muted-foreground opacity-50", | |
| day_disabled: "text-muted-foreground opacity-50", | |
| day_range_middle: "aria-selected:bg-accent aria-selected:text-accent-foreground", | |
| day_hidden: "invisible", | |
| ...classNames, | |
| }} | |
| components={{ | |
| Dropdown: ({ value, onChange, children, ...props }: DropdownProps) => { | |
| const options = React.Children.toArray(children) as React.ReactElement<React.HTMLProps<HTMLOptionElement>>[] | |
| const selected = options.find((child) => child.props.value === value) | |
| const handleChange = (value: string) => { | |
| const changeEvent = { | |
| target: { value }, | |
| } as React.ChangeEvent<HTMLSelectElement> | |
| onChange?.(changeEvent) | |
| } | |
| return ( | |
| <Select | |
| value={value?.toString()} | |
| onValueChange={(value) => { | |
| handleChange(value) | |
| }} | |
| > | |
| <SelectTrigger className="pr-1.5 focus:ring-0"> | |
| <SelectValue>{selected?.props?.children}</SelectValue> | |
| </SelectTrigger> | |
| <SelectContent position="popper"> | |
| <ScrollArea className="h-80"> | |
| {options.map((option, id: number) => ( | |
| <SelectItem key={`${option.props.value}-${id}`} value={option.props.value?.toString() ?? ""}> | |
| {option.props.children} | |
| </SelectItem> | |
| ))} | |
| </ScrollArea> | |
| </SelectContent> | |
| </Select> | |
| ) | |
| }, | |
| IconLeft: ({ ...props }) => <ChevronLeft className="h-4 w-4" />, | |
| IconRight: ({ ...props }) => <ChevronRight className="h-4 w-4" />, | |
| }} | |
| {...props} | |
| /> | |
| ) | |
| } | |
| Calendar.displayName = "Calendar" | |
| export { Calendar } |
| /* add this snippet in your globals.css file */ | |
| .rdp-vhidden { | |
| @apply hidden; | |
| } |
| "use client" | |
| import * as React from "react" | |
| import { Button } from "@/components/ui/button" | |
| import { Calendar } from "@/components/ui/calendar" | |
| import { Popover, PopoverContent, PopoverTrigger } from "@/components/ui/popover" | |
| import { cn } from "@/lib/utils" | |
| import { format } from "date-fns" | |
| import { CalendarIcon } from "lucide-react" | |
| export function SampleDatePicker() { | |
| const [date, setDate] = React.useState<Date>() | |
| return ( | |
| <Popover> | |
| <PopoverTrigger asChild> | |
| <Button | |
| variant={"outline"} | |
| className={cn("w-[240px] justify-start text-left font-normal", !date && "text-muted-foreground")} | |
| > | |
| <CalendarIcon className="mr-2 h-4 w-4" /> | |
| {date ? format(date, "PPP") : <span>Pick a date</span>} | |
| </Button> | |
| </PopoverTrigger> | |
| <PopoverContent align="start" className=" w-auto p-0"> | |
| <Calendar | |
| mode="single" | |
| captionLayout="dropdown-buttons" | |
| selected={date} | |
| onSelect={setDate} | |
| fromYear={1960} | |
| toYear={2030} | |
| /> | |
| </PopoverContent> | |
| </Popover> | |
| ) | |
| } |
you have to use the calendar component in the repository not the shadcn default one, try that and see
i have component called calendar.tsx
in that i have this code
"use client";
import * as React from "react";
import { DayPicker, Dropdown as DropDownDayPicker } from "react-day-picker";
import { buttonVariants } from "@/components/ui/button";
import {
Select,
SelectContent,
SelectItem,
SelectTrigger,
SelectValue,
} from "@/components/ui/select";
import { cn } from "@/lib/utils";
export type CalendarProps = React.ComponentProps & {
captionLabelClassName?: string;
dayClassName?: string;
dayButtonClassName?: string;
dropdownsClassName?: string;
footerClassName?: string;
monthClassName?: string;
monthCaptionClassName?: string;
monthGridClassName?: string;
monthsClassName?: string;
weekClassName?: string;
weekdayClassName?: string;
weekdaysClassName?: string;
rangeEndClassName?: string;
rangeMiddleClassName?: string;
rangeStartClassName?: string;
selectedClassName?: string;
disabledClassName?: string;
hiddenClassName?: string;
outsideClassName?: string;
todayClassName?: string;
selectTriggerClassName?: string;
};
function Calendar({
className,
classNames,
hideNavigation,
showOutsideDays = true,
components: customComponents,
...props
}: CalendarProps) {
const _monthsClassName = cn(
"relative flex flex-col gap-4 sm:flex-row",
props.monthsClassName,
);
const _monthCaptionClassName = cn(
"relative flex h-7 items-center justify-center",
props.monthCaptionClassName,
);
const _dropdownsClassName = cn(
"flex items-center justify-center gap-2 w-full",
hideNavigation ? "w-full" : "",
props.dropdownsClassName,
);
const _footerClassName = cn("pt-3 text-sm", props.footerClassName);
const _weekdaysClassName = cn("flex", props.weekdaysClassName);
const _weekdayClassName = cn(
"w-9 text-sm font-normal text-muted-foreground",
props.weekdayClassName,
);
const _captionLabelClassName = cn(
"truncate text-sm font-medium",
props.captionLabelClassName,
);
const _monthGridClassName = cn("mx-auto mt-4", props.monthGridClassName);
const _weekClassName = cn("mt-2 flex w-max items-start", props.weekClassName);
const _dayClassName = cn(
"flex size-9 flex-1 items-center justify-center p-0 text-sm",
props.dayClassName,
);
const _dayButtonClassName = cn(
buttonVariants({ variant: "ghost" }),
"size-9 rounded-md p-0 font-normal transition-none aria-selected:opacity-100",
props.dayButtonClassName,
);
const buttonRangeClassName =
"bg-accent [&>button]:bg-primary [&>button]:text-primary-foreground [&>button]:hover:bg-primary [&>button]:hover:text-primary-foreground";
const _rangeStartClassName = cn(
buttonRangeClassName,
"rounded-s-md",
props.rangeStartClassName,
);
const _rangeEndClassName = cn(
buttonRangeClassName,
"rounded-e-md",
props.rangeEndClassName,
);
const _rangeMiddleClassName = cn(
"bg-accent !text-foreground [&>button]:bg-transparent [&>button]:!text-foreground [&>button]:hover:bg-transparent [&>button]:hover:!text-foreground",
props.rangeMiddleClassName,
);
const _selectedClassName = cn(
"[&>button]:bg-primary [&>button]:text-primary-foreground [&>button]:hover:bg-primary [&>button]:hover:text-primary-foreground",
props.selectedClassName,
);
const _todayClassName = cn(
"[&>button]:bg-accent [&>button]:text-accent-foreground",
props.todayClassName,
);
const _outsideClassName = cn(
"text-muted-foreground opacity-50 aria-selected:bg-accent/50 aria-selected:text-muted-foreground aria-selected:opacity-30",
props.outsideClassName,
);
const _disabledClassName = cn(
"text-muted-foreground opacity-50",
props.disabledClassName,
);
const _hiddenClassName = cn("invisible flex-1", props.hiddenClassName);
const Dropdown = React.useCallback(
({
value,
onChange,
options,
}: React.ComponentProps) => {
const selected = options?.find((option) => option.value === value);
const handleChange = (value: string) => {
const changeEvent = {
target: { value },
} as React.ChangeEvent;
onChange?.(changeEvent);
};
return (
<Select
value={value?.toString()}
onValueChange={(value) => {
handleChange(value);
}}
>
{selected?.label}
{options?.map(({ value, label, disabled }, id) => (
<SelectItem
key={
${value}-${id}}value={value?.toString()}
disabled={disabled}
>
{label}
))}
);
},
[],
);
return (
<DayPicker
showOutsideDays={showOutsideDays}
hideNavigation={true} // Ensure navigation is hidden
className={cn("p-3", className)}
classNames={{
caption_label: _captionLabelClassName,
day: _dayClassName,
day_button: _dayButtonClassName,
dropdowns: _dropdownsClassName,
footer: _footerClassName,
month: props.monthClassName,
month_caption: _monthCaptionClassName,
month_grid: _monthGridClassName,
months: _monthsClassName,
week: _weekClassName,
weekday: _weekdayClassName,
weekdays: _weekdaysClassName,
range_end: _rangeEndClassName,
range_middle: _rangeMiddleClassName,
range_start: _rangeStartClassName,
selected: _selectedClassName,
disabled: _disabledClassName,
hidden: _hiddenClassName,
outside: _outsideClassName,
today: _todayClassName,
nav: "hidden", // This hides the navigation (chevrons)
...classNames,
}}
components={{
Dropdown,
...customComponents,
}}
{...props}
/>
);
}
Calendar.displayName = "Calendar";
export { Calendar };
you have to use the calendar component in the repository not the shadcn default one, try that and see