import {Component, inject, OnInit} from '@angular/core'; import {CommonModule, NgFor, NgIf} from '@angular/common'; import {TuiAlertService, TuiButton, TuiCalendar, tuiDateFormatProvider, TuiIcon} from '@taiga-ui/core'; import {Appointment} from '../../models/appointment'; import {ModalComponent} from '../../components/modal/modal.component'; import {FormControl, FormGroup, ReactiveFormsModule, Validators} from '@angular/forms'; import { TuiInputDateModule, TuiInputModule, TuiInputTimeModule, TuiTextareaModule, TuiTextfieldControllerModule } from '@taiga-ui/legacy'; import {TuiDay, TuiMonth, TuiTime} from '@taiga-ui/cdk'; import {AppointmentService} from '../../services/appointment.service'; import {DetailsComponent} from '../../components/details/details.component'; import {DateFormatter} from '../../utils/date-formatter'; import {WeekDay} from '../../models/week-day'; import {NewItemComponent} from '../../components/new-item/new-item.component'; import {timeAfterStartValidator} from '../../models/validators/time-after-start-validator'; import {DropdownContentComponent} from '../../components/dropdown-content/dropdown-content.component'; @Component({ selector: 'app-agenda', imports: [NgFor, TuiButton, CommonModule, NgIf, ModalComponent, ReactiveFormsModule, TuiInputTimeModule, TuiTextfieldControllerModule, TuiInputModule, TuiTextareaModule, TuiInputDateModule, TuiIcon, DetailsComponent, TuiCalendar, NewItemComponent, DropdownContentComponent], templateUrl: './agenda.component.html', providers: [tuiDateFormatProvider({separator: '-'}), AppointmentService], styleUrl: './agenda.component.scss' }) export class AgendaComponent implements OnInit { constructor(private appointmentService: AppointmentService) { } ngOnInit(): void { this.getAppointmentsByDate(this.selectedDate); } timeSlots: number[] = Array.from({length: 24}, (_, i) => i); // 24 uren appointments: Appointment[] = []; showNewItem = false today = new Date() selectedDate = new Date() waiting: boolean = false; selectedAppointment: Appointment; protected value: TuiDay | null = null; showCalendar: boolean = false; open = false private readonly alerts = inject(TuiAlertService); protected appointmentForm = new FormGroup({ title: new FormControl('', Validators.required), notes: new FormControl(''), startTime: new FormControl(new TuiTime(this.today.getHours(), this.today.getMinutes()), Validators.required), endTime: new FormControl(new TuiTime(this.getHours(), this.getMinutes()), [Validators.required, timeAfterStartValidator('startTime')]), date: new FormControl(new TuiDay(this.selectedDate.getFullYear(), this.selectedDate.getMonth(), this.selectedDate.getDate()), Validators.required), }); registerAppointment(title: string): void { this.getAppointmentsByDate(this.selectedDate); this.waiting = false this.showNewItem = false this.showNotification(title) this.resetForms() } protected showNotification(message: string): void { this.alerts .open(`Afspraak ${message} is aangemaakt.`) .subscribe(); } getAppointmentsForHour(hour: number) { return this.appointments.filter(appointment => appointment.startHour === hour); } getDate(): string { const date = this.selectedDate const weekDay = WeekDay[date.getDay()]; const day = date.getDate().toString().padStart(2, '0'); // Dag met leading zero (01, 02, ..., 31) const monthName = date.toLocaleString('nl-NL', {month: 'long'}); const year = date.getFullYear().toString(); // Volledig jaar return `${weekDay} ${day} ${monthName} ${year}`; } resetForms() { this.appointmentForm = new FormGroup({ title: new FormControl('', Validators.required), notes: new FormControl(''), startTime: new FormControl(new TuiTime(this.today.getHours(), this.today.getMinutes()), Validators.required), endTime: new FormControl(new TuiTime(this.getEndTime().getHours(), this.getEndTime().getMinutes()), [Validators.required, timeAfterStartValidator('startTime')]), date: new FormControl(new TuiDay(this.selectedDate.getFullYear(), this.selectedDate.getMonth(), this.selectedDate.getDate()), Validators.required), }); } nextDay() { this.selectedDate.setDate(this.selectedDate.getDate() + 1); this.getAppointmentsByDate(this.selectedDate); this.appointmentForm.get('date').setValue(new TuiDay(this.selectedDate.getFullYear(), this.selectedDate.getMonth(), this.selectedDate.getDate())) } previousDay() { this.selectedDate.setDate(this.selectedDate.getDate() - 1); this.getAppointmentsByDate(this.selectedDate); this.appointmentForm.get('date').setValue(new TuiDay(this.selectedDate.getFullYear(), this.selectedDate.getMonth(), this.selectedDate.getDate())) } getHours() { let hours = this.today.getHours() if (hours > 23) { return 23 } return hours } getMinutes() { let minutes = this.today.getMinutes() + 30 if (minutes > 59) { return 59 } return minutes } getEndTime(): Date { const endTime = new Date(this.today); // Kopieer startTime endTime.setMinutes(endTime.getMinutes() + 30); // 30 minuten toevoegen // Controleer of de dag nog steeds hetzelfde is if (endTime.getDate() !== this.today.getDate()) { endTime.setHours(23, 59, 59, 999); // Zet naar 23:59:59 als het overloopt } return endTime; } setToday() { this.selectedDate = new Date() this.getAppointmentsByDate(this.selectedDate); this.appointmentForm.get('date').setValue(new TuiDay(this.selectedDate.getFullYear(), this.selectedDate.getMonth(), this.selectedDate.getDate())) } getAppointmentsByDate(date: Date) { this.appointmentService.getAppointmentsByDate(date).subscribe(appointments => { this.appointments = appointments; }) } getInlineStyles(appointment: Appointment): { [key: string]: string } { return { '--duration': `${appointment.durationInMinutes}`, '--start-minute': `${appointment.startMinute}`, 'top': `${appointment.startMinute}px`, // Startpositie binnen het uur 'height': `${appointment.durationInMinutes}px`, // Hoogte over meerdere uren }; } getFormattedTime(hour: number, minute: number): string { return `${hour.toString().padStart(2, '0')}:${minute.toString().padStart(2, '0')}`; } getAppointmentHeight(appointment: Appointment): number { const startInMinutes = (appointment.startHour * 60) + appointment.startMinute; const endInMinutes = (appointment.endHour * 60) + appointment.endMinute; return (endInMinutes - startInMinutes); // 50px per uur } selectAppointment(appointment: Appointment) { this.selectedAppointment = appointment; } protected readonly DateFormatter = DateFormatter; onDayClick(day: TuiDay) { this.value = day; this.selectedDate = new Date(day.year, day.month, day.day); this.getAppointmentsByDate(this.selectedDate); this.appointmentForm.get('date').setValue(new TuiDay(this.selectedDate.getFullYear(), this.selectedDate.getMonth(), this.selectedDate.getDate())) this.toggleCalendar() } toggleCalendar() { this.showCalendar = !this.showCalendar } closeNewItemModal() { this.showNewItem = false this.resetForms() } appointmentIsDeleted(appointment: Appointment) { this.selectedAppointment = undefined; this.alerts .open(`Afspraak ${appointment.title} is verwijderd.`) .subscribe(); this.getAppointmentsByDate(this.selectedDate); } appointmentIsEdited($event: Appointment) { this.getAppointmentsByDate(this.selectedDate); } protected firstMonth = TuiMonth.currentLocal().append({month: -1}); protected middleMonth = TuiMonth.currentLocal(); protected lastMonth = TuiMonth.currentLocal().append({month: 2}); protected hoveredItem: TuiDay | null = null; protected onMonthChangeFirst(month: TuiMonth): void { this.firstMonth = month.append({month: -1}); this.middleMonth = month this.lastMonth = month.append({month: 2}); } protected onMonthChangeMiddle(month: TuiMonth): void { this.firstMonth = month.append({month: -1}); this.middleMonth = month; this.lastMonth = month.append({month: 1}); } protected onMonthChangeLast(month: TuiMonth): void { this.firstMonth = month.append({month: -2}); this.middleMonth = month.append({month: -1}); this.lastMonth = month; } openSettings() { this.open = !this.open } }