kalendly 0.2.2 → 0.3.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +202 -29
- package/dist/core/index.d.mts +48 -10
- package/dist/core/index.d.ts +48 -10
- package/dist/core/index.js +60 -26
- package/dist/core/index.js.map +1 -1
- package/dist/core/index.mjs +56 -25
- package/dist/core/index.mjs.map +1 -1
- package/dist/index.d.mts +74 -10
- package/dist/index.d.ts +74 -10
- package/dist/index.js +373 -162
- package/dist/index.js.map +1 -1
- package/dist/index.mjs +369 -161
- package/dist/index.mjs.map +1 -1
- package/dist/index.umd.js +363 -158
- package/dist/index.umd.js.map +1 -1
- package/dist/styles/calendar.css +445 -395
- package/package.json +1 -1
package/dist/index.js
CHANGED
|
@@ -107,26 +107,16 @@ function generateCalendarDates(year, month, events = [], weekStartsOn = 0) {
|
|
|
107
107
|
}
|
|
108
108
|
return dates;
|
|
109
109
|
}
|
|
110
|
-
function getPopupPositionClass(selectedDayIndex) {
|
|
111
|
-
if (selectedDayIndex === null) return "popup-center-bottom";
|
|
112
|
-
if (selectedDayIndex < 3) {
|
|
113
|
-
return "popup-right";
|
|
114
|
-
} else if (selectedDayIndex > 4) {
|
|
115
|
-
return "popup-left";
|
|
116
|
-
} else {
|
|
117
|
-
return "popup-center-bottom";
|
|
118
|
-
}
|
|
119
|
-
}
|
|
120
110
|
function getCellClasses(calendarDate) {
|
|
121
111
|
const classes = [];
|
|
122
112
|
if (!calendarDate.isCurrentMonth) {
|
|
123
|
-
classes.push("other-month");
|
|
113
|
+
classes.push("calendar-cell-other-month");
|
|
124
114
|
}
|
|
125
115
|
if (calendarDate.isToday) {
|
|
126
|
-
classes.push("
|
|
116
|
+
classes.push("calendar-cell-today");
|
|
127
117
|
}
|
|
128
118
|
if (calendarDate.hasEvents) {
|
|
129
|
-
classes.push("has
|
|
119
|
+
classes.push("calendar-cell-has-event");
|
|
130
120
|
}
|
|
131
121
|
return classes;
|
|
132
122
|
}
|
|
@@ -185,7 +175,24 @@ function getCategoryColor(category, customColors) {
|
|
|
185
175
|
const color = colorMap[category] || colorMap.other || "#fc8917";
|
|
186
176
|
return isValidHexColor(color) ? color : "#fc8917";
|
|
187
177
|
}
|
|
188
|
-
|
|
178
|
+
function escapeHtml(value) {
|
|
179
|
+
if (value === null || value === void 0) return "";
|
|
180
|
+
return String(value).replace(/[&<>"']/g, (char) => HTML_ESCAPES[char]);
|
|
181
|
+
}
|
|
182
|
+
function slugifyToken(value) {
|
|
183
|
+
return String(value).toLowerCase().replace(/[^a-z0-9]+/g, "-").replace(/^-+|-+$/g, "");
|
|
184
|
+
}
|
|
185
|
+
function safeUrl(value) {
|
|
186
|
+
const normalized = String(value).split("").filter((char) => char.charCodeAt(0) > 32).join("");
|
|
187
|
+
if (/^(?:https?:|mailto:)/i.test(normalized)) return normalized;
|
|
188
|
+
const schemeless = !/^[^/?#]*:/.test(normalized);
|
|
189
|
+
return schemeless ? normalized : "#";
|
|
190
|
+
}
|
|
191
|
+
function safeColor(value) {
|
|
192
|
+
const trimmed = String(value).trim();
|
|
193
|
+
return isValidHexColor(trimmed) || /^[a-z]+$/i.test(trimmed) ? trimmed : "#3b82f6";
|
|
194
|
+
}
|
|
195
|
+
var MONTHS, MONTHS_FULL, DAYS, DEFAULT_CATEGORY_COLORS, HTML_ESCAPES;
|
|
189
196
|
var init_utils = __esm({
|
|
190
197
|
"src/core/utils.ts"() {
|
|
191
198
|
"use strict";
|
|
@@ -234,6 +241,13 @@ var init_utils = __esm({
|
|
|
234
241
|
appointment: "#f59e0b",
|
|
235
242
|
other: "#6b7280"
|
|
236
243
|
};
|
|
244
|
+
HTML_ESCAPES = {
|
|
245
|
+
"&": "&",
|
|
246
|
+
"<": "<",
|
|
247
|
+
">": ">",
|
|
248
|
+
'"': """,
|
|
249
|
+
"'": "'"
|
|
250
|
+
};
|
|
237
251
|
}
|
|
238
252
|
});
|
|
239
253
|
|
|
@@ -281,24 +295,38 @@ var init_calendar_engine = __esm({
|
|
|
281
295
|
* Get view model with computed properties
|
|
282
296
|
*/
|
|
283
297
|
getViewModel() {
|
|
284
|
-
const
|
|
285
|
-
this.
|
|
286
|
-
|
|
287
|
-
|
|
288
|
-
|
|
298
|
+
const panes = Array.from(
|
|
299
|
+
{ length: Math.max(1, this.config.monthCount ?? 1) },
|
|
300
|
+
(_, offset) => {
|
|
301
|
+
const anchor = new Date(
|
|
302
|
+
this.state.currentYear,
|
|
303
|
+
this.state.currentMonth + offset,
|
|
304
|
+
1
|
|
305
|
+
);
|
|
306
|
+
const year = anchor.getFullYear();
|
|
307
|
+
const month = anchor.getMonth();
|
|
308
|
+
return {
|
|
309
|
+
year,
|
|
310
|
+
month,
|
|
311
|
+
monthAndYearText: getMonthYearText(year, month),
|
|
312
|
+
calendarDates: generateCalendarDates(
|
|
313
|
+
year,
|
|
314
|
+
month,
|
|
315
|
+
this.config.events,
|
|
316
|
+
this.config.weekStartsOn
|
|
317
|
+
)
|
|
318
|
+
};
|
|
319
|
+
}
|
|
289
320
|
);
|
|
290
321
|
return {
|
|
291
322
|
...this.state,
|
|
292
323
|
months: MONTHS,
|
|
293
324
|
days: DAYS,
|
|
294
325
|
years: generateYears(this.config.minYear, this.config.maxYear),
|
|
295
|
-
monthAndYearText:
|
|
296
|
-
this.state.currentYear,
|
|
297
|
-
this.state.currentMonth
|
|
298
|
-
),
|
|
326
|
+
monthAndYearText: panes[0].monthAndYearText,
|
|
299
327
|
scheduleDay: this.state.selectedDate ? formatDateForDisplay(this.state.selectedDate) : "",
|
|
300
|
-
|
|
301
|
-
|
|
328
|
+
panes,
|
|
329
|
+
calendarDates: panes[0].calendarDates
|
|
302
330
|
};
|
|
303
331
|
}
|
|
304
332
|
/**
|
|
@@ -494,13 +522,13 @@ function defineCalendarElement(tagName = "kal-calendar") {
|
|
|
494
522
|
customElements.define(tagName, CalendarElement);
|
|
495
523
|
}
|
|
496
524
|
}
|
|
497
|
-
var isSameDay2, CalendarElement;
|
|
525
|
+
var isSameDay2, _CalendarElement, CalendarElement;
|
|
498
526
|
var init_CalendarElement = __esm({
|
|
499
527
|
"src/web-components/CalendarElement.ts"() {
|
|
500
528
|
"use strict";
|
|
501
529
|
init_core();
|
|
502
530
|
isSameDay2 = (a, b) => a.getFullYear() === b.getFullYear() && a.getMonth() === b.getMonth() && a.getDate() === b.getDate();
|
|
503
|
-
|
|
531
|
+
_CalendarElement = class _CalendarElement extends HTMLElement {
|
|
504
532
|
constructor() {
|
|
505
533
|
super(...arguments);
|
|
506
534
|
this.engine = null;
|
|
@@ -521,6 +549,10 @@ var init_CalendarElement = __esm({
|
|
|
521
549
|
this._categoryColors = null;
|
|
522
550
|
this._renderEvent = null;
|
|
523
551
|
this._renderNoEvents = null;
|
|
552
|
+
this._availabilityColors = null;
|
|
553
|
+
this._selectableStatuses = null;
|
|
554
|
+
this._initError = null;
|
|
555
|
+
this.pendingUpdate = null;
|
|
524
556
|
// Selection state (availability mode — range)
|
|
525
557
|
this._rangeStart = null;
|
|
526
558
|
this._rangeEnd = null;
|
|
@@ -533,6 +565,7 @@ var init_CalendarElement = __esm({
|
|
|
533
565
|
return this._events;
|
|
534
566
|
}
|
|
535
567
|
set events(val) {
|
|
568
|
+
this._initError = null;
|
|
536
569
|
this._events = val;
|
|
537
570
|
if (this.engine) {
|
|
538
571
|
this.engine.updateEvents(val);
|
|
@@ -548,13 +581,28 @@ var init_CalendarElement = __esm({
|
|
|
548
581
|
this.engine.updateCategoryColors(val);
|
|
549
582
|
}
|
|
550
583
|
}
|
|
584
|
+
get availabilityColors() {
|
|
585
|
+
return this._availabilityColors ?? {};
|
|
586
|
+
}
|
|
587
|
+
set availabilityColors(val) {
|
|
588
|
+
this._initError = null;
|
|
589
|
+
this._availabilityColors = val;
|
|
590
|
+
if (this.engine) this.scheduleRender();
|
|
591
|
+
}
|
|
592
|
+
get selectableStatuses() {
|
|
593
|
+
return this._selectableStatuses ?? [];
|
|
594
|
+
}
|
|
595
|
+
set selectableStatuses(val) {
|
|
596
|
+
this._selectableStatuses = val;
|
|
597
|
+
if (this.engine) this.scheduleRender();
|
|
598
|
+
}
|
|
551
599
|
set renderEvent(val) {
|
|
552
600
|
this._renderEvent = val;
|
|
553
|
-
if (this.engine) this.
|
|
601
|
+
if (this.engine) this.scheduleRender();
|
|
554
602
|
}
|
|
555
603
|
set renderNoEvents(val) {
|
|
556
604
|
this._renderNoEvents = val;
|
|
557
|
-
if (this.engine) this.
|
|
605
|
+
if (this.engine) this.scheduleRender();
|
|
558
606
|
}
|
|
559
607
|
get loading() {
|
|
560
608
|
return this.hasAttribute("loading");
|
|
@@ -563,10 +611,22 @@ var init_CalendarElement = __esm({
|
|
|
563
611
|
if (val) this.setAttribute("loading", "");
|
|
564
612
|
else this.removeAttribute("loading");
|
|
565
613
|
}
|
|
614
|
+
// Custom element reactions report rather than propagate, so a failure here
|
|
615
|
+
// is kept and resurfaced at the next call the integrator makes
|
|
616
|
+
reaction(run) {
|
|
617
|
+
try {
|
|
618
|
+
run();
|
|
619
|
+
} catch (error) {
|
|
620
|
+
this._initError = error;
|
|
621
|
+
throw error;
|
|
622
|
+
}
|
|
623
|
+
}
|
|
566
624
|
connectedCallback() {
|
|
567
625
|
this.classList.add("kalendly-calendar");
|
|
568
|
-
this.
|
|
569
|
-
|
|
626
|
+
this.reaction(() => {
|
|
627
|
+
this.initEngine();
|
|
628
|
+
this.render();
|
|
629
|
+
});
|
|
570
630
|
}
|
|
571
631
|
disconnectedCallback() {
|
|
572
632
|
this.cleanup();
|
|
@@ -576,7 +636,7 @@ var init_CalendarElement = __esm({
|
|
|
576
636
|
attributeChangedCallback(name, oldVal, newVal) {
|
|
577
637
|
if (oldVal === newVal) return;
|
|
578
638
|
if (name === "loading") {
|
|
579
|
-
this.
|
|
639
|
+
this.scheduleRender();
|
|
580
640
|
return;
|
|
581
641
|
}
|
|
582
642
|
if (name === "selectable" && newVal === null) {
|
|
@@ -589,6 +649,23 @@ var init_CalendarElement = __esm({
|
|
|
589
649
|
}
|
|
590
650
|
this.reinit();
|
|
591
651
|
}
|
|
652
|
+
get headingText() {
|
|
653
|
+
const heading = this.getAttribute("heading");
|
|
654
|
+
if (heading !== null) return heading;
|
|
655
|
+
const title = this.getAttribute("title");
|
|
656
|
+
if (title !== null && !_CalendarElement.titleDeprecationWarned) {
|
|
657
|
+
_CalendarElement.titleDeprecationWarned = true;
|
|
658
|
+
console.warn(
|
|
659
|
+
`<kal-calendar> the title attribute is deprecated and will be removed in a future release \u2014 use heading instead. title is a global HTML attribute, so the browser also renders it as a tooltip over the whole calendar.`
|
|
660
|
+
);
|
|
661
|
+
}
|
|
662
|
+
return title;
|
|
663
|
+
}
|
|
664
|
+
get monthCount() {
|
|
665
|
+
const requested = Number(this.getAttribute("months") ?? 1);
|
|
666
|
+
if (!Number.isInteger(requested) || requested < 1) return 1;
|
|
667
|
+
return Math.min(requested, 2);
|
|
668
|
+
}
|
|
592
669
|
get minYear() {
|
|
593
670
|
const val = this.getAttribute("min-year");
|
|
594
671
|
return val ? parseInt(val, 10) : (/* @__PURE__ */ new Date()).getFullYear() - 30;
|
|
@@ -608,19 +685,20 @@ var init_CalendarElement = __esm({
|
|
|
608
685
|
minYear: this.minYear,
|
|
609
686
|
maxYear: this.maxYear,
|
|
610
687
|
weekStartsOn,
|
|
611
|
-
categoryColors: this._categoryColors ?? void 0
|
|
688
|
+
categoryColors: this._categoryColors ?? void 0,
|
|
689
|
+
monthCount: this.monthCount
|
|
612
690
|
});
|
|
613
691
|
this.actions = this.engine.getActions();
|
|
614
692
|
this.applyTheme();
|
|
615
693
|
this.unsubscribe = this.engine.subscribe(() => {
|
|
616
|
-
this.
|
|
694
|
+
this.scheduleRender();
|
|
617
695
|
});
|
|
618
696
|
}
|
|
619
697
|
reinit() {
|
|
620
698
|
if (!this.engine) return;
|
|
621
699
|
this.cleanup();
|
|
622
700
|
this.initEngine();
|
|
623
|
-
this.
|
|
701
|
+
this.scheduleRender();
|
|
624
702
|
}
|
|
625
703
|
cleanup() {
|
|
626
704
|
if (this.unsubscribe) {
|
|
@@ -657,42 +735,84 @@ var init_CalendarElement = __esm({
|
|
|
657
735
|
applyTheme() {
|
|
658
736
|
if (!this._theme) return;
|
|
659
737
|
const root = document.documentElement;
|
|
660
|
-
const
|
|
661
|
-
|
|
662
|
-
root.style.setProperty(
|
|
663
|
-
|
|
664
|
-
|
|
665
|
-
|
|
666
|
-
|
|
667
|
-
|
|
668
|
-
|
|
669
|
-
|
|
670
|
-
|
|
671
|
-
|
|
672
|
-
|
|
673
|
-
|
|
674
|
-
|
|
675
|
-
if (
|
|
676
|
-
|
|
677
|
-
|
|
678
|
-
|
|
679
|
-
|
|
680
|
-
|
|
681
|
-
|
|
682
|
-
|
|
683
|
-
|
|
684
|
-
|
|
738
|
+
for (const key of Object.keys(_CalendarElement.themeMap)) {
|
|
739
|
+
const value = this._theme[key];
|
|
740
|
+
if (value) root.style.setProperty(_CalendarElement.themeMap[key], value);
|
|
741
|
+
}
|
|
742
|
+
}
|
|
743
|
+
get knownBuckets() {
|
|
744
|
+
return [
|
|
745
|
+
..._CalendarElement.BUILT_IN_BUCKETS,
|
|
746
|
+
...Object.keys(this._availabilityColors ?? {})
|
|
747
|
+
];
|
|
748
|
+
}
|
|
749
|
+
get updateComplete() {
|
|
750
|
+
return this.pendingUpdate ?? Promise.resolve();
|
|
751
|
+
}
|
|
752
|
+
scheduleRender() {
|
|
753
|
+
if (this.pendingUpdate) return;
|
|
754
|
+
this.pendingUpdate = Promise.resolve().then(() => {
|
|
755
|
+
this.pendingUpdate = null;
|
|
756
|
+
try {
|
|
757
|
+
this.render();
|
|
758
|
+
} catch (error) {
|
|
759
|
+
this._initError = error;
|
|
760
|
+
throw error;
|
|
761
|
+
}
|
|
762
|
+
});
|
|
763
|
+
}
|
|
764
|
+
rethrowInitError() {
|
|
765
|
+
if (this._initError) throw this._initError;
|
|
766
|
+
}
|
|
767
|
+
assertStatusesDeclared() {
|
|
768
|
+
if (!this.getAttribute("availability-mode")) return;
|
|
769
|
+
const missing = this._events.filter(
|
|
770
|
+
(event) => typeof event.availabilityStatus !== "string" || event.availabilityStatus === ""
|
|
771
|
+
).map((event) => String(event.id));
|
|
772
|
+
if (missing.length) {
|
|
773
|
+
throw new Error(
|
|
774
|
+
`<kal-calendar> availability-mode requires availabilityStatus on every event. Missing on: ${missing.join(", ")}.`
|
|
775
|
+
);
|
|
776
|
+
}
|
|
777
|
+
}
|
|
778
|
+
assertStatusesKnown() {
|
|
779
|
+
const known = new Set(this.knownBuckets);
|
|
780
|
+
const unknown = this._events.filter((event) => !known.has(event.availabilityStatus)).map((event) => `${event.id} (${event.availabilityStatus})`);
|
|
781
|
+
if (unknown.length) {
|
|
782
|
+
throw new Error(
|
|
783
|
+
`<kal-calendar> availabilityStatus must name a built-in bucket (${_CalendarElement.BUILT_IN_BUCKETS.join(", ")}) or a key of availabilityColors. Unrecognised on: ${unknown.join(", ")}.`
|
|
784
|
+
);
|
|
785
|
+
}
|
|
786
|
+
}
|
|
787
|
+
resolveBucket(date) {
|
|
788
|
+
if (!this.engine) return "open";
|
|
789
|
+
const declared = new Set(
|
|
790
|
+
this.engine.getEventsForDate(date).map((event) => event.availabilityStatus)
|
|
791
|
+
);
|
|
792
|
+
if (declared.size === 0) return "open";
|
|
793
|
+
return this.knownBuckets.find((bucket) => declared.has(bucket));
|
|
794
|
+
}
|
|
795
|
+
isDateSelectable(date) {
|
|
796
|
+
if (!this.engine) return false;
|
|
797
|
+
if (this._selectableStatuses) {
|
|
798
|
+
return this._selectableStatuses.includes(this.resolveBucket(date));
|
|
799
|
+
}
|
|
800
|
+
return this.engine.getEventsForDate(date).length === 0;
|
|
685
801
|
}
|
|
686
802
|
render() {
|
|
687
803
|
if (!this.engine) return;
|
|
688
804
|
const viewModel = this.engine.getViewModel();
|
|
689
805
|
const useShortMonths = this.hasAttribute("use-short-month-names");
|
|
690
|
-
const title = this.
|
|
806
|
+
const title = this.headingText;
|
|
691
807
|
const minYear = this.minYear;
|
|
692
808
|
const maxYear = this.maxYear;
|
|
693
809
|
const availabilityMode = this.getAttribute("availability-mode");
|
|
694
810
|
const selectable = this.hasAttribute("selectable");
|
|
695
811
|
const isLoading = this.loading;
|
|
812
|
+
if (availabilityMode) {
|
|
813
|
+
this.assertStatusesDeclared();
|
|
814
|
+
this.assertStatusesKnown();
|
|
815
|
+
}
|
|
696
816
|
const today = /* @__PURE__ */ new Date();
|
|
697
817
|
const todayMonth = today.getMonth();
|
|
698
818
|
const todayYear = today.getFullYear();
|
|
@@ -701,7 +821,7 @@ var init_CalendarElement = __esm({
|
|
|
701
821
|
const defaultRenderEvent = (event) => {
|
|
702
822
|
const timeRange = formatTimeRange(event);
|
|
703
823
|
const attendeesList = formatAttendees(event.attendees);
|
|
704
|
-
let borderColor = event.color || "#3b82f6";
|
|
824
|
+
let borderColor = safeColor(event.color || "#3b82f6");
|
|
705
825
|
if (event.category) {
|
|
706
826
|
borderColor = this.engine.getCategoryColor(event.category);
|
|
707
827
|
}
|
|
@@ -736,56 +856,56 @@ var init_CalendarElement = __esm({
|
|
|
736
856
|
return `
|
|
737
857
|
<div class="event-card" style="border-left-color: ${borderColor}">
|
|
738
858
|
<div class="event-header">
|
|
739
|
-
<div class="event-title">${event.name}</div>
|
|
859
|
+
<div class="event-title">${escapeHtml(event.name)}</div>
|
|
740
860
|
<div class="event-badges">
|
|
741
|
-
${event.category ? `<span class="badge category-${event.category}">${getCategoryLabel(event.category)}</span>` : ""}
|
|
742
|
-
${event.priority ? `<span class="badge priority-${event.priority}">${getPriorityLabel(event.priority)}</span>` : ""}
|
|
743
|
-
${event.status && event.status !== "scheduled" ? `<span class="badge status-${event.status}">${getStatusLabel(event.status)}</span>` : ""}
|
|
861
|
+
${event.category ? `<span class="badge category category-${slugifyToken(event.category)}">${escapeHtml(getCategoryLabel(event.category))}</span>` : ""}
|
|
862
|
+
${event.priority ? `<span class="badge priority priority-${slugifyToken(event.priority)}">${escapeHtml(getPriorityLabel(event.priority))}</span>` : ""}
|
|
863
|
+
${event.status && event.status !== "scheduled" ? `<span class="badge status status-${slugifyToken(event.status)}">${escapeHtml(getStatusLabel(event.status))}</span>` : ""}
|
|
744
864
|
</div>
|
|
745
865
|
</div>
|
|
746
866
|
|
|
747
867
|
${timeRange ? `
|
|
748
868
|
<div class="event-time">
|
|
749
869
|
<span class="event-time-label">Time:</span>
|
|
750
|
-
<span class="event-time-value">${timeRange}</span>
|
|
870
|
+
<span class="event-time-value">${escapeHtml(timeRange)}</span>
|
|
751
871
|
</div>
|
|
752
872
|
` : ""}
|
|
753
873
|
|
|
754
874
|
${event.description ? `
|
|
755
|
-
<div class="event-description">${event.description}</div>
|
|
875
|
+
<div class="event-description">${escapeHtml(event.description)}</div>
|
|
756
876
|
` : ""}
|
|
757
877
|
|
|
758
878
|
${event.location ? `
|
|
759
879
|
<div class="event-time">
|
|
760
880
|
<span class="event-time-label">Location:</span>
|
|
761
|
-
<span class="event-time-value">${event.location}</span>
|
|
881
|
+
<span class="event-time-value">${escapeHtml(event.location)}</span>
|
|
762
882
|
</div>
|
|
763
883
|
` : ""}
|
|
764
884
|
|
|
765
885
|
${attendeesList ? `
|
|
766
886
|
<div class="event-time">
|
|
767
887
|
<span class="event-time-label">Attendees:</span>
|
|
768
|
-
<span class="event-time-value">${attendeesList}</span>
|
|
888
|
+
<span class="event-time-value">${escapeHtml(attendeesList)}</span>
|
|
769
889
|
</div>
|
|
770
890
|
` : ""}
|
|
771
891
|
|
|
772
892
|
${event.organizer ? `
|
|
773
893
|
<div class="event-time">
|
|
774
894
|
<span class="event-time-label">Organizer:</span>
|
|
775
|
-
<span class="event-time-value">${event.organizer}</span>
|
|
895
|
+
<span class="event-time-value">${escapeHtml(event.organizer)}</span>
|
|
776
896
|
</div>
|
|
777
897
|
` : ""}
|
|
778
898
|
|
|
779
899
|
${event.notes ? `
|
|
780
900
|
<div class="event-time">
|
|
781
901
|
<span class="event-time-label">Notes:</span>
|
|
782
|
-
<span class="event-time-value">${event.notes}</span>
|
|
902
|
+
<span class="event-time-value">${escapeHtml(event.notes)}</span>
|
|
783
903
|
</div>
|
|
784
904
|
` : ""}
|
|
785
905
|
|
|
786
906
|
${event.url ? `
|
|
787
907
|
<div class="event-time">
|
|
788
|
-
<a href="${event.url}" target="_blank" rel="noopener noreferrer" class="event-link">
|
|
908
|
+
<a href="${escapeHtml(safeUrl(event.url))}" target="_blank" rel="noopener noreferrer" class="event-link">
|
|
789
909
|
View Details \u2192
|
|
790
910
|
</a>
|
|
791
911
|
</div>
|
|
@@ -793,7 +913,7 @@ var init_CalendarElement = __esm({
|
|
|
793
913
|
|
|
794
914
|
${event.tags && event.tags.length > 0 ? `
|
|
795
915
|
<div class="event-tags">
|
|
796
|
-
${event.tags.map((tag) => `<span class="event-tag">${tag}</span>`).join("")}
|
|
916
|
+
${event.tags.map((tag) => `<span class="event-tag">${escapeHtml(tag)}</span>`).join("")}
|
|
797
917
|
</div>
|
|
798
918
|
` : ""}
|
|
799
919
|
</div>
|
|
@@ -803,11 +923,17 @@ var init_CalendarElement = __esm({
|
|
|
803
923
|
const renderEvent = this._renderEvent || defaultRenderEvent;
|
|
804
924
|
const renderNoEvents = this._renderNoEvents || defaultRenderNoEvents;
|
|
805
925
|
const renderTimeGrid = (events, date) => {
|
|
926
|
+
const startHour = (time) => {
|
|
927
|
+
if (typeof time !== "string") return null;
|
|
928
|
+
const hour = Number(time.split(":")[0]);
|
|
929
|
+
return Number.isInteger(hour) && hour >= 0 && hour <= 24 ? hour : null;
|
|
930
|
+
};
|
|
806
931
|
const isHourBooked = (hour) => events.some((event) => {
|
|
807
|
-
if (!event.startTime
|
|
808
|
-
const
|
|
809
|
-
const
|
|
810
|
-
|
|
932
|
+
if (!event.startTime) return true;
|
|
933
|
+
const from = startHour(event.startTime);
|
|
934
|
+
const to = event.endTime ? startHour(event.endTime) : 24;
|
|
935
|
+
if (from === null || to === null) return true;
|
|
936
|
+
return hour >= from && hour < to;
|
|
811
937
|
});
|
|
812
938
|
const slots = Array.from({ length: 24 }, (_, hour) => {
|
|
813
939
|
const startTime = `${String(hour).padStart(2, "0")}:00`;
|
|
@@ -818,81 +944,156 @@ var init_CalendarElement = __esm({
|
|
|
818
944
|
const isRangeEnd = inTimeRange && endTime === this._timeRangeEnd;
|
|
819
945
|
const isInRange = inTimeRange && !isRangeStart && !isRangeEnd;
|
|
820
946
|
const slotClasses = [
|
|
821
|
-
"time-
|
|
822
|
-
booked ? "time-
|
|
823
|
-
isRangeStart ? "time-
|
|
824
|
-
isRangeEnd ? "time-
|
|
825
|
-
isInRange ? "time-
|
|
947
|
+
"time-grid-slot",
|
|
948
|
+
booked ? "time-grid-slot-blocked" : "time-grid-slot-open",
|
|
949
|
+
isRangeStart ? "time-grid-slot-range-start" : "",
|
|
950
|
+
isRangeEnd ? "time-grid-slot-range-end" : "",
|
|
951
|
+
isInRange ? "time-grid-slot-in-range" : ""
|
|
826
952
|
].filter(Boolean).join(" ");
|
|
827
953
|
const slotAttrs = !booked && selectable ? `data-action="select-slot" data-start-time="${startTime}" data-end-time="${endTime}" data-date="${date.toISOString()}"` : "";
|
|
828
954
|
return `
|
|
829
955
|
<div class="${slotClasses}" ${slotAttrs}>
|
|
830
|
-
<span class="time-
|
|
831
|
-
<span class="time-
|
|
956
|
+
<span class="time-grid-label">${startTime}</span>
|
|
957
|
+
<span class="time-grid-status">${booked ? "Booked" : "Available"}</span>
|
|
832
958
|
</div>`;
|
|
833
959
|
});
|
|
834
960
|
return `<div class="time-grid">${slots.join("")}</div>`;
|
|
835
961
|
};
|
|
962
|
+
const multiMonth = viewModel.panes.length > 1;
|
|
963
|
+
const renderPane = (pane) => `
|
|
964
|
+
<div class="calendar-pane">
|
|
965
|
+
${multiMonth ? `<div class="calendar-pane-caption">${escapeHtml(pane.monthAndYearText)}</div>` : ""}
|
|
966
|
+
<table class="calendar-table calendar-table-bordered">
|
|
967
|
+
<thead>
|
|
968
|
+
<tr>
|
|
969
|
+
${viewModel.days.map((day) => `<th>${day.slice(0, 3)}</th>`).join("")}
|
|
970
|
+
</tr>
|
|
971
|
+
</thead>
|
|
972
|
+
<tbody data-calendar-body>
|
|
973
|
+
${isLoading ? Array.from(
|
|
974
|
+
{ length: 6 },
|
|
975
|
+
() => `<tr>${Array.from(
|
|
976
|
+
{ length: 7 },
|
|
977
|
+
() => `<td class="calendar-skeleton" aria-hidden="true"></td>`
|
|
978
|
+
).join("")}</tr>`
|
|
979
|
+
).join("") : pane.calendarDates.map(
|
|
980
|
+
(week) => `
|
|
981
|
+
<tr>
|
|
982
|
+
${week.map((calendarDate, dayIndex) => {
|
|
983
|
+
const classes = getCellClasses(calendarDate);
|
|
984
|
+
const cellAttrs = [];
|
|
985
|
+
if (availabilityMode && calendarDate.isCurrentMonth) {
|
|
986
|
+
const bucket = this.resolveBucket(
|
|
987
|
+
calendarDate.date
|
|
988
|
+
);
|
|
989
|
+
const custom = (this._availabilityColors ?? {})[bucket];
|
|
990
|
+
classes.push(
|
|
991
|
+
`availability-${slugifyToken(bucket)}`
|
|
992
|
+
);
|
|
993
|
+
if (custom) {
|
|
994
|
+
classes.push("availability-status");
|
|
995
|
+
cellAttrs.push(
|
|
996
|
+
`style="--availability-color: ${escapeHtml(safeColor(custom))}"`
|
|
997
|
+
);
|
|
998
|
+
}
|
|
999
|
+
if (!this.isDateSelectable(calendarDate.date)) {
|
|
1000
|
+
classes.push("availability-unselectable");
|
|
1001
|
+
}
|
|
1002
|
+
cellAttrs.push(
|
|
1003
|
+
`aria-label="${escapeHtml(bucket)}"`
|
|
1004
|
+
);
|
|
1005
|
+
}
|
|
1006
|
+
if (availabilityMode === "day" && selectable && calendarDate.isCurrentMonth) {
|
|
1007
|
+
const d = calendarDate.date;
|
|
1008
|
+
if (this._rangeStart && isSameDay2(d, this._rangeStart))
|
|
1009
|
+
classes.push("availability-range-start");
|
|
1010
|
+
if (this._rangeEnd && isSameDay2(d, this._rangeEnd))
|
|
1011
|
+
classes.push("availability-range-end");
|
|
1012
|
+
if (this._rangeStart && this._rangeEnd) {
|
|
1013
|
+
if (d > this._rangeStart && d < this._rangeEnd)
|
|
1014
|
+
classes.push("availability-in-range");
|
|
1015
|
+
}
|
|
1016
|
+
}
|
|
1017
|
+
const dateString = calendarDate.date.toISOString();
|
|
1018
|
+
return `
|
|
1019
|
+
<td
|
|
1020
|
+
class="${classes.join(" ")}"
|
|
1021
|
+
data-date="${dateString}"
|
|
1022
|
+
data-day-index="${dayIndex}"
|
|
1023
|
+
data-clickable="true"
|
|
1024
|
+
${cellAttrs.join(" ")}
|
|
1025
|
+
>
|
|
1026
|
+
${calendarDate.date.getDate()}
|
|
1027
|
+
</td>
|
|
1028
|
+
`;
|
|
1029
|
+
}).join("")}
|
|
1030
|
+
</tr>
|
|
1031
|
+
`
|
|
1032
|
+
).join("")}
|
|
1033
|
+
</tbody>
|
|
1034
|
+
</table>
|
|
1035
|
+
</div>
|
|
1036
|
+
`;
|
|
836
1037
|
const html = `
|
|
837
1038
|
${title ? `
|
|
838
|
-
<div class="
|
|
839
|
-
<h1>${title}</h1>
|
|
1039
|
+
<div class="calendar-title">
|
|
1040
|
+
<h1>${escapeHtml(title)}</h1>
|
|
840
1041
|
</div>
|
|
841
1042
|
` : ""}
|
|
842
1043
|
|
|
843
|
-
<div class="calendar
|
|
844
|
-
<div class="calendar
|
|
845
|
-
<div class="calendar
|
|
846
|
-
<button type="button" class="calendar
|
|
1044
|
+
<div class="calendar-content">
|
|
1045
|
+
<div class="calendar-card">
|
|
1046
|
+
<div class="calendar-nav-header">
|
|
1047
|
+
<button type="button" class="calendar-nav-arrow" data-action="previous" aria-label="Previous month">
|
|
847
1048
|
‹
|
|
848
1049
|
</button>
|
|
849
1050
|
|
|
850
|
-
<div class="calendar
|
|
1051
|
+
<div class="calendar-picker-container" data-picker-container>
|
|
851
1052
|
<button
|
|
852
1053
|
type="button"
|
|
853
|
-
class="calendar
|
|
1054
|
+
class="calendar-picker-btn"
|
|
854
1055
|
data-action="toggle-picker"
|
|
855
1056
|
aria-expanded="${this.pickerOpen ? "true" : "false"}"
|
|
856
1057
|
aria-haspopup="true"
|
|
857
1058
|
>
|
|
858
1059
|
${useShortMonths ? `${MONTHS[viewModel.currentMonth]} ${viewModel.currentYear}` : viewModel.monthAndYearText}
|
|
859
|
-
<span class="calendar
|
|
1060
|
+
<span class="calendar-picker-chevron">▾</span>
|
|
860
1061
|
</button>
|
|
861
1062
|
|
|
862
1063
|
${this.pickerOpen ? `
|
|
863
|
-
<div class="calendar
|
|
864
|
-
<div class="calendar
|
|
1064
|
+
<div class="calendar-picker-dropdown">
|
|
1065
|
+
<div class="calendar-picker-year-row">
|
|
865
1066
|
<button
|
|
866
1067
|
type="button"
|
|
867
|
-
class="calendar
|
|
1068
|
+
class="calendar-picker-year-arrow"
|
|
868
1069
|
data-action="year-prev"
|
|
869
1070
|
${viewModel.currentYear <= minYear ? "disabled" : ""}
|
|
870
1071
|
aria-label="Previous year"
|
|
871
1072
|
>‹</button>
|
|
872
1073
|
<input
|
|
873
1074
|
type="text"
|
|
874
|
-
class="calendar
|
|
875
|
-
value="${this.yearInput || viewModel.currentYear}"
|
|
1075
|
+
class="calendar-picker-year-input${!this.yearInputValid ? " invalid" : ""}"
|
|
1076
|
+
value="${escapeHtml(this.yearInput || viewModel.currentYear)}"
|
|
876
1077
|
data-year-input
|
|
877
1078
|
aria-label="Year"
|
|
878
1079
|
/>
|
|
879
1080
|
<button
|
|
880
1081
|
type="button"
|
|
881
|
-
class="calendar
|
|
1082
|
+
class="calendar-picker-year-arrow"
|
|
882
1083
|
data-action="year-next"
|
|
883
1084
|
${viewModel.currentYear >= maxYear ? "disabled" : ""}
|
|
884
1085
|
aria-label="Next year"
|
|
885
1086
|
>›</button>
|
|
886
1087
|
</div>
|
|
887
1088
|
|
|
888
|
-
<div class="calendar
|
|
1089
|
+
<div class="calendar-picker-months">
|
|
889
1090
|
${(useShortMonths ? MONTHS : MONTHS_FULL).map((month, index) => {
|
|
890
1091
|
const isSelected = index === viewModel.currentMonth;
|
|
891
1092
|
const isCurrent = index === todayMonth && viewModel.currentYear === todayYear;
|
|
892
1093
|
return `
|
|
893
1094
|
<button
|
|
894
1095
|
type="button"
|
|
895
|
-
class="calendar
|
|
1096
|
+
class="calendar-picker-month${isSelected ? " selected" : ""}${isCurrent ? " current-month" : ""}"
|
|
896
1097
|
data-action="select-month"
|
|
897
1098
|
data-month="${index}"
|
|
898
1099
|
>${month}</button>
|
|
@@ -905,70 +1106,22 @@ var init_CalendarElement = __esm({
|
|
|
905
1106
|
|
|
906
1107
|
<button
|
|
907
1108
|
type="button"
|
|
908
|
-
class="calendar
|
|
1109
|
+
class="calendar-today-btn"
|
|
909
1110
|
data-action="today"
|
|
910
1111
|
${isCurrentMonth ? "disabled" : ""}
|
|
911
1112
|
>Today</button>
|
|
912
1113
|
|
|
913
|
-
<button type="button" class="calendar
|
|
1114
|
+
<button type="button" class="calendar-nav-arrow" data-action="next" aria-label="Next month">
|
|
914
1115
|
›
|
|
915
1116
|
</button>
|
|
916
1117
|
</div>
|
|
917
1118
|
|
|
918
|
-
<
|
|
919
|
-
|
|
920
|
-
|
|
921
|
-
${viewModel.days.map((day) => `<th>${day.slice(0, 3)}</th>`).join("")}
|
|
922
|
-
</tr>
|
|
923
|
-
</thead>
|
|
924
|
-
<tbody data-calendar-body>
|
|
925
|
-
${isLoading ? Array.from(
|
|
926
|
-
{ length: 6 },
|
|
927
|
-
() => `<tr>${Array.from(
|
|
928
|
-
{ length: 7 },
|
|
929
|
-
() => `<td class="calendar--skeleton" aria-hidden="true"></td>`
|
|
930
|
-
).join("")}</tr>`
|
|
931
|
-
).join("") : viewModel.calendarDates.map(
|
|
932
|
-
(week) => `
|
|
933
|
-
<tr>
|
|
934
|
-
${week.map((calendarDate, dayIndex) => {
|
|
935
|
-
const classes = getCellClasses(calendarDate);
|
|
936
|
-
if (availabilityMode && calendarDate.isCurrentMonth) {
|
|
937
|
-
classes.push(
|
|
938
|
-
calendarDate.hasEvents ? "availability--booked" : "availability--free"
|
|
939
|
-
);
|
|
940
|
-
}
|
|
941
|
-
if (availabilityMode === "day" && selectable && calendarDate.isCurrentMonth) {
|
|
942
|
-
const d = calendarDate.date;
|
|
943
|
-
if (this._rangeStart && isSameDay2(d, this._rangeStart))
|
|
944
|
-
classes.push("availability--range-start");
|
|
945
|
-
if (this._rangeEnd && isSameDay2(d, this._rangeEnd))
|
|
946
|
-
classes.push("availability--range-end");
|
|
947
|
-
if (this._rangeStart && this._rangeEnd) {
|
|
948
|
-
if (d > this._rangeStart && d < this._rangeEnd)
|
|
949
|
-
classes.push("availability--in-range");
|
|
950
|
-
}
|
|
951
|
-
}
|
|
952
|
-
const dateString = calendarDate.date.toISOString();
|
|
953
|
-
return `
|
|
954
|
-
<td
|
|
955
|
-
class="${classes.join(" ")}"
|
|
956
|
-
data-date="${dateString}"
|
|
957
|
-
data-day-index="${dayIndex}"
|
|
958
|
-
data-clickable="true"
|
|
959
|
-
>
|
|
960
|
-
${calendarDate.date.getDate()}
|
|
961
|
-
</td>
|
|
962
|
-
`;
|
|
963
|
-
}).join("")}
|
|
964
|
-
</tr>
|
|
965
|
-
`
|
|
966
|
-
).join("")}
|
|
967
|
-
</tbody>
|
|
968
|
-
</table>
|
|
1119
|
+
<div class="calendar-panes">
|
|
1120
|
+
${viewModel.panes.map(renderPane).join("")}
|
|
1121
|
+
</div>
|
|
969
1122
|
|
|
970
1123
|
${!isLoading && availabilityMode !== "day" && viewModel.selectedDate ? `
|
|
971
|
-
<div class="date-popup
|
|
1124
|
+
<div class="date-popup">
|
|
972
1125
|
<div class="popup-header">
|
|
973
1126
|
<h2>${viewModel.scheduleDay}</h2>
|
|
974
1127
|
<button type="button" class="popup-close" data-action="close-popup" aria-label="Close">\u2715</button>
|
|
@@ -1006,8 +1159,7 @@ var init_CalendarElement = __esm({
|
|
|
1006
1159
|
const availMode = this.getAttribute("availability-mode");
|
|
1007
1160
|
const isSelectable = this.hasAttribute("selectable");
|
|
1008
1161
|
if (availMode === "day" && isSelectable) {
|
|
1009
|
-
|
|
1010
|
-
if (!isBooked) {
|
|
1162
|
+
if (this.isDateSelectable(date)) {
|
|
1011
1163
|
let startDate;
|
|
1012
1164
|
let endDate;
|
|
1013
1165
|
if (this._rangeEnd !== null) {
|
|
@@ -1025,7 +1177,7 @@ var init_CalendarElement = __esm({
|
|
|
1025
1177
|
cursor.setDate(cursor.getDate() + 1);
|
|
1026
1178
|
let blocked = false;
|
|
1027
1179
|
while (cursor < e2) {
|
|
1028
|
-
if (this.
|
|
1180
|
+
if (!this.isDateSelectable(cursor)) {
|
|
1029
1181
|
blocked = true;
|
|
1030
1182
|
break;
|
|
1031
1183
|
}
|
|
@@ -1259,31 +1411,84 @@ var init_CalendarElement = __esm({
|
|
|
1259
1411
|
this.theme = theme;
|
|
1260
1412
|
}
|
|
1261
1413
|
getCurrentDate() {
|
|
1414
|
+
this.rethrowInitError();
|
|
1262
1415
|
return this.engine?.getViewModel().selectedDate ?? null;
|
|
1263
1416
|
}
|
|
1264
1417
|
goToDate(date) {
|
|
1418
|
+
this.rethrowInitError();
|
|
1265
1419
|
const year = date.getFullYear();
|
|
1266
1420
|
const month = date.getMonth();
|
|
1267
1421
|
this.dispatchMonthChange(year, month);
|
|
1268
1422
|
this.actions?.jump(year, month);
|
|
1269
1423
|
}
|
|
1270
1424
|
getEngine() {
|
|
1425
|
+
this.rethrowInitError();
|
|
1271
1426
|
if (!this.engine)
|
|
1272
1427
|
throw new Error("CalendarElement is not connected to the DOM");
|
|
1273
1428
|
return this.engine;
|
|
1274
1429
|
}
|
|
1275
1430
|
};
|
|
1276
|
-
|
|
1431
|
+
_CalendarElement.observedAttributes = [
|
|
1277
1432
|
"initial-date",
|
|
1278
1433
|
"min-year",
|
|
1279
1434
|
"max-year",
|
|
1280
1435
|
"week-starts-on",
|
|
1436
|
+
"heading",
|
|
1437
|
+
"months",
|
|
1281
1438
|
"title",
|
|
1282
1439
|
"use-short-month-names",
|
|
1283
1440
|
"availability-mode",
|
|
1284
1441
|
"selectable",
|
|
1285
1442
|
"loading"
|
|
1286
1443
|
];
|
|
1444
|
+
_CalendarElement.themeMap = {
|
|
1445
|
+
primary: "--calendar-primary-color",
|
|
1446
|
+
secondary: "--calendar-secondary-color",
|
|
1447
|
+
tertiary: "--calendar-tertiary-color",
|
|
1448
|
+
textColor: "--calendar-text-color",
|
|
1449
|
+
textLight: "--calendar-text-light",
|
|
1450
|
+
background: "--calendar-background",
|
|
1451
|
+
cellHover: "--calendar-cell-hover",
|
|
1452
|
+
borderColor: "--calendar-border-color",
|
|
1453
|
+
todayOutline: "--calendar-today-outline",
|
|
1454
|
+
selectedBg: "--calendar-selected-bg",
|
|
1455
|
+
headerBg: "--calendar-header-bg",
|
|
1456
|
+
popupBg: "--calendar-popup-bg",
|
|
1457
|
+
pickerBg: "--calendar-picker-bg",
|
|
1458
|
+
pickerShadow: "--calendar-picker-shadow",
|
|
1459
|
+
eventIndicator: "--calendar-event-indicator",
|
|
1460
|
+
onAccent: "--calendar-on-accent",
|
|
1461
|
+
link: "--calendar-link",
|
|
1462
|
+
openBg: "--calendar-open-bg",
|
|
1463
|
+
openFg: "--calendar-open-fg",
|
|
1464
|
+
conditionalBg: "--calendar-conditional-bg",
|
|
1465
|
+
conditionalFg: "--calendar-conditional-fg",
|
|
1466
|
+
blockedBg: "--calendar-blocked-bg",
|
|
1467
|
+
blockedFg: "--calendar-blocked-fg",
|
|
1468
|
+
rangeBg: "--calendar-range-bg",
|
|
1469
|
+
rangeOutline: "--calendar-range-outline",
|
|
1470
|
+
inRangeBg: "--calendar-in-range-bg",
|
|
1471
|
+
inRangeOutline: "--calendar-in-range-outline",
|
|
1472
|
+
badgeBg: "--calendar-badge-bg",
|
|
1473
|
+
badgeText: "--calendar-badge-text",
|
|
1474
|
+
badgeSuccessBg: "--calendar-badge-success-bg",
|
|
1475
|
+
badgeSuccessText: "--calendar-badge-success-text",
|
|
1476
|
+
badgeInfoBg: "--calendar-badge-info-bg",
|
|
1477
|
+
badgeInfoText: "--calendar-badge-info-text",
|
|
1478
|
+
badgeWarningBg: "--calendar-badge-warning-bg",
|
|
1479
|
+
badgeWarningText: "--calendar-badge-warning-text",
|
|
1480
|
+
badgeDangerBg: "--calendar-badge-danger-bg",
|
|
1481
|
+
badgeDangerText: "--calendar-badge-danger-text",
|
|
1482
|
+
badgeNeutralBg: "--calendar-badge-neutral-bg",
|
|
1483
|
+
badgeNeutralText: "--calendar-badge-neutral-text",
|
|
1484
|
+
badgePositiveBg: "--calendar-badge-positive-bg",
|
|
1485
|
+
badgePositiveText: "--calendar-badge-positive-text",
|
|
1486
|
+
badgeTentativeBg: "--calendar-badge-tentative-bg",
|
|
1487
|
+
badgeTentativeText: "--calendar-badge-tentative-text"
|
|
1488
|
+
};
|
|
1489
|
+
_CalendarElement.BUILT_IN_BUCKETS = ["blocked", "conditional", "open"];
|
|
1490
|
+
_CalendarElement.titleDeprecationWarned = false;
|
|
1491
|
+
CalendarElement = _CalendarElement;
|
|
1287
1492
|
}
|
|
1288
1493
|
});
|
|
1289
1494
|
|
|
@@ -1297,6 +1502,7 @@ __export(web_components_exports, {
|
|
|
1297
1502
|
MONTHS: () => MONTHS,
|
|
1298
1503
|
MONTHS_FULL: () => MONTHS_FULL,
|
|
1299
1504
|
defineCalendarElement: () => defineCalendarElement,
|
|
1505
|
+
escapeHtml: () => escapeHtml,
|
|
1300
1506
|
formatAttendees: () => formatAttendees,
|
|
1301
1507
|
formatDateForDisplay: () => formatDateForDisplay,
|
|
1302
1508
|
formatTimeRange: () => formatTimeRange,
|
|
@@ -1307,13 +1513,15 @@ __export(web_components_exports, {
|
|
|
1307
1513
|
getDefaultEventColor: () => getDefaultEventColor,
|
|
1308
1514
|
getEventsForDate: () => getEventsForDate,
|
|
1309
1515
|
getMonthYearText: () => getMonthYearText,
|
|
1310
|
-
getPopupPositionClass: () => getPopupPositionClass,
|
|
1311
1516
|
hasEvents: () => hasEvents,
|
|
1312
1517
|
isSameDay: () => isSameDay,
|
|
1313
1518
|
isToday: () => isToday,
|
|
1314
1519
|
isValidHexColor: () => isValidHexColor,
|
|
1315
1520
|
mergeCategoryColors: () => mergeCategoryColors,
|
|
1316
1521
|
normalizeDate: () => normalizeDate,
|
|
1522
|
+
safeColor: () => safeColor,
|
|
1523
|
+
safeUrl: () => safeUrl,
|
|
1524
|
+
slugifyToken: () => slugifyToken,
|
|
1317
1525
|
sortEventsByTime: () => sortEventsByTime
|
|
1318
1526
|
});
|
|
1319
1527
|
module.exports = __toCommonJS(web_components_exports);
|
|
@@ -1335,6 +1543,7 @@ if (typeof customElements !== "undefined" && !customElements.get("kal-calendar")
|
|
|
1335
1543
|
MONTHS,
|
|
1336
1544
|
MONTHS_FULL,
|
|
1337
1545
|
defineCalendarElement,
|
|
1546
|
+
escapeHtml,
|
|
1338
1547
|
formatAttendees,
|
|
1339
1548
|
formatDateForDisplay,
|
|
1340
1549
|
formatTimeRange,
|
|
@@ -1345,13 +1554,15 @@ if (typeof customElements !== "undefined" && !customElements.get("kal-calendar")
|
|
|
1345
1554
|
getDefaultEventColor,
|
|
1346
1555
|
getEventsForDate,
|
|
1347
1556
|
getMonthYearText,
|
|
1348
|
-
getPopupPositionClass,
|
|
1349
1557
|
hasEvents,
|
|
1350
1558
|
isSameDay,
|
|
1351
1559
|
isToday,
|
|
1352
1560
|
isValidHexColor,
|
|
1353
1561
|
mergeCategoryColors,
|
|
1354
1562
|
normalizeDate,
|
|
1563
|
+
safeColor,
|
|
1564
|
+
safeUrl,
|
|
1565
|
+
slugifyToken,
|
|
1355
1566
|
sortEventsByTime
|
|
1356
1567
|
});
|
|
1357
1568
|
//# sourceMappingURL=index.js.map
|