Migrate to luxon. Fixes wrong weekday to date bug as well.

This commit is contained in:
2025-06-23 10:33:37 +02:00
parent 7ddca43a01
commit 9b793d47d8
2 changed files with 44 additions and 56 deletions

View File

@ -1,6 +1,6 @@
{
"name": "@tp/tp-date-picker",
"version": "2.3.0",
"version": "3.0.0",
"description": "",
"main": "tp-date-picker.js",
"scripts": {
@ -13,8 +13,7 @@
"author": "trading_peter",
"license": "Apache-2.0",
"dependencies": {
"@date-fns/utc": "^2.1.0",
"date-fns": "^4.0.0",
"luxon": "^3.6.1",
"lit": "^2.2.0"
}
}

View File

@ -7,7 +7,7 @@ This program is available under Apache License Version 2.0
import '@tp/tp-icon/tp-icon.js';
import { FormElement } from '@tp/helpers/form-element';
import { LitElement, html, css, svg } from 'lit';
import { UTCDate } from '@date-fns/utc';
import { DateTime } from 'luxon';
class TpDatePicker extends FormElement(LitElement) {
static get styles() {
@ -142,14 +142,17 @@ class TpDatePicker extends FormElement(LitElement) {
render() {
let { month, year, dayNames, value, yearsForward, yearsBackwards } = this;
const today = new UTCDate();
const today = DateTime.utc();
if ((!month && month !== 0) || (!year && year !== 0)) {
month = today.getMonth();
year = today.getFullYear();
month = today.month - 1; // Luxon uses 1-based months, convert to 0-based for compatibility
year = today.year;
}
const years = Array(yearsForward + yearsBackwards).fill().map((_, i) => today.getFullYear()-yearsBackwards+i).reverse();
const years = Array(yearsForward + yearsBackwards)
.fill()
.map((_, i) => today.year - yearsBackwards + i)
.reverse();
const curMonth = this.getMonthDates(month, year);
return html`
@ -183,9 +186,9 @@ class TpDatePicker extends FormElement(LitElement) {
const eventCount = this.countEventsForDate(d);
return html`
<div .date=${d} part="date ${d.getMonth() !== month ? 'filler' : 'of-month'}">
<div class="number" part="number ${matchesValue ? 'selected' : ''} ${isToday ? 'today' : ''} ${d.getMonth() === month ? 'of-month' : ''}">
${d.getDate()}
<div .date=${d} part="date ${d.month - 1 !== month ? 'filler' : 'of-month'}">
<div class="number" part="number ${matchesValue ? 'selected' : ''} ${isToday ? 'today' : ''} ${d.month - 1 === month ? 'of-month' : ''}">
${d.day}
${eventCount > 0 ? html`
<div class="event-dots">
<div class="event-dot" part="event-dot"></div>
@ -207,8 +210,8 @@ class TpDatePicker extends FormElement(LitElement) {
static get properties() {
return {
value: { type: Date },
today: { type: Date },
value: { type: Object }, // Changed from Date to Luxon DateTime
today: { type: Object }, // Changed from Date to Luxon DateTime
month: { type: Number },
year: { type: Number },
monthNames: { type: Array },
@ -235,9 +238,9 @@ class TpDatePicker extends FormElement(LitElement) {
constructor() {
super();
this.today = new UTCDate();
this.month = this.today.getMonth();
this.year = this.today.getFullYear();
this.today = DateTime.utc();
this.month = this.today.month - 1; // Convert 1-based to 0-based month
this.year = this.today.year;
this.yearsForward = 10;
this.yearsBackwards = 100;
this.events = [];
@ -269,17 +272,17 @@ class TpDatePicker extends FormElement(LitElement) {
}
shouldUpdate(changes) {
if (changes.has('value')) {
this.month = this.value.getMonth();
this.year = this.value.getFullYear();
if (changes.has('value') && this.value) {
this.month = this.value.month - 1; // Convert 1-based to 0-based month
this.year = this.value.year;
}
return true;
}
equalDate(d, value) {
if (!value) return false;
return d.getDate() === value.getDate() && d.getFullYear() === value.getFullYear() && d.getMonth() === value.getMonth();
equalDate(d1, d2) {
if (!d1 || !d2) return false;
return d1.day === d2.day && d1.year === d2.year && d1.month === d2.month;
}
selectDate(e) {
@ -331,50 +334,36 @@ class TpDatePicker extends FormElement(LitElement) {
}
getMonthDates(month = null, year = null) {
month = month !== null ? month : new UTCDate().getMonth();
year = year || new UTCDate().getFullYear();
month = month !== null ? month : DateTime.utc().month - 1; // Convert 1-based to 0-based
year = year || DateTime.utc().year;
const firstOfMonth = new UTCDate();
firstOfMonth.setFullYear(year);
firstOfMonth.setMonth(month);
firstOfMonth.setDate(1);
firstOfMonth.setHours(0);
firstOfMonth.setMinutes(0);
firstOfMonth.setSeconds(0);
const lastOfMonth = new UTCDate();
lastOfMonth.setDate(1);
lastOfMonth.setFullYear(year);
lastOfMonth.setMonth(month + 1);
lastOfMonth.setDate(lastOfMonth.getDate() - 1);
lastOfMonth.setHours(0);
lastOfMonth.setMinutes(0);
lastOfMonth.setSeconds(0);
// Create DateTime for the first of the month (convert 0-based month back to 1-based)
const firstOfMonth = DateTime.utc(year, month + 1, 1, 0, 0, 0);
// Create DateTime for the last of the month
const lastOfMonth = firstOfMonth.endOf('month').startOf('day');
const dates = [];
while (firstOfMonth.getDay() > 1) {
firstOfMonth.setDate(firstOfMonth.getDate() - 1);
dates.push(new UTCDate(firstOfMonth));
// Calculate dates before the first of month to fill the calendar
let firstDayOfCalendar = firstOfMonth;
while (firstDayOfCalendar.weekday > 1) { // 1 is Monday in Luxon
firstDayOfCalendar = firstDayOfCalendar.minus({ days: 1 });
dates.push(firstDayOfCalendar);
}
dates.reverse();
for (let i = 1; i <= lastOfMonth.getDate(); ++i) {
const d = new UTCDate();
d.setFullYear(year);
d.setMonth(month);
d.setDate(i);
d.setHours(0);
d.setMinutes(0);
d.setSeconds(0);
dates.push(d);
// Add all days of the current month
for (let i = 1; i <= lastOfMonth.day; i++) {
dates.push(DateTime.utc(year, month + 1, i, 0, 0, 0));
}
// Make sure we always fill 42 date get guarantee equal size of the date picker.
// Make sure we always fill 42 dates to guarantee equal size of the date picker
let nextDate = lastOfMonth;
while (dates.length < 42) {
lastOfMonth.setDate(lastOfMonth.getDate() + 1);
dates.push(new UTCDate(lastOfMonth));
nextDate = nextDate.plus({ days: 1 });
dates.push(nextDate);
}
return dates;