php artisan aura:add scheduler
Copies the component source into resources/views/components/aura/. Run php artisan aura:init first if you haven't already. See the CLI guide for all options.
composer require bluestarsystem/aura-ui
php artisan aura:install
Full installation instructions in the Installation guide.
- Overview
- Basic Usage
- Props
- Dispatched Events
- Livewire Integration
- Month View
- Custom Event Keys
- Accessibility
Pro Component — This component requires an Aura UI Pro license.
Just need to display events? The free Calendar renders month/week/day read-only. The Scheduler adds interactive click-to-create/edit and drag move/resize/create.
Overview
The Scheduler renders a calendar in week (7 columns), day (1 column), or month (full month grid) view. In week/day views, a time-grid covers a configurable range of hours; events are positioned by their start/end datetimes and can be dragged to move, dragged at the bottom edge to resize, or clicked, and empty slots can be clicked or drag-selected to create new events. In month view, events render as chips inside day cells and can be dragged between days.
The scheduler never mutates its events array. Instead, it dispatches browser-level custom events (bubbling, datetime strings in Y-m-d H:i format) that the host Livewire component listens to via #[On(...)], persists the change, and re-passes the updated :events array to re-render.
Basic Usage
<x-aura::scheduler
view="day"
:date="now()->toDateString()"
:day-start="8"
:day-end="18"
:events="[
['id' => 1, 'title' => 'Standup', 'start' => now()->toDateString().' 09:00', 'end' => now()->toDateString().' 09:30', 'color' => 'primary'],
['id' => 2, 'title' => 'Code Review', 'start' => now()->toDateString().' 11:00', 'end' => now()->toDateString().' 12:00', 'color' => 'success'],
]"
/><x-aura::scheduler
view="day"
:date="now()->toDateString()"
:day-start="8"
:day-end="18"
:events="$events"
/>
Props
| Prop | Type | Default | Description |
|---|---|---|---|
events |
array |
[] |
Array of event objects to display. Each entry must have the fields named by the event*Key props. |
view |
'week'|'day'|'month' |
'week' |
Initial view mode. week shows 7 columns; day shows 1 column; month shows a full month grid. |
date |
string|null |
null |
Reference date (Y-m-d) for the visible period. Defaults to today when null. |
dayStart |
int |
8 |
First hour shown on the time-grid (0–23). |
dayEnd |
int |
20 |
Last hour shown on the time-grid. Must be greater than dayStart. |
slotMinutes |
int |
30 |
Duration of each time slot in minutes (minimum 5). |
slotHeight |
int |
48 |
Pixel height of each time slot row (minimum 16). |
locale |
string |
'en' |
UI locale for day/button labels. Supported: 'en', 'it'. |
startOfWeek |
int |
1 |
First day of week: 1 = Monday, 0 = Sunday. |
nowIndicator |
bool |
true |
Show a red line at the current time. |
eventIdKey |
string |
'id' |
Key used to read the event's unique identifier. |
eventTitleKey |
string |
'title' |
Key used to read the event's display title. |
eventStartKey |
string |
'start' |
Key used to read the event's start datetime (Y-m-d H:i). |
eventEndKey |
string |
'end' |
Key used to read the event's end datetime (Y-m-d H:i). |
eventColorKey |
string |
'color' |
Key used to read the event's color variant. Accepts Aura color tokens (e.g. primary, success, danger). |
Dispatched Events
The scheduler dispatches the following browser-level custom events (bubbling). All datetime values in payloads are ISO strings (Y-m-d H:i). The host is responsible for handling them and re-passing updated :events.
| Event | Payload | Triggered when |
|---|---|---|
aura-scheduler-slot-click |
{ start, end } |
User clicks an empty time slot. |
aura-scheduler-event-click |
{ id } |
User clicks an existing event (also fired by Enter/Space on a focused event button). |
aura-scheduler-event-drop |
{ id, start, end } |
User drags an event to a new position (duration is preserved). |
aura-scheduler-event-resize |
{ id, start, end } |
User drags the bottom edge of an event to change its end time (start is fixed). |
aura-scheduler-range-create |
{ start, end } |
User drag-selects an empty range to create a new event. |
aura-scheduler-day-click |
{ start, end } |
Clicking an empty day cell in month view. |
Livewire Integration
The scheduler is designed as a controlled component. The host Livewire component owns the $events array, listens for the dispatched events, persists changes to the database, and re-passes the updated array so the scheduler re-renders.
<?php
namespace App\Livewire;
use App\Models\CalendarEvent;
use Livewire\Attributes\On;
use Livewire\Component;
class SchedulerPage extends Component
{
/** @var array<int, array<string, mixed>> */
public array $events = [];
public function mount(): void
{
$this->loadEvents();
}
#[On('aura-scheduler-slot-click')]
public function onSlotClick(string $start, string $end): void
{
// Open a modal or inline form to create a new event.
// Example: dispatch a browser event to open a creation modal.
$this->dispatch('open-create-modal', start: $start, end: $end);
}
#[On('aura-scheduler-event-click')]
public function onEventClick(int|string $id): void
{
// Open a detail/edit modal for the clicked event.
$this->dispatch('open-edit-modal', id: $id);
}
#[On('aura-scheduler-event-drop')]
public function onEventDrop(int|string $id, string $start, string $end): void
{
CalendarEvent::where('id', $id)->update([
'start' => $start,
'end' => $end,
]);
$this->loadEvents();
}
#[On('aura-scheduler-event-resize')]
public function onEventResize(int|string $id, string $start, string $end): void
{
CalendarEvent::where('id', $id)->update([
'start' => $start,
'end' => $end,
]);
$this->loadEvents();
}
#[On('aura-scheduler-range-create')]
public function onRangeCreate(string $start, string $end): void
{
// Open a creation modal pre-filled with the selected range.
$this->dispatch('open-create-modal', start: $start, end: $end);
}
private function loadEvents(): void
{
$this->events = CalendarEvent::all()
->map(fn ($e) => [
'id' => $e->id,
'title' => $e->title,
'start' => $e->start,
'end' => $e->end,
'color' => $e->color ?? 'primary',
])
->toArray();
}
public function render(): \Illuminate\View\View
{
return view('livewire.scheduler-page');
}
}
{{-- livewire/scheduler-page.blade.php --}}
<div>
<x-aura::scheduler
view="week"
:events="$events"
/>
</div>
Month View
Set view="month" to render a full month grid. Each day cell shows event chips; the time-grid and slot interactions do not apply in this mode.
- Drag between days — dragging an event chip to another day cell moves the event: the date changes but the original time-of-day is preserved. Dispatches
aura-scheduler-event-dropwith the updatedstart/end. - Click an empty day cell — dispatches
aura-scheduler-day-clickwithstartset to that day at thedayStarthour andendsetslotMinuteslater. Use this to open a creation modal pre-filled with the date. - Click an event chip — dispatches
aura-scheduler-event-click { id }, same as in week/day view.
<x-aura::scheduler
view="month"
:date="now()->toDateString()"
:day-start="8"
:slot-minutes="30"
:events="[
['id' => 1, 'title' => 'Kick-off', 'start' => now()->startOfMonth()->addDays(2)->format('Y-m-d').' 09:00', 'end' => now()->startOfMonth()->addDays(2)->format('Y-m-d').' 10:00', 'color' => 'primary'],
['id' => 2, 'title' => 'Review', 'start' => now()->startOfMonth()->addDays(9)->format('Y-m-d').' 14:00', 'end' => now()->startOfMonth()->addDays(9)->format('Y-m-d').' 15:00', 'color' => 'success'],
]"
/><x-aura::scheduler
view="month"
:date="now()->toDateString()"
:day-start="8"
:slot-minutes="30"
:events="$events"
/>
Custom Event Keys
If your event model uses different field names, map them with the event*Key props:
<x-aura::scheduler
:events="$appointments"
event-id-key="uuid"
event-title-key="name"
event-start-key="begins_at"
event-end-key="ends_at"
event-color-key="category_color"
/>
Accessibility
Event editing is keyboard-accessible. Event blocks and month-view chips are rendered as <button> elements. Focusing an event with Tab and pressing Enter or Space dispatches aura-scheduler-event-click { id }, so the full edit flow is reachable without a pointer.
Drag interactions — move, resize (week/day), drag-between-days (month), and range-create — remain pointer-only. The scheduler does not render keyboard-focusable slot targets for drag-based creation. For keyboard and screen-reader users, provide host-level controls (e.g. a "New event" button and an event list with Edit actions) that invoke the same create/edit flow your #[On(...)] listeners use.
Event blocks expose an aria-label (title + time range) so assistive technology can announce them.