Skip to content

Commit f36d4b1

Browse files
committed
feature: datepicker
1 parent a0f04ed commit f36d4b1

File tree

10 files changed

+284
-5
lines changed

10 files changed

+284
-5
lines changed

docs/.vitepress/config.mts

Lines changed: 13 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -21,15 +21,18 @@ function buildSidebar() {
2121
{
2222
text: 'Typography',
2323
collapsible: true,
24-
items: [
25-
...getTypography(),
26-
]
24+
items: [...getTypography()],
2725
},
2826
{
2927
text: 'Utils',
3028
collapsible: true,
3129
items: [...getUtils()],
3230
},
31+
{
32+
text: 'Plugins',
33+
collapsible: true,
34+
items: [...getPlugins()],
35+
},
3336
]
3437
}
3538

@@ -88,7 +91,13 @@ function getTypography() {
8891
{ text: 'Heading', link: '/components/heading' },
8992
{ text: 'Paragraph', link: '/components/paragraph' },
9093
{ text: 'Image', link: '/components/image' },
91-
{ text: 'Link', link: '/components/link' }
94+
{ text: 'Link', link: '/components/link' },
95+
]
96+
}
97+
98+
function getPlugins() {
99+
return [
100+
{ text: 'Datepicker', link: '/components/datepicker' },
92101
]
93102
}
94103

docs/components/datepicker.md

Lines changed: 54 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,54 @@
1+
<script setup>
2+
import FwbDatepickerExampleDefault from './datepicker/examples/FwbDatepickerExampleDefault.vue'
3+
import FwbDatepickerExampleCustomIcon from './datepicker/examples/FwbDatepickerExampleCustomIcon.vue'
4+
</script>
5+
6+
# Vue Datepicker - Flowbite
7+
8+
#### Get started with the datepicker component to let the user choose dates in the form with multiple styles and colors
9+
10+
:::tip
11+
Original reference: [https://flowbite.com/docs/plugins/datepicker/](https://flowbite.com/docs/components/accordion/)\
12+
Options: [https://github.com/themesberg/flowbite-datepicker/blob/master/docs/options.md](https://github.com/themesberg/flowbite-datepicker/blob/master/docs/options.md)
13+
:::
14+
15+
<fwb-datepicker-example-default></fwb-datepicker-example-default>
16+
17+
```vue
18+
<template>
19+
<fwb-datepicker></fwb-datepicker>
20+
</template>
21+
22+
<script setup lang="ts">
23+
import { FwbDatepicker } from '../../../../src/index'
24+
</script>
25+
```
26+
27+
Here is an example with some more customization.
28+
<fwb-datepicker-example-custom-icon></fwb-datepicker-example-custom-icon>
29+
30+
```vue
31+
<template>
32+
<fwb-datepicker
33+
v-model="model"
34+
autohide
35+
format="DD dd MM yyyy"
36+
clear-btn
37+
today-btn
38+
:today-btn-mode="1"
39+
title="Example datepicker"
40+
:week-start="1"
41+
>
42+
<template #calendar-icon>
43+
<calendar-icon></calendar-icon>
44+
</template>
45+
</fwb-datepicker>
46+
</template>
47+
48+
<script setup lang="ts">
49+
import { FwbDatepicker } from '../../../../src/index'
50+
import CalendarIcon from '../assets/CalendarIcon.vue'
51+
52+
const model = defineModel({ default: new Date() })
53+
</script>
54+
```
Lines changed: 25 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,25 @@
1+
<template>
2+
<svg
3+
class="w-4 h-4 text-gray-500 dark:text-gray-400"
4+
viewBox="0 0 14 14"
5+
fill="none"
6+
xmlns="http://www.w3.org/2000/svg"
7+
>
8+
<g clip-path="url(#clip0_5993_10460)">
9+
<path
10+
d="M11.666 1.75016H11.0827V0.583496H9.91602V1.75016H4.08268V0.583496H2.91602V1.75016H2.33268C1.69102 1.75016 1.16602 2.27516 1.16602 2.91683V12.2502C1.16602 12.8918 1.69102 13.4168 2.33268 13.4168H11.666C12.3077 13.4168 12.8327 12.8918 12.8327 12.2502V2.91683C12.8327 2.27516 12.3077 1.75016 11.666 1.75016ZM11.666 12.2502H2.33268V5.8335H11.666V12.2502ZM11.666 4.66683H2.33268V2.91683H11.666V4.66683Z"
11+
fill="grey"
12+
/>
13+
</g>
14+
<defs>
15+
<clipPath id="clip0_5993_10460">
16+
<rect
17+
width="20"
18+
height="20"
19+
fill="white"
20+
/>
21+
</clipPath>
22+
</defs>
23+
</svg>
24+
</template>
25+
<script setup lang="ts"></script>
Lines changed: 23 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,23 @@
1+
<template>
2+
<fwb-datepicker
3+
v-model="model"
4+
autohide
5+
format="DD dd MM yyyy"
6+
clear-btn
7+
today-btn
8+
:today-btn-mode="1"
9+
title="Example datepicker"
10+
:week-start="1"
11+
>
12+
<template #calendar-icon>
13+
<calendar-icon />
14+
</template>
15+
</fwb-datepicker>
16+
</template>
17+
18+
<script setup lang="ts">
19+
import { FwbDatepicker } from '../../../../src/index'
20+
import CalendarIcon from '../assets/CalendarIcon.vue'
21+
22+
const model = defineModel<string | Date | null>({ default: new Date() })
23+
</script>
Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,7 @@
1+
<template>
2+
<fwb-datepicker />
3+
</template>
4+
5+
<script setup lang="ts">
6+
import { FwbDatepicker } from '../../../../src/index'
7+
</script>

package-lock.json

Lines changed: 10 additions & 1 deletion
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

package.json

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -75,6 +75,7 @@
7575
"classnames": "2.5.1",
7676
"floating-vue": "^5.2.2",
7777
"flowbite": "2.3.0",
78+
"flowbite-datepicker": "^1.2.6",
7879
"lodash-es": "4.17.21",
7980
"nanoid": "5.0.7",
8081
"tailwind-merge": "2.3.0",
Lines changed: 147 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,147 @@
1+
<template>
2+
<div class="relative max-w-sm">
3+
<div class="absolute inset-y-0 pe-3.5 end-0 flex items-center pointer-events-none">
4+
<slot name="calendar-icon">
5+
<svg
6+
class="w-4 h-4 text-gray-500 dark:text-gray-400"
7+
aria-hidden="true"
8+
xmlns="http://www.w3.org/2000/svg"
9+
fill="currentColor"
10+
viewBox="0 0 20 20"
11+
>
12+
<path
13+
d="M20 4a2 2 0 0 0-2-2h-2V1a1 1 0 0 0-2 0v1h-3V1a1 1 0 0 0-2 0v1H6V1a1 1 0 0 0-2 0v1H2a2 2 0 0 0-2 2v2h20V4ZM0 18a2 2 0 0 0 2 2h16a2 2 0 0 0 2-2V8H0v10Zm5-8h10a1 1 0 0 1 0 2H5a1 1 0 0 1 0-2Z"
14+
/>
15+
</svg>
16+
</slot>
17+
</div>
18+
<input
19+
ref="datepickerRef"
20+
type="text"
21+
class="bg-gray-50 border border-gray-300 text-gray-900 text-sm rounded-lg focus:ring-blue-500 focus:border-blue-500 block w-full dark:bg-gray-700 dark:border-gray-600 dark:placeholder-gray-400 dark:text-white dark:focus:ring-blue-500 dark:focus:border-blue-500"
22+
placeholder="Select date"
23+
@changeDate="(target: any) => (model = target.detail.date)"
24+
>
25+
</div>
26+
</template>
27+
28+
<script lang="ts" setup>
29+
import Datepicker from 'flowbite-datepicker/Datepicker'
30+
import { onMounted, onUnmounted, onUpdated, ref } from 'vue'
31+
import type { DateInput } from '@/components/FwbDatepicker/types'
32+
33+
interface FwbDatePickerProps {
34+
autohide?: boolean
35+
beforeShowDay?(date: Date): { enabled: boolean; classes: string; content: string } | string | boolean | null
36+
beforeShowDecade?(date: Date): { enabled: boolean; classes: string; content: string } | string | boolean | null
37+
beforeShowMonth?(date: Date): { enabled: boolean; classes: string; content: string } | string | boolean | null
38+
beforeShowYear?(date: Date): { enabled: boolean; classes: string; content: string } | string | boolean | null
39+
buttonClass?: string
40+
calendarWeeks?: boolean
41+
clearBtn?: boolean
42+
container?: string
43+
dateDelimiter?: string
44+
dateDisabled?: DateInput[]
45+
daysOfWeekDisabled?: number[]
46+
daysOfWeekHighlighted?: number[]
47+
defaultViewDate?: DateInput
48+
disableTouchKeyboard?: boolean
49+
format?:
50+
| string
51+
| {
52+
format: {
53+
toValue(date: DateInput, format: object, locale: object): Date
54+
toDisplay(date: Date, format: object, locale: object): string
55+
}
56+
}
57+
language?: string
58+
maxDate?: DateInput | null
59+
maxNumberOfDates?: number
60+
maxView?: number
61+
minDate?: DateInput | null
62+
nextArrow?: string
63+
orientation?: string
64+
pickLevel?: number
65+
prevArrow?: string
66+
showDaysOfWeek?: boolean
67+
showOnClick?: boolean
68+
showOnFocus?: boolean
69+
startView?: number
70+
title?: string
71+
todayBtn?: boolean
72+
todayBtnMode?: number
73+
todayHighlight?: boolean
74+
updateOnBlur?: boolean
75+
weekStart?: number
76+
}
77+
78+
const props = withDefaults(defineProps<FwbDatePickerProps>(), {
79+
autohide: false,
80+
beforeShowDay: () => null,
81+
beforeShowDecade: () => null,
82+
beforeShowMonth: () => null,
83+
beforeShowYear: () => null,
84+
buttonClass: 'button',
85+
calendarWeeks: false,
86+
clearBtn: false,
87+
container: 'body',
88+
dateDelimiter: ',',
89+
dateDisabled: () => [],
90+
daysOfWeekDisabled: () => [],
91+
daysOfWeekHighlighted: () => [],
92+
defaultViewDate: Date.now(),
93+
disableTouchKeyboard: false,
94+
format: 'mm/dd/yyyy',
95+
language: 'en',
96+
maxDate: null,
97+
maxNumberOfDates: 1,
98+
maxView: 3,
99+
minDate: null,
100+
nextArrow: undefined,
101+
orientation: 'auto',
102+
pickLevel: 0,
103+
prevArrow: undefined,
104+
showDaysOfWeek: true,
105+
showOnClick: true,
106+
showOnFocus: true,
107+
startView: 0,
108+
title: '',
109+
todayBtn: false,
110+
// 0 - focus, 1 - select
111+
todayBtnMode: 0,
112+
todayHighlight: false,
113+
updateOnBlur: true,
114+
weekStart: 0,
115+
})
116+
117+
const datepickerRef = ref<Datepicker | null>(null)
118+
let datepickerInstance: Datepicker | null = null
119+
120+
const refreshDatepicker = () => {
121+
if (!model.value) {
122+
datepickerInstance.setDate([], {
123+
clear: true,
124+
})
125+
} else {
126+
datepickerInstance.setDate([new Date(model.value)], {
127+
clear: true,
128+
})
129+
}
130+
}
131+
132+
onMounted(() => {
133+
datepickerInstance = new Datepicker(datepickerRef.value, { ...props })
134+
refreshDatepicker()
135+
})
136+
137+
onUpdated(() => {
138+
refreshDatepicker()
139+
})
140+
141+
onUnmounted(() => {
142+
if (datepickerInstance) {
143+
datepickerInstance.destroy()
144+
}
145+
})
146+
const model = defineModel<DateInput | null>()
147+
</script>

src/components/FwbDatepicker/types.ts

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1 @@
1+
export type DateInput = Date | string | number

src/index.ts

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -78,4 +78,7 @@ export { default as FlowbiteThemable } from './components/utils/FlowbiteThemable
7878
export { default as FlowbiteThemableChild } from './components/utils/FlowbiteThemable/FlowbiteThemableChild.vue'
7979
export { default as FwbSlotListener } from './components/utils/FwbSlotListener/FwbSlotListener.vue'
8080

81+
// plugins
82+
export { default as FwbDatepicker } from './components/FwbDatepicker/FwbDatepicker.vue'
83+
8184
export * from './composables'

0 commit comments

Comments
 (0)