React Availability Calendar
A customizable React component for displaying booking availabilities on a calendar.
No moment
dependency required, but accepts a moment
-like prop that needs to implement a subset of Moment
's API.
DatePoll app built on top of this component
DatePoll
Example installation
yarn add react-availability-calendar moment bootstrap
(or npm install
)
typescript definitions included
Props:
Provide bookings, from which avails will be derived, or avails
directly
export interface AvailabilityCalendarProps {
moment: MomentCtrFunc;
theme?: CalendarThemeProp;
onCalRangeChange?: (range: Range) => any;
providerTimeZone: string;
bookings: Booking[];
avails?: AvailabilityEvent[];
initialDate: Date | null;
onAvailabilitySelected: (e: AvailabilityEvent) => any;
onDaySelected?: (d: Date | null) => any;
blockOutPeriods?: MsSinceMidnightRange[];
excludeWeekends?: boolean;
excludeFn?: (date: Date) => boolean;
slotLengthMs?: number;
slotStepMs?: number;
}
Customize "Request Appointment" label:
pass theme={{requestAppointmentLabel: "Request Booking or other wording"}}
Installation:
npm install react-availability-calendar --save
Demos:
non-typescript example:
Usage:
import React from 'react';
import {
AvailabilityCalendar,
AvailabilityEvent,
MsSinceMidnightRange,
Booking,
Range,
CalendarThemeProp,
} from 'react-availability-calendar';
import moment from 'moment';
import 'bootstrap/dist/css/bootstrap.min.css';
import './custom.scss';
const msInHour = 60 * 60 * 1000;
const App: React.FC = () => {
const now = new Date();
const onAvailabilitySelected = (a: AvailabilityEvent) =>
console.log('Availability slot selected: ', a);
const onChangedCalRange = (r: Range) =>
console.log('Calendar range selected (fetch bookings here): ', r);
const blockOutPeriods: MsSinceMidnightRange[] = [
[0 * msInHour, 9 * msInHour],
[19 * msInHour, 24 * msInHour],
];
const bookings: Booking[] = [
{
startDate: new Date(2020, 2, 1, 19),
endDate: new Date(2020, 2, 1, 20),
},
{
startDate: new Date(2020, 2, 1, 16, 30),
endDate: new Date(2020, 2, 1, 17),
},
];
const providerTimeZone = 'America/New_York';
return (
<div style={{ width: 350 }}>
<AvailabilityCalendar
bookings={bookings}
providerTimeZone={providerTimeZone}
moment={moment}
initialDate={now}
onAvailabilitySelected={onAvailabilitySelected}
onCalRangeChange={onChangedCalRange}
blockOutPeriods={blockOutPeriods}
/>
</div>
);
};
export default App;
Customizability via overrides
const overrides =
{
...defaultComponents,
ToolBar: {
className: "border btn-group",
style: { minHeight: undefined }
},
ToolBarButton: {
className: "btn btn-outline-info",
style: { outline: "none" }
},
Weekday: {
style: {
borderWidth: 0,
borderStyle: "solid",
borderBottomWidth: 1,
borderRightWidth: 1,
borderColor: "#dddddd"
},
className: "none"
},
AvailSlot: {
className: p =>
myAvailSlotLogic(p.date)
? "btn btn-success"
: "btn btn-outline-primary"
},
DayCell: {
style: p =>
p.isSelected
? { transition: "width 200ms, height 200ms", height: 60, width: 60 }
: { transition: "width 200ms, height 200ms" },
className: p =>
myDayLogic(p.date)
? "rounded-circle border-success"
: p.isSelected || p.hasAvail
? "rounded-circle border-primary"
: "rounded-circle border-default"
}
};
<AvailabilityCalendar overrides={overrides} {...restOfProps} />
```
### Examples
- [Example](https://github.com/nyura123/react-availability-calendar/tree/master/examples/example1)
### Running an example
`cd example/example1`
`npm install`
`npm start`
## Bootstrapped with [TSDX](https://github.com/palmerhq/tsdx)