@fullcalendar/daygrid 7.0.0-beta.0 → 7.0.0-beta.3

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/index.global.js CHANGED
@@ -1,5 +1,5 @@
1
1
  /*!
2
- FullCalendar Day Grid Plugin v7.0.0-beta.0
2
+ FullCalendar Day Grid Plugin v7.0.0-beta.3
3
3
  Docs & License: https://fullcalendar.io/docs/month-view
4
4
  (c) 2024 Adam Shaw
5
5
  */
@@ -16,154 +16,90 @@ FullCalendar.DayGrid = (function (exports, core, internal$1, preact) {
16
16
  }
17
17
  }
18
18
 
19
- function renderInner(renderProps) {
20
- return renderProps.text;
21
- }
22
- function buildDayTableModel(dateProfile, dateProfileGenerator) {
23
- let daySeries = new internal$1.DaySeriesModel(dateProfile.renderRange, dateProfileGenerator);
24
- return new internal$1.DayTableModel(daySeries, /year|month|week/.test(dateProfile.currentRangeUnit));
25
- }
26
- function computeColWidth(colCnt, colMinWidth, viewportWidth) {
27
- if (viewportWidth == null) {
28
- return [undefined, undefined];
29
- }
30
- const colTempWidth = viewportWidth / colCnt;
31
- if (colTempWidth < colMinWidth) {
32
- return [colMinWidth * colCnt, colMinWidth];
33
- }
34
- return [viewportWidth, undefined];
35
- }
36
- function buildHeaderTiers(dates, datesRepDistinctDays) {
37
- return [
38
- datesRepDistinctDays
39
- ? dates.map((date) => ({ colSpan: 1, date }))
40
- : dates.map((date) => ({ colSpan: 1, dow: date.getUTCDay() }))
41
- ];
42
- }
43
- // Positioning
19
+ // TODO: converge types with DayTableCell and DayCellContainer (the component) and refineRenderProps
20
+ // the generation of DayTableCell will be distinct (for the BODY cells)
21
+ // but can share some of the same types/utils
22
+ // Date Cells
44
23
  // -------------------------------------------------------------------------------------------------
45
- function computeTopFromDate(date, cellRows, rowHeightMap) {
46
- let top = 0;
47
- for (const cells of cellRows) {
48
- const start = cells[0].date;
49
- const end = cells[cells.length - 1].date;
50
- const key = start.toISOString();
51
- if (date >= start && date <= end) {
52
- return top;
53
- }
54
- const rowHeight = rowHeightMap.get(key);
55
- if (rowHeight == null) {
56
- return; // denote unknown
57
- }
58
- top += rowHeight;
59
- }
60
- return top;
61
- }
62
- function computeHorizontalsFromSeg(seg, colWidth, colCnt, isRtl) {
63
- let left;
64
- let right;
65
- let width;
66
- if (colWidth != null) {
67
- width = (seg.lastCol - seg.firstCol + 1) * colWidth;
68
- if (isRtl) {
69
- right = seg.firstCol * colWidth;
70
- }
71
- else {
72
- left = seg.firstCol * colWidth;
73
- }
74
- }
75
- else {
76
- const colWidthFrac = 1 / colCnt;
77
- width = internal$1.fracToCssDim((seg.lastCol - seg.firstCol + 1) * colWidthFrac);
78
- if (isRtl) {
79
- right = internal$1.fracToCssDim(seg.firstCol * colWidthFrac);
80
- }
81
- else {
82
- left = internal$1.fracToCssDim(seg.firstCol * colWidthFrac);
83
- }
84
- }
85
- return { left, right, width };
86
- }
87
- function computeColFromPosition(positionLeft, elWidth, colWidth, colCnt, isRtl) {
88
- const realColWidth = colWidth != null ? colWidth : elWidth / colCnt;
89
- const colFromLeft = Math.floor(positionLeft / realColWidth);
90
- const col = isRtl ? (colCnt - colFromLeft - 1) : colFromLeft;
91
- const left = colFromLeft * realColWidth;
92
- const right = left + realColWidth;
93
- return { col, left, right };
94
- }
95
- function computeRowFromPosition(positionTop, cellRows, rowHeightMap) {
96
- let row = 0;
97
- let top = 0;
98
- let bottom = 0;
99
- for (const cells of cellRows) {
100
- const key = cells[0].key;
101
- top = bottom;
102
- bottom = top + rowHeightMap.get(key);
103
- if (positionTop < bottom) {
104
- break;
105
- }
106
- row++;
107
- }
108
- return { row, top, bottom };
24
+ const WEEKDAY_FORMAT = internal$1.createFormatter({ weekday: 'long' });
25
+ const firstSunday = new Date(259200000);
26
+ function buildDateRowConfigs(...args) {
27
+ return [buildDateRowConfig(...args)];
109
28
  }
110
- // Hit Element
111
- // -------------------------------------------------------------------------------------------------
112
- function getRowEl(rootEl, row) {
113
- return rootEl.querySelectorAll(':scope > [role=row]')[row];
29
+ /*
30
+ Should this receive resource data attributes?
31
+ Or ResourceApi object itself?
32
+ */
33
+ function buildDateRowConfig(dates, datesRepDistinctDays, dateProfile, todayRange, dayHeaderFormat, // TODO: rename to dateHeaderFormat?
34
+ context, colSpan) {
35
+ return {
36
+ renderConfig: buildDateRenderConfig(context),
37
+ dataConfigs: buildDateDataConfigs(dates, datesRepDistinctDays, dateProfile, todayRange, dayHeaderFormat, context, colSpan)
38
+ };
114
39
  }
115
- function getCellEl(rowEl, col) {
116
- return rowEl.querySelectorAll(':scope > [role=gridcell]')[col];
40
+ function buildDateRenderConfig(context) {
41
+ const { options } = context;
42
+ return {
43
+ generatorName: 'dayHeaderContent',
44
+ customGenerator: options.dayHeaderContent,
45
+ classNameGenerator: options.dayHeaderClassNames,
46
+ didMount: options.dayHeaderDidMount,
47
+ willUnmount: options.dayHeaderWillUnmount,
48
+ };
117
49
  }
118
-
119
- class DateHeaderCell extends internal$1.BaseComponent {
120
- constructor() {
121
- super(...arguments);
122
- // ref
123
- this.innerElRef = preact.createRef();
124
- }
125
- render() {
126
- let { props, context } = this;
127
- let { dateProfile, date, extraRenderProps, extraDataAttrs } = props;
128
- let { dateEnv, options, theme, viewApi } = context;
129
- let dayMeta = internal$1.getDateMeta(date, props.todayRange, null, dateProfile);
130
- let text = dateEnv.format(date, props.dayHeaderFormat);
131
- let navLinkAttrs = (!dayMeta.isDisabled && props.navLink)
132
- ? internal$1.buildNavLinkAttrs(context, date)
133
- : {};
134
- let renderProps = Object.assign(Object.assign(Object.assign({ date: dateEnv.toDate(date), view: viewApi }, extraRenderProps), { text }), dayMeta);
135
- return (preact.createElement(internal$1.ContentContainer, { elTag: 'div', elClasses: [
136
- ...internal$1.getDayClassNames(dayMeta, theme),
137
- ...(props.extraClassNames || []),
138
- 'fc-header-cell',
139
- 'fc-cell',
140
- props.colWidth != null ? '' : 'fc-liquid',
141
- 'fc-flex-column',
142
- 'fc-align-center',
143
- ], elAttrs: Object.assign({ 'data-date': !dayMeta.isDisabled ? internal$1.formatDayString(date) : undefined }, extraDataAttrs), elStyle: {
144
- width: props.colWidth != null // TODO: DRY
145
- ? props.colWidth * (props.colSpan || 1)
146
- : undefined,
147
- }, renderProps: renderProps, generatorName: "dayHeaderContent", customGenerator: options.dayHeaderContent, defaultGenerator: renderInner, classNameGenerator: options.dayHeaderClassNames, didMount: options.dayHeaderDidMount, willUnmount: options.dayHeaderWillUnmount }, (InnerContainer) => (preact.createElement("div", { ref: this.innerElRef, className: [
148
- 'fc-flex-column',
149
- props.isSticky ? 'fc-sticky-x' : '',
150
- ].join(' ') }, !dayMeta.isDisabled && (preact.createElement(InnerContainer, { elTag: "a", elAttrs: navLinkAttrs, elClasses: [
151
- 'fc-cell-inner',
152
- 'fc-padding-sm',
153
- ] }))))));
154
- }
155
- componentDidMount() {
156
- const innerEl = this.innerElRef.current; // TODO: make dynamic with useEffect
157
- // TODO: only attach this if refs props present
158
- this.disconectInnerHeight = internal$1.watchHeight(innerEl, (height) => {
159
- internal$1.setRef(this.props.innerHeightRef, height);
50
+ function buildDateDataConfigs(dates, datesRepDistinctDays, dateProfile, todayRange, dayHeaderFormat, // TODO: rename to dateHeaderFormat?
51
+ context, colSpan = 1, keyPrefix = '') {
52
+ const { dateEnv, viewApi, options } = context;
53
+ return datesRepDistinctDays
54
+ ? dates.map((date) => {
55
+ const dateMeta = internal$1.getDateMeta(date, todayRange, null, dateProfile);
56
+ const text = dateEnv.format(date, dayHeaderFormat);
57
+ const renderProps = Object.assign(Object.assign({}, dateMeta), { date: dateEnv.toDate(date), view: viewApi, text });
58
+ const isNavLink = options.navLinks && !dateMeta.isDisabled;
59
+ return {
60
+ key: keyPrefix + date.toUTCString(),
61
+ renderProps,
62
+ attrs: { 'data-date': !dateMeta.isDisabled ? internal$1.formatDayString(date) : undefined },
63
+ innerAttrs: isNavLink ? internal$1.buildNavLinkAttrs(context, date) : {},
64
+ colSpan,
65
+ isNavLink,
66
+ className: internal$1.getDayClassName(dateMeta),
67
+ };
68
+ })
69
+ : dates.map((date) => {
70
+ const dow = date.getUTCDay();
71
+ const normDate = internal$1.addDays(firstSunday, dow);
72
+ const dayMeta = {
73
+ dow,
74
+ isDisabled: false,
75
+ isFuture: false,
76
+ isPast: false,
77
+ isToday: false,
78
+ isOther: false,
79
+ };
80
+ const text = dateEnv.format(normDate, dayHeaderFormat);
81
+ const renderProps = Object.assign(Object.assign({}, dayMeta), { date, view: viewApi, text });
82
+ return {
83
+ key: keyPrefix + String(dow),
84
+ renderProps,
85
+ innerAttrs: { 'aria-label': dateEnv.format(normDate, WEEKDAY_FORMAT) },
86
+ colSpan,
87
+ className: internal$1.getDayClassName(dayMeta),
88
+ };
160
89
  });
161
- }
162
- componentWillUnmount() {
163
- this.disconectInnerHeight();
164
- }
165
90
  }
166
91
 
92
+ /*
93
+ We need really specific keys because RefMap::createRef() which is then given to heightRef
94
+ unable to change key! As a result, we cannot reuse elements between normal/slice/standin types,
95
+ but that's okay since they render quite differently
96
+ */
97
+ function getEventPartKey(seg) {
98
+ return internal$1.getEventKey(seg) + ':' + seg.start +
99
+ (seg.standinFor ? ':standin' : seg.isSlice ? ':slice' : '');
100
+ }
101
+ // DayGridRange utils (TODO: move)
102
+ // -------------------------------------------------------------------------------------------------
167
103
  function splitSegsByRow(segs, rowCnt) {
168
104
  const byRow = [];
169
105
  for (let row = 0; row < rowCnt; row++) {
@@ -195,20 +131,8 @@ FullCalendar.DayGrid = (function (exports, core, internal$1, preact) {
195
131
  }
196
132
  return byRow;
197
133
  }
198
- function splitSegsByCol(segs, colCnt) {
199
- let byCol = [];
200
- for (let col = 0; col < colCnt; col++) {
201
- byCol.push([]);
202
- }
203
- for (let seg of segs) {
204
- for (let col = seg.firstCol; col <= seg.lastCol; col++) {
205
- if (seg.firstCol !== col) {
206
- seg = Object.assign(Object.assign({}, seg), { firstCol: col, lastCol: col, isStart: false, isEnd: seg.isEnd && seg.lastCol === col, isStandin: true });
207
- }
208
- byCol[col].push(seg);
209
- }
210
- }
211
- return byCol;
134
+ function sliceSegForCol(seg, col) {
135
+ return Object.assign(Object.assign({}, seg), { start: col, end: col + 1, isStart: seg.isStart && seg.start === col, isEnd: seg.isEnd && seg.end - 1 === col, standinFor: seg });
212
136
  }
213
137
 
214
138
  const DEFAULT_TABLE_EVENT_TIME_FORMAT = internal$1.createFormatter({
@@ -221,7 +145,7 @@ FullCalendar.DayGrid = (function (exports, core, internal$1, preact) {
221
145
  let { display } = seg.eventRange.ui;
222
146
  return display === 'list-item' || (display === 'auto' &&
223
147
  !seg.eventRange.def.allDay &&
224
- seg.firstCol === seg.lastCol && // can't be multi-day
148
+ (seg.end - seg.start) === 1 && // single-day
225
149
  seg.isStart && // "
226
150
  seg.isEnd // "
227
151
  );
@@ -230,7 +154,7 @@ FullCalendar.DayGrid = (function (exports, core, internal$1, preact) {
230
154
  class DayGridBlockEvent extends internal$1.BaseComponent {
231
155
  render() {
232
156
  let { props } = this;
233
- return (preact.createElement(internal$1.StandardEvent, Object.assign({}, props, { elClasses: ['fc-daygrid-event', 'fc-daygrid-block-event', 'fc-h-event'], defaultTimeFormat: DEFAULT_TABLE_EVENT_TIME_FORMAT, defaultDisplayEventEnd: props.defaultDisplayEventEnd, disableResizing: !props.seg.eventRange.def.allDay })));
157
+ return (preact.createElement(internal$1.StandardEvent, Object.assign({}, props, { className: 'fc-daygrid-block-event fc-daygrid-event fc-h-event', defaultTimeFormat: DEFAULT_TABLE_EVENT_TIME_FORMAT, defaultDisplayEventEnd: props.defaultDisplayEventEnd, disableResizing: !props.eventRange.def.allDay })));
234
158
  }
235
159
  }
236
160
 
@@ -238,10 +162,14 @@ FullCalendar.DayGrid = (function (exports, core, internal$1, preact) {
238
162
  render() {
239
163
  let { props, context } = this;
240
164
  let { options } = context;
241
- let { seg } = props;
165
+ let { eventRange } = props;
242
166
  let timeFormat = options.eventTimeFormat || DEFAULT_TABLE_EVENT_TIME_FORMAT;
243
- let timeText = internal$1.buildSegTimeText(seg, timeFormat, context, true, props.defaultDisplayEventEnd);
244
- return (preact.createElement(internal$1.EventContainer, Object.assign({}, props, { elTag: "a", elClasses: ['fc-daygrid-event', 'fc-daygrid-dot-event'], elAttrs: internal$1.getSegAnchorAttrs(props.seg, context), defaultGenerator: renderInnerContent, timeText: timeText, isResizing: false, isDateSelecting: false })));
167
+ let timeText = internal$1.buildEventRangeTimeText(timeFormat, eventRange,
168
+ /* slicedStart = */ undefined,
169
+ /* slicedEnd = */ undefined, props.isStart, props.isEnd, context,
170
+ /* defaultDisplayEventTime = */ true, props.defaultDisplayEventEnd);
171
+ let anchorAttrs = internal$1.getEventRangeAnchorAttrs(eventRange, context);
172
+ return (preact.createElement(internal$1.EventContainer, Object.assign({}, props, { tag: anchorAttrs ? 'a' : 'div', attrs: anchorAttrs, className: 'fc-daygrid-dot-event fc-daygrid-event', defaultGenerator: renderInnerContent, timeText: timeText, isResizing: false, isDateSelecting: false })));
245
173
  }
246
174
  }
247
175
  function renderInnerContent(renderProps) {
@@ -254,16 +182,19 @@ FullCalendar.DayGrid = (function (exports, core, internal$1, preact) {
254
182
  class DayGridMoreLink extends internal$1.BaseComponent {
255
183
  render() {
256
184
  let { props } = this;
257
- return (preact.createElement(internal$1.MoreLinkContainer, { elClasses: ['fc-daygrid-more-link'], dateProfile: props.dateProfile, todayRange: props.todayRange, allDayDate: props.allDayDate, segs: props.segs, hiddenSegs: props.hiddenSegs, alignmentElRef: props.alignmentElRef, alignGridTop: props.alignGridTop, extraDateSpan: props.extraDateSpan, popoverContent: () => {
185
+ return (preact.createElement(internal$1.MoreLinkContainer, { className: internal$1.joinClassNames('fc-daygrid-more-link', props.isBlock
186
+ ? 'fc-daygrid-more-link-block'
187
+ : 'fc-daygrid-more-link-button'), dateProfile: props.dateProfile, todayRange: props.todayRange, allDayDate: props.allDayDate, segs: props.segs, hiddenSegs: props.hiddenSegs, alignElRef: props.alignElRef, alignParentTop: props.alignParentTop, dateSpanProps: props.dateSpanProps, popoverContent: () => {
258
188
  let forcedInvisibleMap = // TODO: more convenient/DRY
259
189
  (props.eventDrag ? props.eventDrag.affectedInstances : null) ||
260
190
  (props.eventResize ? props.eventResize.affectedInstances : null) ||
261
191
  {};
262
192
  return (preact.createElement(preact.Fragment, null, props.segs.map((seg) => {
263
- let instanceId = seg.eventRange.instance.instanceId;
193
+ let { eventRange } = seg;
194
+ let { instanceId } = eventRange.instance;
264
195
  return (preact.createElement("div", { key: instanceId, style: {
265
196
  visibility: forcedInvisibleMap[instanceId] ? 'hidden' : '',
266
- } }, hasListItemDisplay(seg) ? (preact.createElement(DayGridListEvent, Object.assign({ seg: seg, isDragging: false, isSelected: instanceId === props.eventSelection, defaultDisplayEventEnd: false }, internal$1.getSegMeta(seg, props.todayRange)))) : (preact.createElement(DayGridBlockEvent, Object.assign({ seg: seg, isDragging: false, isResizing: false, isDateSelecting: false, isSelected: instanceId === props.eventSelection, defaultDisplayEventEnd: false }, internal$1.getSegMeta(seg, props.todayRange))))));
197
+ } }, hasListItemDisplay(seg) ? (preact.createElement(DayGridListEvent, Object.assign({ eventRange: eventRange, isStart: seg.isStart, isEnd: seg.isEnd, isDragging: false, isSelected: instanceId === props.eventSelection, defaultDisplayEventEnd: false }, internal$1.getEventRangeMeta(eventRange, props.todayRange)))) : (preact.createElement(DayGridBlockEvent, Object.assign({ eventRange: eventRange, isStart: seg.isStart, isEnd: seg.isEnd, isDragging: false, isResizing: false, isDateSelecting: false, isSelected: instanceId === props.eventSelection, defaultDisplayEventEnd: false }, internal$1.getEventRangeMeta(eventRange, props.todayRange))))));
267
198
  })));
268
199
  } }));
269
200
  }
@@ -273,8 +204,8 @@ FullCalendar.DayGrid = (function (exports, core, internal$1, preact) {
273
204
  constructor() {
274
205
  super(...arguments);
275
206
  // ref
276
- this.innerElRef = preact.createRef();
277
- this.headerWrapElRef = preact.createRef();
207
+ this.rootElRef = preact.createRef();
208
+ this.bodyElRef = preact.createRef();
278
209
  }
279
210
  render() {
280
211
  let { props, context } = this;
@@ -282,48 +213,37 @@ FullCalendar.DayGrid = (function (exports, core, internal$1, preact) {
282
213
  // TODO: memoize this
283
214
  const isMonthStart = props.showDayNumber &&
284
215
  shouldDisplayMonthStart(props.date, props.dateProfile.currentRange, dateEnv);
285
- return (preact.createElement(internal$1.DayCellContainer, { elTag: "div", elClasses: [
286
- 'fc-daygrid-cell',
287
- 'fc-cell',
288
- props.width != null ? '' : 'fc-liquid',
289
- 'fc-flex-column',
290
- ...(props.extraClassNames || []),
291
- ], elAttrs: Object.assign(Object.assign({}, props.extraDataAttrs), { role: 'gridcell' }), elStyle: {
216
+ return (preact.createElement(internal$1.DayCellContainer, { tag: "div", className: internal$1.joinClassNames(props.className, 'fc-daygrid-day fc-flex-col', props.borderStart && 'fc-border-s', props.width != null ? '' : 'fc-liquid'), attrs: Object.assign(Object.assign({}, props.attrs), { role: 'gridcell' }), style: {
292
217
  width: props.width
293
- }, extraRenderProps: props.extraRenderProps, defaultGenerator: renderTopInner, date: props.date, dateProfile: props.dateProfile, todayRange: props.todayRange, showDayNumber: props.showDayNumber, isMonthStart: isMonthStart }, (InnerContent, renderProps) => (preact.createElement("div", { ref: this.innerElRef, className: [
294
- 'fc-daygrid-cell-inner',
295
- props.fgLiquidHeight ? 'fc-liquid' : ''
296
- ].join(' ') },
297
- preact.createElement("div", { ref: this.headerWrapElRef, className: "fc-flex-column" }, !renderProps.isDisabled && (props.showDayNumber || internal$1.hasCustomDayCellContent(options)) && (preact.createElement("div", { className: "fc-daygrid-cell-header" },
298
- preact.createElement(InnerContent, { elTag: "a", elClasses: [
299
- 'fc-daygrid-cell-number',
300
- isMonthStart && 'fc-daygrid-month-start',
301
- ], elAttrs: internal$1.buildNavLinkAttrs(context, props.date) })))),
302
- preact.createElement("div", { className: "fc-daygrid-cell-main", style: {
303
- height: props.fgLiquidHeight ? '' : props.fgHeight
304
- } }, props.fg),
305
- preact.createElement("div", { className: "fc-daygrid-cell-footer", style: props.fgLiquidHeight
306
- ? { position: 'relative', top: props.fgHeight }
307
- : {} },
308
- preact.createElement(DayGridMoreLink, { allDayDate: props.date, segs: props.segs, hiddenSegs: props.hiddenSegs, alignmentElRef: this.innerElRef, alignGridTop: !props.showDayNumber, extraDateSpan: props.extraDateSpan, dateProfile: props.dateProfile, eventSelection: props.eventSelection, eventDrag: props.eventDrag, eventResize: props.eventResize, todayRange: props.todayRange })),
309
- props.bg))));
218
+ }, elRef: this.rootElRef, renderProps: props.renderProps, defaultGenerator: renderTopInner, date: props.date, dateProfile: props.dateProfile, todayRange: props.todayRange, showDayNumber: props.showDayNumber, isMonthStart: isMonthStart }, (InnerContent, renderProps) => (preact.createElement(preact.Fragment, null,
219
+ !renderProps.isDisabled && (props.showDayNumber || internal$1.hasCustomDayCellContent(options)) && (preact.createElement("div", { className: "fc-daygrid-day-header" },
220
+ preact.createElement(InnerContent, { tag: "a", attrs: internal$1.buildNavLinkAttrs(context, props.date), className: internal$1.joinClassNames('fc-daygrid-day-number', isMonthStart && 'fc-daygrid-month-start') }))),
221
+ preact.createElement("div", { className: internal$1.joinClassNames('fc-daygrid-day-body', props.isTall && 'fc-daygrid-day-body-tall', props.fgLiquidHeight ? 'fc-liquid' : 'fc-grow'), ref: this.bodyElRef },
222
+ preact.createElement("div", { className: 'fc-daygrid-day-events', style: { height: props.fgHeight } }, props.fg),
223
+ preact.createElement(DayGridMoreLink, { isBlock: props.isCompact, allDayDate: props.date, segs: props.segs, hiddenSegs: props.hiddenSegs, alignElRef: this.rootElRef, alignParentTop: props.showDayNumber ? '[role=row]' : '.fc-view', dateSpanProps: props.dateSpanProps, dateProfile: props.dateProfile, eventSelection: props.eventSelection, eventDrag: props.eventDrag, eventResize: props.eventResize, todayRange: props.todayRange }))))));
310
224
  }
311
225
  componentDidMount() {
312
- const innerEl = this.innerElRef.current; // TODO: make dynamic with useEffect
313
- const headerWrapEl = this.headerWrapElRef.current; // "
314
- // TODO: only attach this if refs props present
315
- this.detachInnerHeight = internal$1.watchHeight(innerEl, (height) => {
316
- internal$1.setRef(this.props.innerHeightRef, height);
317
- });
318
- this.detachHeaderHeight = internal$1.watchHeight(headerWrapEl, (height) => {
319
- internal$1.setRef(this.props.headerHeightRef, height);
226
+ const bodyEl = this.bodyElRef.current;
227
+ // we want to fire on ANY size change, because we do more advanced stuff
228
+ this.disconnectBodyHeight = internal$1.watchSize(bodyEl, (_bodyWidth, bodyHeight) => {
229
+ const { props } = this;
230
+ const mainRect = bodyEl.getBoundingClientRect();
231
+ const rootRect = this.rootElRef.current.getBoundingClientRect();
232
+ const headerHeight = mainRect.top - rootRect.top;
233
+ if (!internal$1.isDimsEqual(this.headerHeight, headerHeight)) {
234
+ this.headerHeight = headerHeight;
235
+ internal$1.setRef(props.headerHeightRef, headerHeight);
236
+ }
237
+ if (props.fgLiquidHeight) {
238
+ internal$1.setRef(props.mainHeightRef, bodyHeight);
239
+ }
320
240
  });
321
241
  }
322
242
  componentWillUnmount() {
323
- this.detachInnerHeight();
324
- this.detachHeaderHeight();
325
- internal$1.setRef(this.props.innerHeightRef, null);
326
- internal$1.setRef(this.props.headerHeightRef, null);
243
+ this.disconnectBodyHeight();
244
+ const { props } = this;
245
+ internal$1.setRef(props.headerHeightRef, null);
246
+ internal$1.setRef(props.mainHeightRef, null);
327
247
  }
328
248
  }
329
249
  // Utils
@@ -347,121 +267,232 @@ FullCalendar.DayGrid = (function (exports, core, internal$1, preact) {
347
267
  (dateEnv.getDay(date) === 1 && date.valueOf() < currentEnd.valueOf()));
348
268
  }
349
269
 
270
+ function computeFgSegVerticals(segs, segHeightMap, cells, maxHeight, strictOrder, allowSlicing = true, dayMaxEvents, dayMaxEventRows) {
271
+ let maxCoord;
272
+ let maxDepth;
273
+ let hiddenConsumes;
274
+ if (dayMaxEvents === true || dayMaxEventRows === true) {
275
+ maxCoord = maxHeight;
276
+ hiddenConsumes = true;
277
+ }
278
+ else if (typeof dayMaxEvents === 'number') {
279
+ maxDepth = dayMaxEvents;
280
+ hiddenConsumes = false;
281
+ }
282
+ else if (typeof dayMaxEventRows === 'number') {
283
+ maxDepth = dayMaxEventRows;
284
+ hiddenConsumes = true;
285
+ }
286
+ // NOTE: visibleSegsMap and hiddenSegMap map NEVER overlap for a given event
287
+ // once a seg has a height, the combined potentially-sliced segs will comprise the entire span of the seg
288
+ // if a seg does not have a height yet, it won't be inserted into either visibleSegsMap/hiddenSegMap
289
+ const visibleSegMap = new Map();
290
+ const hiddenSegMap = new Map();
291
+ const segTops = new Map();
292
+ const isSlicedMap = new Map();
293
+ let hierarchy = new internal$1.SegHierarchy(segs, (seg) => segHeightMap.get(getEventPartKey(seg)), strictOrder, maxCoord, maxDepth, hiddenConsumes, allowSlicing);
294
+ hierarchy.traverseSegs((seg, segTop) => {
295
+ addToSegMap(visibleSegMap, seg);
296
+ segTops.set(getEventPartKey(seg), segTop);
297
+ if (seg.isSlice) {
298
+ isSlicedMap.set(seg.eventRange, true);
299
+ }
300
+ });
301
+ for (const hiddenSeg of hierarchy.hiddenSegs) {
302
+ addToSegMap(hiddenSegMap, hiddenSeg); // hidden main segs
303
+ }
304
+ // recompute tops while considering slices
305
+ // portions of these slices might be added to hiddenSegMap
306
+ if (isSlicedMap.size) {
307
+ segTops.clear();
308
+ hierarchy = new internal$1.SegHierarchy(compileSegMap(segs, visibleSegMap), (seg) => segHeightMap.get(getEventPartKey(seg)), strictOrder, maxCoord, maxDepth, hiddenConsumes);
309
+ hierarchy.traverseSegs((seg, segTop) => {
310
+ segTops.set(getEventPartKey(seg), segTop); // newly-hidden main segs and slices
311
+ });
312
+ for (const hiddenSeg of hierarchy.hiddenSegs) {
313
+ addToSegMap(hiddenSegMap, hiddenSeg);
314
+ }
315
+ }
316
+ const segsByCol = [];
317
+ const hiddenSegsByCol = [];
318
+ const renderableSegsByCol = [];
319
+ const heightsByCol = [];
320
+ for (let col = 0; col < cells.length; col++) {
321
+ segsByCol.push([]);
322
+ hiddenSegsByCol.push([]);
323
+ renderableSegsByCol.push([]);
324
+ heightsByCol.push(0);
325
+ }
326
+ for (const seg of segs) {
327
+ const { eventRange } = seg;
328
+ const visibleSegs = visibleSegMap.get(eventRange) || [];
329
+ const hiddenSegs = hiddenSegMap.get(eventRange) || [];
330
+ const isSliced = isSlicedMap.get(eventRange) || false;
331
+ // add orig to renderable
332
+ renderableSegsByCol[seg.start].push(seg);
333
+ // add slices to renderable
334
+ if (isSliced) {
335
+ for (const visibleSeg of visibleSegs) {
336
+ renderableSegsByCol[visibleSeg.start].push(visibleSeg);
337
+ }
338
+ }
339
+ // accumulate segsByCol/heightsByCol for visible segs
340
+ for (const visibleSeg of visibleSegs) {
341
+ for (let col = visibleSeg.start; col < visibleSeg.end; col++) {
342
+ const slice = sliceSegForCol(visibleSeg, col);
343
+ segsByCol[col].push(slice);
344
+ }
345
+ const segKey = getEventPartKey(visibleSeg);
346
+ const segTop = segTops.get(segKey);
347
+ if (segTop != null) { // positioned?
348
+ const segHeight = segHeightMap.get(segKey);
349
+ for (let col = visibleSeg.start; col < visibleSeg.end; col++) {
350
+ heightsByCol[col] = Math.max(heightsByCol[col], segTop + segHeight);
351
+ }
352
+ }
353
+ }
354
+ // accumulate segsByCol/hiddenSegsByCol for hidden segs
355
+ for (const hiddenSeg of hiddenSegs) {
356
+ for (let col = hiddenSeg.start; col < hiddenSeg.end; col++) {
357
+ const slice = sliceSegForCol(hiddenSeg, col);
358
+ segsByCol[col].push(slice);
359
+ hiddenSegsByCol[col].push(slice);
360
+ }
361
+ }
362
+ }
363
+ return [
364
+ segsByCol,
365
+ hiddenSegsByCol,
366
+ renderableSegsByCol,
367
+ segTops,
368
+ heightsByCol,
369
+ ];
370
+ }
371
+ // Utils
372
+ // -------------------------------------------------------------------------------------------------
373
+ function addToSegMap(map, seg) {
374
+ let list = map.get(seg.eventRange);
375
+ if (!list) {
376
+ map.set(seg.eventRange, list = []);
377
+ }
378
+ list.push(seg);
379
+ }
350
380
  /*
351
- Unique per-START-column, good for cataloging by top
381
+ Ensures relative order of DayRowEventRange stays consistent with segs
352
382
  */
353
- function getSegStartId(seg) {
354
- return seg.eventRange.instance.instanceId + ':' + seg.firstCol;
383
+ function compileSegMap(segs, segMap) {
384
+ const res = [];
385
+ for (const seg of segs) {
386
+ res.push(...(segMap.get(seg.eventRange) || []));
387
+ }
388
+ return res;
355
389
  }
390
+
356
391
  /*
357
- Unique per-START-and-END-column, good for cataloging by width/height
392
+ TODO: move this so @fullcalendar/daygrid
358
393
  */
359
- function getSegSpanId(seg) {
360
- return getSegStartId(seg) + ':' + seg.lastCol;
394
+ function buildDayTableModel(dateProfile, dateProfileGenerator) {
395
+ let daySeries = new internal$1.DaySeriesModel(dateProfile.renderRange, dateProfileGenerator);
396
+ return new internal$1.DayTableModel(daySeries, /year|month|week/.test(dateProfile.currentRangeUnit));
361
397
  }
362
- function computeFgSegVerticals(segs, segHeightMap, // keyed by segSpanId
363
- cells, topOrigin, maxHeight, strictOrder, dayMaxEvents, dayMaxEventRows) {
364
- // initialize column-based arrays
365
- const colCnt = cells.length;
366
- const hiddenSegsByCol = [];
367
- const heightsByCol = [];
368
- for (let col = 0; col < colCnt; col++) {
369
- hiddenSegsByCol.push([]);
370
- heightsByCol.push(0);
371
- }
372
- // create entries to be given to DayGridSegHierarchy
373
- const segEntries = segs.map((seg, index) => ({
374
- index: index,
375
- seg,
376
- span: {
377
- start: seg.firstCol,
378
- end: seg.lastCol + 1,
379
- },
380
- }));
381
- // configure hierarchy position-generator
382
- let hierarchy = new DayGridSegHierarchy((segEntry) => (segHeightMap.get(getSegSpanId(segs[segEntry.index]))));
383
- hierarchy.allowReslicing = false;
384
- hierarchy.strictOrder = strictOrder;
385
- if (dayMaxEvents === true || dayMaxEventRows === true) {
386
- hierarchy.maxCoord = maxHeight;
387
- hierarchy.hiddenConsumes = true;
398
+ function computeColWidth(colCnt, colMinWidth, viewportWidth) {
399
+ if (viewportWidth == null) {
400
+ return [undefined, undefined];
388
401
  }
389
- else if (typeof dayMaxEvents === 'number') {
390
- hierarchy.maxStackCnt = dayMaxEvents;
402
+ const colTempWidth = viewportWidth / colCnt;
403
+ if (colTempWidth < colMinWidth) {
404
+ return [colMinWidth * colCnt, colMinWidth];
391
405
  }
392
- else if (typeof dayMaxEventRows === 'number') {
393
- hierarchy.maxStackCnt = dayMaxEventRows;
394
- hierarchy.hiddenConsumes = true;
395
- }
396
- // compile segTops & heightsByCol
397
- const hiddenSegEntries = hierarchy.addSegs(segEntries);
398
- const segRects = hierarchy.toRects();
399
- const segTops = {};
400
- for (const segRect of segRects) {
401
- const seg = segs[segRect.index];
402
- segTops[getSegStartId(seg)] = topOrigin + segRect.levelCoord;
403
- let { start: col, end: endCol } = segRect.span;
404
- for (; col < endCol; col++) {
405
- heightsByCol[col] = Math.max(heightsByCol[col], segRect.levelCoord + segRect.thickness);
406
+ return [viewportWidth, undefined];
407
+ }
408
+ // Positioning
409
+ // -------------------------------------------------------------------------------------------------
410
+ function computeTopFromDate(date, cellRows, rowHeightMap, adjust = 0) {
411
+ let top = 0;
412
+ for (const cells of cellRows) {
413
+ const start = cells[0].date;
414
+ const end = cells[cells.length - 1].date;
415
+ const key = start.toISOString();
416
+ if (date >= start && date <= end) {
417
+ return top;
418
+ }
419
+ const rowHeight = rowHeightMap.get(key);
420
+ if (rowHeight == null) {
421
+ return; // denote unknown
406
422
  }
423
+ top += rowHeight + adjust;
424
+ }
425
+ return top;
426
+ }
427
+ /*
428
+ FYI, `width` is not dependable for aligning completely to farside
429
+ */
430
+ function computeHorizontalsFromSeg(seg, colWidth, colCnt, isRtl) {
431
+ let fromStart;
432
+ let fromEnd;
433
+ if (colWidth != null) {
434
+ fromStart = seg.start * colWidth;
435
+ fromEnd = (colCnt - seg.end) * colWidth;
436
+ }
437
+ else {
438
+ const colWidthFrac = 1 / colCnt;
439
+ fromStart = internal$1.fracToCssDim(seg.start * colWidthFrac);
440
+ fromEnd = internal$1.fracToCssDim(1 - seg.end * colWidthFrac);
441
+ }
442
+ if (isRtl) {
443
+ return { right: fromStart, left: fromEnd };
444
+ }
445
+ else {
446
+ return { left: fromStart, right: fromEnd };
407
447
  }
408
- // compile # of invisible segs per-column
409
- for (const hiddenSegEntry of hiddenSegEntries) {
410
- const { span } = hiddenSegEntry;
411
- const hiddenSeg = segs[hiddenSegEntry.index];
412
- for (let col = span.start; col < span.end; col++) {
413
- hiddenSegsByCol[col].push(hiddenSeg);
448
+ }
449
+ function computeColFromPosition(positionLeft, elWidth, colWidth, colCnt, isRtl) {
450
+ const realColWidth = colWidth != null ? colWidth : elWidth / colCnt;
451
+ const colFromLeft = Math.floor(positionLeft / realColWidth);
452
+ const col = isRtl ? (colCnt - colFromLeft - 1) : colFromLeft;
453
+ const left = colFromLeft * realColWidth;
454
+ const right = left + realColWidth;
455
+ return { col, left, right };
456
+ }
457
+ function computeRowFromPosition(positionTop, cellRows, rowHeightMap) {
458
+ let row = 0;
459
+ let top = 0;
460
+ let bottom = 0;
461
+ for (const cells of cellRows) {
462
+ const key = cells[0].key;
463
+ top = bottom;
464
+ bottom = top + rowHeightMap.get(key);
465
+ if (positionTop < bottom) {
466
+ break;
414
467
  }
468
+ row++;
415
469
  }
416
- return [segTops, heightsByCol, hiddenSegsByCol];
470
+ return { row, top, bottom };
417
471
  }
418
- // DayGridSegHierarchy
472
+ // Hit Element
419
473
  // -------------------------------------------------------------------------------------------------
420
- class DayGridSegHierarchy extends internal$1.SegHierarchy {
421
- constructor() {
422
- super(...arguments);
423
- // config
424
- this.hiddenConsumes = false;
425
- // allows us to keep hidden entries in the hierarchy so they take up space
426
- this.forceHidden = {};
427
- }
428
- addSegs(segInputs) {
429
- const hiddenSegs = super.addSegs(segInputs);
430
- const { entriesByLevel } = this;
431
- const excludeHidden = (entry) => !this.forceHidden[internal$1.buildEntryKey(entry)];
432
- // remove the forced-hidden segs
433
- for (let level = 0; level < entriesByLevel.length; level += 1) {
434
- entriesByLevel[level] = entriesByLevel[level].filter(excludeHidden);
435
- }
436
- return hiddenSegs;
437
- }
438
- handleInvalidInsertion(insertion, entry, hiddenEntries) {
439
- const { entriesByLevel, forceHidden } = this;
440
- const { touchingEntry, touchingLevel, touchingLateral } = insertion;
441
- // the entry that the new insertion is touching must be hidden
442
- if (this.hiddenConsumes && touchingEntry) {
443
- const touchingEntryId = internal$1.buildEntryKey(touchingEntry);
444
- if (!forceHidden[touchingEntryId]) {
445
- if (this.allowReslicing) {
446
- // split up the touchingEntry, reinsert it
447
- const hiddenEntry = Object.assign(Object.assign({}, touchingEntry), { span: internal$1.intersectSpans(touchingEntry.span, entry.span) });
448
- // reinsert the area that turned into a "more" link (so no other entries try to
449
- // occupy the space) but mark it forced-hidden
450
- const hiddenEntryId = internal$1.buildEntryKey(hiddenEntry);
451
- forceHidden[hiddenEntryId] = true;
452
- entriesByLevel[touchingLevel][touchingLateral] = hiddenEntry;
453
- hiddenEntries.push(hiddenEntry);
454
- this.splitEntry(touchingEntry, entry, hiddenEntries);
455
- }
456
- else {
457
- forceHidden[touchingEntryId] = true;
458
- hiddenEntries.push(touchingEntry);
459
- }
460
- }
461
- }
462
- // will try to reslice...
463
- super.handleInvalidInsertion(insertion, entry, hiddenEntries);
474
+ function getRowEl(rootEl, row) {
475
+ return rootEl.querySelectorAll(':scope > [role=row]')[row];
476
+ }
477
+ function getCellEl(rowEl, col) {
478
+ return rowEl.querySelectorAll(':scope > [role=gridcell]')[col];
479
+ }
480
+ // Header Formatting
481
+ // -------------------------------------------------------------------------------------------------
482
+ function createDayHeaderFormatter(explicitFormat, datesRepDistinctDays, dateCnt) {
483
+ return explicitFormat || computeFallbackHeaderFormat(datesRepDistinctDays, dateCnt);
484
+ }
485
+ // Computes a default column header formatting string if `colFormat` is not explicitly defined
486
+ function computeFallbackHeaderFormat(datesRepDistinctDays, dayCnt) {
487
+ // if more than one week row, or if there are a lot of columns with not much space,
488
+ // put just the day numbers will be in each cell
489
+ if (!datesRepDistinctDays || dayCnt > 10) {
490
+ return internal$1.createFormatter({ weekday: 'short' }); // "Sat"
491
+ }
492
+ if (dayCnt > 1) {
493
+ return internal$1.createFormatter({ weekday: 'short', month: 'numeric', day: 'numeric', omitCommas: true }); // "Sat 11/12"
464
494
  }
495
+ return internal$1.createFormatter({ weekday: 'long' }); // "Saturday"
465
496
  }
466
497
 
467
498
  class DayGridEventHarness extends preact.Component {
@@ -472,128 +503,96 @@ FullCalendar.DayGrid = (function (exports, core, internal$1, preact) {
472
503
  }
473
504
  render() {
474
505
  const { props } = this;
475
- return (preact.createElement("div", { className: "fc-abs", style: props.style, ref: this.rootElRef }, props.children));
506
+ return (preact.createElement("div", { className: internal$1.joinClassNames(props.className, 'fc-abs'), style: props.style, ref: this.rootElRef }, props.children));
476
507
  }
477
508
  componentDidMount() {
478
509
  const rootEl = this.rootElRef.current; // TODO: make dynamic with useEffect
479
- this.detachHeight = internal$1.watchHeight(rootEl, (height) => {
510
+ this.disconnectHeight = internal$1.watchHeight(rootEl, (height) => {
480
511
  internal$1.setRef(this.props.heightRef, height);
481
512
  });
482
513
  }
483
514
  componentWillUnmount() {
484
- this.detachHeight();
515
+ this.disconnectHeight();
516
+ internal$1.setRef(this.props.heightRef, null);
485
517
  }
486
518
  }
487
519
 
488
520
  const DEFAULT_WEEK_NUM_FORMAT = internal$1.createFormatter({ week: 'narrow' });
489
- const COMPACT_CELL_WIDTH = 80;
490
521
  class DayGridRow extends internal$1.BaseComponent {
491
522
  constructor() {
492
523
  super(...arguments);
493
- this.cellInnerHeightRefMap = new internal$1.RefMap(() => {
494
- internal$1.afterSize(this.handleInnerHeights);
524
+ this.headerHeightRefMap = new internal$1.RefMap(() => {
525
+ internal$1.afterSize(this.handleSegPositioning);
495
526
  });
496
- this.cellHeaderHeightRefMap = new internal$1.RefMap(() => {
497
- internal$1.afterSize(this.handleHeaderHeights);
527
+ this.mainHeightRefMap = new internal$1.RefMap(() => {
528
+ const fgLiquidHeight = this.props.dayMaxEvents === true || this.props.dayMaxEventRows === true;
529
+ if (fgLiquidHeight) {
530
+ internal$1.afterSize(this.handleSegPositioning);
531
+ }
498
532
  });
499
533
  this.segHeightRefMap = new internal$1.RefMap(() => {
500
- internal$1.afterSize(this.handleSegHeights);
534
+ internal$1.afterSize(this.handleSegPositioning);
501
535
  });
502
536
  this.handleRootEl = (rootEl) => {
503
537
  this.rootEl = rootEl;
504
538
  internal$1.setRef(this.props.rootElRef, rootEl);
505
539
  };
506
- // Sizing
507
- // -----------------------------------------------------------------------------------------------
508
- this.handleHeaderHeights = () => {
509
- const cellHeaderHeightMap = this.cellHeaderHeightRefMap.current;
510
- let max = 0;
511
- for (const height of cellHeaderHeightMap.values()) {
512
- max = Math.max(max, height);
513
- }
514
- if (this.state.headerHeight !== max) {
515
- this.setState({ headerHeight: max });
516
- }
517
- };
518
- this.handleInnerHeights = () => {
519
- const { props } = this;
520
- const fgLiquidHeight = props.dayMaxEvents === true || props.dayMaxEventRows === true;
521
- const cellInnerHeightMap = this.cellInnerHeightRefMap.current;
522
- let max = 0;
523
- for (const height of cellInnerHeightMap.values()) {
524
- max = Math.max(max, height);
525
- }
526
- if (fgLiquidHeight) {
527
- if (this.state.innerHeight !== max) {
528
- this.setState({ innerHeight: max }); // will trigger event rerender
529
- }
530
- }
531
- else {
532
- internal$1.setRef(props.innerHeightRef, max);
533
- }
534
- };
535
- this.handleSegHeights = () => {
536
- this.setState({ segHeightRev: this.segHeightRefMap.rev }); // will trigger event rerender
540
+ this.handleSegPositioning = () => {
541
+ this.forceUpdate();
537
542
  };
538
543
  }
539
544
  render() {
540
- const { props, state, context, cellInnerHeightRefMap, cellHeaderHeightRefMap } = this;
545
+ const { props, context, headerHeightRefMap, mainHeightRefMap } = this;
541
546
  const { cells } = props;
542
547
  const { options } = context;
543
548
  const weekDate = props.cells[0].date;
544
- const colCnt = props.cells.length;
545
549
  const fgLiquidHeight = props.dayMaxEvents === true || props.dayMaxEventRows === true;
546
550
  // TODO: memoize? sort all types of segs?
547
551
  const fgEventSegs = internal$1.sortEventSegs(props.fgEventSegs, options.eventOrder);
548
552
  // TODO: memoize?
549
- const fgEventSegsByCol = splitSegsByCol(fgEventSegs, colCnt);
550
- const bgEventSegsByCol = splitSegsByCol(props.bgEventSegs, colCnt);
551
- const businessHoursByCol = splitSegsByCol(props.businessHourSegs, colCnt);
552
- const highlightSegsByCol = splitSegsByCol(this.getHighlightSegs(), colCnt); // TODO: doesn't need standins
553
- const mirrorSegsByCol = splitSegsByCol(this.getMirrorSegs(), colCnt); // TODO: doesn't need standins
554
- // TODO: memoize?
555
- const [segTops, heightsByCol, hiddenSegsByCol] = computeFgSegVerticals(fgEventSegs, this.segHeightRefMap.current, cells, state.headerHeight, (fgLiquidHeight && state.innerHeight != null && state.headerHeight != null)
556
- ? state.innerHeight - state.headerHeight
557
- : undefined, options.eventOrderStrict, props.dayMaxEvents, props.dayMaxEventRows);
553
+ const [maxMainTop, minMainHeight] = this.computeFgDims(); // uses headerHeightRefMap/mainHeightRefMap
554
+ const [segsByCol, hiddenSegsByCol, renderableSegsByCol, segTops, simpleHeightsByCol] = computeFgSegVerticals(fgEventSegs, this.segHeightRefMap.current, cells, fgLiquidHeight ? minMainHeight : undefined, // if not defined in first run, will unlimited!?
555
+ options.eventOrderStrict, options.eventSlicing, props.dayMaxEvents, props.dayMaxEventRows);
556
+ const heightsByCol = [];
557
+ if (maxMainTop != null) {
558
+ let col = 0;
559
+ for (const cell of cells) { // uses headerHeightRefMap/maxMainTop/simpleHeightsByCol
560
+ const cellHeaderHeight = headerHeightRefMap.current.get(cell.key);
561
+ const extraFgHeight = maxMainTop - cellHeaderHeight;
562
+ heightsByCol.push(simpleHeightsByCol[col++] + extraFgHeight);
563
+ }
564
+ }
565
+ const highlightSegs = this.getHighlightSegs();
566
+ const mirrorSegs = this.getMirrorSegs();
558
567
  const forcedInvisibleMap = // TODO: more convenient/DRY
559
568
  (props.eventDrag && props.eventDrag.affectedInstances) ||
560
569
  (props.eventResize && props.eventResize.affectedInstances) ||
561
570
  {};
562
- return (preact.createElement("div", { role: props.cellGroup ? undefined : 'row', className: [
563
- 'fc-daygrid-row',
564
- props.forceVSpacing
565
- ? 'fc-daygrid-row-spacious'
566
- : props.compact
567
- ? 'fc-daygrid-row-compact'
568
- : '',
569
- props.cellGroup ? 'fc-flex-row' : 'fc-row',
570
- 'fc-rel',
571
- props.className || '',
572
- ].join(' '), style: {
571
+ return (preact.createElement("div", { role: 'row' // TODO: audit this for all scenarios
572
+ , className: internal$1.joinClassNames('fc-flex-row fc-rel', props.className), style: {
573
573
  minHeight: props.minHeight,
574
574
  }, ref: this.handleRootEl },
575
- props.cells.map((cell, col) => {
576
- const normalFgNodes = this.renderFgSegs(fgEventSegsByCol[col], segTops, props.todayRange, forcedInvisibleMap);
577
- const mirrorFgNodes = this.renderFgSegs(mirrorSegsByCol[col], segTops, props.todayRange, {}, // forcedInvisibleMap
578
- Boolean(props.eventDrag), Boolean(props.eventResize), false);
579
- return (preact.createElement(DayGridCell, { key: cell.key, dateProfile: props.dateProfile, todayRange: props.todayRange, date: cell.date, showDayNumber: props.showDayNumbers,
575
+ this.renderFillSegs(props.businessHourSegs, 'non-business'),
576
+ this.renderFillSegs(props.bgEventSegs, 'bg-event'),
577
+ this.renderFillSegs(highlightSegs, 'highlight'),
578
+ preact.createElement("div", { className: 'fc-flex-row fc-liquid fc-rel' }, props.cells.map((cell, col) => {
579
+ const normalFgNodes = this.renderFgSegs(maxMainTop, renderableSegsByCol[col], segTops, props.todayRange, forcedInvisibleMap);
580
+ return (preact.createElement(DayGridCell, { key: cell.key, dateProfile: props.dateProfile, todayRange: props.todayRange, date: cell.date, showDayNumber: props.showDayNumbers, isCompact: props.isCompact, isTall: props.isTall, borderStart: Boolean(col),
580
581
  // content
581
- segs: fgEventSegsByCol[col], hiddenSegs: hiddenSegsByCol[col], fgLiquidHeight: fgLiquidHeight, fg: (preact.createElement(preact.Fragment, null,
582
- preact.createElement(preact.Fragment, null, normalFgNodes),
583
- preact.createElement(preact.Fragment, null, mirrorFgNodes))), bg: (preact.createElement(preact.Fragment, null,
584
- this.renderFillSegs(highlightSegsByCol[col], 'highlight'),
585
- this.renderFillSegs(businessHoursByCol[col], 'non-business'),
586
- this.renderFillSegs(bgEventSegsByCol[col], 'bg-event'))), eventDrag: props.eventDrag, eventResize: props.eventResize, eventSelection: props.eventSelection,
582
+ segs: segsByCol[col], hiddenSegs: hiddenSegsByCol[col], fgLiquidHeight: fgLiquidHeight, fg: (preact.createElement(preact.Fragment, null, normalFgNodes)), eventDrag: props.eventDrag, eventResize: props.eventResize, eventSelection: props.eventSelection,
587
583
  // render hooks
588
- extraRenderProps: cell.extraRenderProps, extraDateSpan: cell.extraDateSpan, extraDataAttrs: cell.extraDataAttrs, extraClassNames: cell.extraClassNames,
584
+ renderProps: cell.renderProps, dateSpanProps: cell.dateSpanProps, attrs: cell.attrs, className: cell.className,
589
585
  // dimensions
590
586
  fgHeight: heightsByCol[col], width: props.colWidth,
591
587
  // refs
592
- innerHeightRef: cellInnerHeightRefMap.createRef(cell.key), headerHeightRef: cellHeaderHeightRefMap.createRef(cell.key) }));
593
- }),
594
- props.showWeekNumbers && (preact.createElement(internal$1.WeekNumberContainer, { elTag: "a", elClasses: ['fc-daygrid-week-number'], elAttrs: internal$1.buildNavLinkAttrs(context, weekDate, 'week'), date: weekDate, defaultFormat: DEFAULT_WEEK_NUM_FORMAT }))));
595
- }
596
- renderFgSegs(segs, segTops, todayRange, forcedInvisibleMap, isDragging, isResizing, isDateSelecting) {
588
+ headerHeightRef: headerHeightRefMap.createRef(cell.key), mainHeightRef: mainHeightRefMap.createRef(cell.key) }));
589
+ })),
590
+ props.showWeekNumbers && (preact.createElement(internal$1.WeekNumberContainer, { tag: "a", attrs: internal$1.buildNavLinkAttrs(context, weekDate, 'week'), className: 'fc-daygrid-week-number', date: weekDate, defaultFormat: DEFAULT_WEEK_NUM_FORMAT })),
591
+ this.renderFgSegs(maxMainTop, mirrorSegs, segTops, props.todayRange, {}, // forcedInvisibleMap
592
+ Boolean(props.eventDrag), Boolean(props.eventResize), false)));
593
+ }
594
+ renderFgSegs(headerHeight, segs, segTops, todayRange, forcedInvisibleMap, isDragging, isResizing, isDateSelecting) {
595
+ var _a;
597
596
  const { props, context, segHeightRefMap } = this;
598
597
  const { isRtl } = context;
599
598
  const { colWidth, eventSelection } = props;
@@ -602,29 +601,26 @@ FullCalendar.DayGrid = (function (exports, core, internal$1, preact) {
602
601
  const isMirror = isDragging || isResizing || isDateSelecting;
603
602
  const nodes = [];
604
603
  for (const seg of segs) {
605
- const { left, right, width } = computeHorizontalsFromSeg(seg, colWidth, colCnt, isRtl);
606
- // TODO: optimize ID creation? all related
607
- const { instanceId } = seg.eventRange.instance;
608
- const segSpanId = getSegSpanId(seg);
609
- const segStartId = getSegStartId(seg);
610
- const top = segTops[segStartId];
611
- const isVisible = !seg.isStandin &&
612
- top != null &&
613
- !forcedInvisibleMap[instanceId];
614
- /*
615
- TODO: is this comment still relevant? vvvvvvvv
616
- known bug: events that are force to be list-item but span multiple days still take up space in later columns
617
- todo: in print view, for multi-day events, don't display title within non-start/end segs
618
- */
619
- nodes.push(preact.createElement(DayGridEventHarness, { key: segSpanId, style: {
620
- visibility: isVisible ? '' : 'hidden',
604
+ const key = getEventPartKey(seg);
605
+ const { standinFor, eventRange } = seg;
606
+ const { instanceId } = eventRange.instance;
607
+ if (standinFor) {
608
+ continue;
609
+ }
610
+ const { left, right } = computeHorizontalsFromSeg(seg, colWidth, colCnt, isRtl);
611
+ const localTop = (_a = segTops.get(standinFor ? getEventPartKey(standinFor) : key)) !== null && _a !== void 0 ? _a : (isMirror ? 0 : undefined);
612
+ const top = headerHeight != null && localTop != null
613
+ ? headerHeight + localTop
614
+ : undefined;
615
+ const isInvisible = standinFor || forcedInvisibleMap[instanceId] || top == null;
616
+ nodes.push(preact.createElement(DayGridEventHarness, { key: key, className: seg.start ? 'fc-border-transparent fc-border-s' : '', style: {
617
+ visibility: isInvisible ? 'hidden' : '',
621
618
  top,
622
619
  left,
623
620
  right,
624
- width,
625
- }, heightRef: (isMirror || seg.isStandin)
626
- ? null
627
- : segHeightRefMap.createRef(segSpanId) }, hasListItemDisplay(seg) ? (preact.createElement(DayGridListEvent, Object.assign({ seg: seg, isDragging: isDragging, isSelected: instanceId === eventSelection, defaultDisplayEventEnd: defaultDisplayEventEnd }, internal$1.getSegMeta(seg, todayRange)))) : (preact.createElement(DayGridBlockEvent, Object.assign({ seg: seg, isDragging: isDragging, isResizing: isResizing, isDateSelecting: isDateSelecting, isSelected: instanceId === eventSelection, defaultDisplayEventEnd: defaultDisplayEventEnd }, internal$1.getSegMeta(seg, todayRange))))));
621
+ }, heightRef: (!standinFor && !isMirror)
622
+ ? segHeightRefMap.createRef(key)
623
+ : null }, hasListItemDisplay(seg) ? (preact.createElement(DayGridListEvent, Object.assign({ eventRange: eventRange, isStart: seg.isStart, isEnd: seg.isEnd, isDragging: isDragging, isSelected: instanceId === eventSelection, defaultDisplayEventEnd: defaultDisplayEventEnd }, internal$1.getEventRangeMeta(eventRange, todayRange)))) : (preact.createElement(DayGridBlockEvent, Object.assign({ eventRange: eventRange, isStart: seg.isStart, isEnd: seg.isEnd, isDragging: isDragging, isResizing: isResizing, isDateSelecting: isDateSelecting, isSelected: instanceId === eventSelection, defaultDisplayEventEnd: defaultDisplayEventEnd }, internal$1.getEventRangeMeta(eventRange, todayRange))))));
628
624
  }
629
625
  return nodes;
630
626
  }
@@ -635,18 +631,17 @@ FullCalendar.DayGrid = (function (exports, core, internal$1, preact) {
635
631
  const colCnt = props.cells.length;
636
632
  const nodes = [];
637
633
  for (const seg of segs) {
638
- const { left, right, width } = computeHorizontalsFromSeg(seg, colWidth, colCnt, isRtl);
639
- const isVisible = !seg.isStandin;
640
- nodes.push(preact.createElement("div", { key: internal$1.buildEventRangeKey(seg.eventRange), className: "fc-fill-y", style: {
634
+ const key = internal$1.buildEventRangeKey(seg.eventRange); // TODO: use different type of key than fg!?
635
+ const { left, right } = computeHorizontalsFromSeg(seg, colWidth, colCnt, isRtl);
636
+ const isVisible = !seg.standinFor;
637
+ nodes.push(preact.createElement("div", { key: key, className: "fc-fill-y", style: {
641
638
  visibility: isVisible ? '' : 'hidden',
642
639
  left,
643
640
  right,
644
- width,
645
641
  } }, fillType === 'bg-event' ?
646
- preact.createElement(internal$1.BgEvent, Object.assign({ seg: seg }, internal$1.getSegMeta(seg, todayRange))) :
647
- internal$1.renderFill(fillType)));
642
+ preact.createElement(internal$1.BgEvent, Object.assign({ eventRange: seg.eventRange, isStart: seg.isStart, isEnd: seg.isEnd }, internal$1.getEventRangeMeta(seg.eventRange, todayRange))) : (internal$1.renderFill(fillType))));
648
643
  }
649
- return preact.createElement(preact.Fragment, {}, ...nodes);
644
+ return preact.createElement(preact.Fragment, {}, ...nodes); // TODO: shouldn't this be an array, so keyed?
650
645
  }
651
646
  // Sizing
652
647
  // -----------------------------------------------------------------------------------------------
@@ -659,9 +654,36 @@ FullCalendar.DayGrid = (function (exports, core, internal$1, preact) {
659
654
  componentWillUnmount() {
660
655
  this.disconnectHeight();
661
656
  internal$1.setRef(this.props.heightRef, null);
662
- internal$1.setRef(this.props.innerHeightRef, null);
663
657
  }
664
- // Utils
658
+ computeFgDims() {
659
+ const { cells } = this.props;
660
+ const headerHeightMap = this.headerHeightRefMap.current;
661
+ const mainHeightMap = this.mainHeightRefMap.current;
662
+ let maxMainTop;
663
+ let minMainBottom;
664
+ for (const cell of cells) {
665
+ const mainTop = headerHeightMap.get(cell.key);
666
+ const mainHeight = mainHeightMap.get(cell.key);
667
+ if (mainTop != null) {
668
+ if (maxMainTop === undefined || mainTop > maxMainTop) {
669
+ maxMainTop = mainTop;
670
+ }
671
+ if (mainHeight != null) {
672
+ const mainBottom = mainTop + mainHeight;
673
+ if (minMainBottom === undefined || mainBottom < minMainBottom) {
674
+ minMainBottom = mainBottom;
675
+ }
676
+ }
677
+ }
678
+ }
679
+ return [
680
+ maxMainTop,
681
+ minMainBottom != null && maxMainTop != null
682
+ ? minMainBottom - maxMainTop
683
+ : undefined,
684
+ ];
685
+ }
686
+ // Internal Utils
665
687
  // -----------------------------------------------------------------------------------------------
666
688
  getMirrorSegs() {
667
689
  let { props } = this;
@@ -714,7 +736,7 @@ FullCalendar.DayGrid = (function (exports, core, internal$1, preact) {
714
736
  };
715
737
  }
716
738
  render() {
717
- let { props, state, context, rowHeightRefMap } = this;
739
+ let { props, context, rowHeightRefMap } = this;
718
740
  let { options } = context;
719
741
  let rowCnt = props.cellRows.length;
720
742
  let fgEventSegsByRow = this.splitFgEventSegs(props.fgEventSegs, rowCnt);
@@ -723,31 +745,31 @@ FullCalendar.DayGrid = (function (exports, core, internal$1, preact) {
723
745
  let dateSelectionSegsByRow = this.splitDateSelectionSegs(props.dateSelectionSegs, rowCnt);
724
746
  let eventDragByRow = this.splitEventDrag(props.eventDrag, rowCnt);
725
747
  let eventResizeByRow = this.splitEventResize(props.eventResize, rowCnt);
726
- // whether the ROW should expand in height
727
- // (not to be confused with whether the fg events within the row should be molded by height of row)
728
748
  let isHeightAuto = internal$1.getIsHeightAuto(options);
729
- // maintain at least aspectRatio for cells?
730
- let rowMinHeight = (state.width != null && (rowCnt >= 7 || // TODO: better way to infer if across single-month boundary
731
- isHeightAuto)) ? state.width / context.options.aspectRatio / 6 // okay to hardcode 6 (weeks) ?
732
- : null;
733
- return (preact.createElement("div", { className: 'fc-grow fc-flex-column', style: { width: props.width }, ref: this.handleRootEl }, props.cellRows.map((cells, row) => (preact.createElement(DayGridRow, { key: cells[0].key, dateProfile: props.dateProfile, todayRange: props.todayRange, cells: cells, showDayNumbers: rowCnt > 1, showWeekNumbers: options.weekNumbers, forPrint: props.forPrint, compact: state.width != null && (state.width / cells.length) < COMPACT_CELL_WIDTH,
749
+ let rowHeightsRedistribute = !props.forPrint && !isHeightAuto;
750
+ let [rowMinHeight, isCompact] = computeRowHeight(props.visibleWidth, rowCnt, isHeightAuto, props.forPrint, options);
751
+ return (preact.createElement("div", { className: internal$1.joinClassNames(
752
+ // HACK for Safari. Can't do break-inside:avoid with flexbox items, likely b/c it's not standard:
753
+ // https://stackoverflow.com/a/60256345
754
+ !props.forPrint && 'fc-flex-col', props.className), style: { width: props.width }, ref: this.handleRootEl }, props.cellRows.map((cells, row) => (preact.createElement(DayGridRow, { key: cells[0].key, dateProfile: props.dateProfile, todayRange: props.todayRange, cells: cells, showDayNumbers: rowCnt > 1, showWeekNumbers: options.weekNumbers, forPrint: props.forPrint, isCompact: isCompact,
734
755
  // if not auto-height, distribute height of container somewhat evently to rows
735
756
  // (treat all as zero, distribute height, then ensure min-heights -- the inner content height)
736
- className: isHeightAuto ? '' : 'fc-grow fc-basis0',
757
+ className: internal$1.joinClassNames(rowHeightsRedistribute && 'fc-grow fc-basis0', rowCnt > 1 && 'fc-break-inside-avoid', // don't avoid breaks for single tall row
758
+ row < rowCnt - 1 && 'fc-border-b'),
737
759
  // content
738
- fgEventSegs: fgEventSegsByRow[row], bgEventSegs: bgEventSegsByRow[row].filter(isSegAllDay) /* HACK */, businessHourSegs: businessHourSegsByRow[row], dateSelectionSegs: dateSelectionSegsByRow[row], eventSelection: props.eventSelection, eventDrag: eventDragByRow[row], eventResize: eventResizeByRow[row], dayMaxEvents: options.dayMaxEvents, dayMaxEventRows: options.dayMaxEventRows,
760
+ fgEventSegs: fgEventSegsByRow[row], bgEventSegs: bgEventSegsByRow[row].filter(isSegAllDay) /* HACK */, businessHourSegs: businessHourSegsByRow[row], dateSelectionSegs: dateSelectionSegsByRow[row], eventSelection: props.eventSelection, eventDrag: eventDragByRow[row], eventResize: eventResizeByRow[row], dayMaxEvents: props.dayMaxEvents, dayMaxEventRows: props.dayMaxEventRows,
739
761
  // dimensions
740
762
  colWidth: props.colWidth, minHeight: rowMinHeight,
741
763
  // refs
742
764
  heightRef: rowHeightRefMap.createRef(cells[0].key) })))));
743
765
  }
744
766
  componentDidMount() {
745
- this.unwatchWidth = internal$1.watchWidth(this.rootEl, (width) => {
767
+ this.disconnectWidth = internal$1.watchWidth(this.rootEl, (width) => {
746
768
  this.setState({ width });
747
769
  });
748
770
  }
749
771
  componentWillUnmount() {
750
- this.unwatchWidth();
772
+ this.disconnectWidth();
751
773
  }
752
774
  // Hit System
753
775
  // -----------------------------------------------------------------------------------------------
@@ -764,7 +786,7 @@ FullCalendar.DayGrid = (function (exports, core, internal$1, preact) {
764
786
  dateSpan: Object.assign({ range: {
765
787
  start: cellStartDate,
766
788
  end: cellEndDate,
767
- }, allDay: true }, cell.extraDateSpan),
789
+ }, allDay: true }, cell.dateSpanProps),
768
790
  // HACK. TODO: This is expensive to do every hit-query
769
791
  dayEl: getCellEl(getRowEl(this.rootEl, row), col),
770
792
  rect: {
@@ -782,28 +804,96 @@ FullCalendar.DayGrid = (function (exports, core, internal$1, preact) {
782
804
  function isSegAllDay(seg) {
783
805
  return seg.eventRange.def.allDay;
784
806
  }
807
+ function computeRowHeight(visibleWidth, // should INCLUDE any scrollbar width to avoid oscillation
808
+ rowCnt, isHeightAuto, forPrint, options) {
809
+ if (visibleWidth != null) {
810
+ // ensure a consistent row min-height modelled after a month with 6 rows respecting aspectRatio
811
+ // will result in same minHeight regardless of weekends, dayMinWidth, height:auto
812
+ const rowMinHeight = visibleWidth / options.aspectRatio / 6;
813
+ return [
814
+ forPrint
815
+ // special-case for print, which condenses whole-page width without notifying
816
+ // this is value that looks natural on paper for portrait/landscape
817
+ ? '6em'
818
+ // don't give minHeight when single-month non-auto-height
819
+ // TODO: better way to detect this with DateProfile?
820
+ : (rowCnt > 6 || isHeightAuto)
821
+ ? rowMinHeight
822
+ : undefined,
823
+ // isCompact?: just before most lone +more links hit bottom of cell
824
+ rowMinHeight < 70,
825
+ ];
826
+ }
827
+ return [undefined, false];
828
+ }
829
+
830
+ class DayGridHeaderCell extends internal$1.BaseComponent {
831
+ constructor() {
832
+ super(...arguments);
833
+ this.handleInnerEl = (innerEl) => {
834
+ if (this.disconectInnerHeight) {
835
+ this.disconectInnerHeight();
836
+ this.disconectInnerHeight = undefined;
837
+ }
838
+ if (innerEl) {
839
+ this.disconectInnerHeight = internal$1.watchHeight(innerEl, (height) => {
840
+ internal$1.setRef(this.props.innerHeightRef, height);
841
+ });
842
+ }
843
+ else {
844
+ internal$1.setRef(this.props.innerHeightRef, null);
845
+ }
846
+ };
847
+ }
848
+ render() {
849
+ const { props } = this;
850
+ const { renderConfig, dataConfig } = props;
851
+ return (preact.createElement(internal$1.ContentContainer, { tag: 'div', attrs: dataConfig.attrs, className: internal$1.joinClassNames(dataConfig.className, 'fc-header-cell fc-cell fc-flex-col fc-align-center', props.borderStart && 'fc-border-s', !props.isSticky && 'fc-crop', props.colWidth == null && 'fc-liquid'), style: {
852
+ width: props.colWidth != null
853
+ ? props.colWidth * (dataConfig.colSpan || 1)
854
+ : undefined,
855
+ }, renderProps: dataConfig.renderProps, generatorName: renderConfig.generatorName, customGenerator: renderConfig.customGenerator, defaultGenerator: internal$1.renderText, classNameGenerator:
856
+ // don't use custom classNames if disabled
857
+ // TODO: make DRY with DayCellContainer
858
+ dataConfig.renderProps.isDisabled ? undefined : renderConfig.classNameGenerator, didMount: renderConfig.didMount, willUnmount: renderConfig.willUnmount }, (InnerContainer) => (!dataConfig.renderProps.isDisabled && (preact.createElement(InnerContainer, { tag: dataConfig.isNavLink ? 'a' : 'div', attrs: dataConfig.innerAttrs, className: internal$1.joinClassNames('fc-cell-inner fc-flex-col fc-padding-sm', props.isSticky && 'fc-sticky-s'), elRef: this.handleInnerEl })))));
859
+ }
860
+ }
785
861
 
786
- class HeaderRow extends internal$1.BaseComponent {
862
+ class DayGridHeaderRow extends internal$1.BaseComponent {
863
+ constructor() {
864
+ super(...arguments);
865
+ // ref
866
+ this.innerHeightRefMap = new internal$1.RefMap(() => {
867
+ internal$1.afterSize(this.handleInnerHeights);
868
+ });
869
+ this.handleInnerHeights = () => {
870
+ const innerHeightMap = this.innerHeightRefMap.current;
871
+ let max = 0;
872
+ for (const innerHeight of innerHeightMap.values()) {
873
+ max = Math.max(max, innerHeight);
874
+ }
875
+ if (this.currentInnerHeight !== max) {
876
+ this.currentInnerHeight = max;
877
+ internal$1.setRef(this.props.innerHeightRef, max);
878
+ }
879
+ };
880
+ }
787
881
  render() {
788
882
  const { props } = this;
789
- return (preact.createElement("div", { role: props.cellGroup ? undefined : 'row', className: [
790
- props.cellGroup ? 'fc-flex-row' : 'fc-row',
791
- props.className || '',
792
- ].join(' ') }, props.cells.map((cell) => (preact.createElement(preact.Fragment, { key: props.getHeaderModelKey(cell) }, props.renderHeaderContent(cell, props.tierNum, undefined, // innerHeightRef
793
- props.colWidth))))));
883
+ return (preact.createElement("div", { role: 'row', className: internal$1.joinClassNames('fc-flex-row fc-content-box', props.className), style: { height: props.height } }, props.dataConfigs.map((dataConfig, cellI) => (preact.createElement(DayGridHeaderCell, { key: dataConfig.key, renderConfig: props.renderConfig, dataConfig: dataConfig, isSticky: props.isSticky, borderStart: Boolean(cellI), colWidth: props.colWidth, innerHeightRef: props.innerHeightRef })))));
794
884
  }
795
885
  }
796
886
 
797
- function DayGridHeader(props) {
798
- return (preact.createElement("div", { className: [
799
- 'fc-rowgroup',
800
- 'fc-content-box',
801
- ...(props.extraClassNames || []),
802
- ].join(' '), style: {
803
- width: props.width,
804
- paddingLeft: props.paddingLeft,
805
- paddingRight: props.paddingRight,
806
- } }, props.headerTiers.map((cells, tierNum) => (preact.createElement(HeaderRow, { key: tierNum, tierNum: tierNum, cells: cells, renderHeaderContent: props.renderHeaderContent, getHeaderModelKey: props.getHeaderModelKey, colWidth: props.colWidth })))));
887
+ /*
888
+ TODO: kill this class in favor of DayGridHeaderRows?
889
+ */
890
+ class DayGridHeader extends internal$1.BaseComponent {
891
+ render() {
892
+ const { props } = this;
893
+ return (preact.createElement("div", { className: internal$1.joinClassNames(props.className, 'fc-flex-col', props.width == null && 'fc-liquid'), style: {
894
+ width: props.width
895
+ } }, props.headerTiers.map((rowConfig, tierNum) => (preact.createElement(DayGridHeaderRow, Object.assign({}, rowConfig, { key: tierNum, className: tierNum ? 'fc-border-t' : '', colWidth: props.colWidth }))))));
896
+ }
807
897
  }
808
898
 
809
899
  class DayGridLayoutNormal extends internal$1.BaseComponent {
@@ -812,11 +902,11 @@ FullCalendar.DayGrid = (function (exports, core, internal$1, preact) {
812
902
  this.handleScroller = (scroller) => {
813
903
  internal$1.setRef(this.props.scrollerRef, scroller);
814
904
  };
815
- this.handleLeftScrollbarWidth = (leftScrollbarWidth) => {
816
- this.setState({ leftScrollbarWidth });
905
+ this.handleClientWidth = (clientWidth) => {
906
+ this.setState({ clientWidth });
817
907
  };
818
- this.handleRightScrollbarWidth = (rightScrollbarWidth) => {
819
- this.setState({ rightScrollbarWidth });
908
+ this.handleEndScrollbarWidth = (endScrollbarWidth) => {
909
+ this.setState({ endScrollbarWidth });
820
910
  };
821
911
  }
822
912
  render() {
@@ -825,24 +915,22 @@ FullCalendar.DayGrid = (function (exports, core, internal$1, preact) {
825
915
  const verticalScrollbars = !props.forPrint && !internal$1.getIsHeightAuto(options);
826
916
  const stickyHeaderDates = !props.forPrint && internal$1.getStickyHeaderDates(options);
827
917
  return (preact.createElement(preact.Fragment, null,
828
- options.dayHeaders && (preact.createElement(DayGridHeader, { headerTiers: props.headerTiers, renderHeaderContent: props.renderHeaderContent, getHeaderModelKey: props.getHeaderModelKey,
829
- // render hooks
830
- extraClassNames: [
831
- 'fc-daygrid-header',
832
- stickyHeaderDates ? 'fc-sticky-header' : '',
833
- ],
834
- // dimensions
835
- paddingLeft: state.leftScrollbarWidth, paddingRight: state.rightScrollbarWidth })),
836
- preact.createElement(internal$1.Scroller, { vertical: verticalScrollbars, leftScrollbarWidthRef: this.handleLeftScrollbarWidth, rightScrollbarWidthRef: this.handleRightScrollbarWidth, elClassNames: [
837
- 'fc-daygrid-body',
838
- 'fc-rowgroup',
839
- 'fc-flex-column',
840
- verticalScrollbars ? 'fc-liquid' : '',
841
- ], ref: this.handleScroller },
842
- preact.createElement(DayGridRows // .fc-grow
843
- , { dateProfile: props.dateProfile, todayRange: props.todayRange, cellRows: props.cellRows, forPrint: props.forPrint, isHitComboAllowed: props.isHitComboAllowed,
918
+ options.dayHeaders && (preact.createElement("div", { className: internal$1.joinClassNames(props.forPrint ? 'fc-print-header' : 'fc-flex-row', // col for print, row for screen
919
+ 'fc-border-b') },
920
+ preact.createElement(DayGridHeader, { headerTiers: props.headerTiers, className: internal$1.joinClassNames('fc-daygrid-header', stickyHeaderDates && 'fc-table-header-sticky') }),
921
+ Boolean(state.endScrollbarWidth) && (preact.createElement("div", { className: 'fc-border-s fc-filler', style: { minWidth: state.endScrollbarWidth } })))),
922
+ preact.createElement(internal$1.Scroller, { vertical: verticalScrollbars, clientWidthRef: this.handleClientWidth, endScrollbarWidthRef: this.handleEndScrollbarWidth, className: internal$1.joinClassNames('fc-daygrid-body',
923
+ // HACK for Safari. Can't do break-inside:avoid with flexbox items, likely b/c it's not standard:
924
+ // https://stackoverflow.com/a/60256345
925
+ !props.forPrint && 'fc-flex-col', verticalScrollbars && 'fc-liquid'), ref: this.handleScroller },
926
+ preact.createElement(DayGridRows, { dateProfile: props.dateProfile, todayRange: props.todayRange, cellRows: props.cellRows, forPrint: props.forPrint, isHitComboAllowed: props.isHitComboAllowed, className: 'fc-grow', dayMaxEvents: props.forPrint ? undefined : options.dayMaxEvents, dayMaxEventRows: options.dayMaxEventRows,
844
927
  // content
845
928
  fgEventSegs: props.fgEventSegs, bgEventSegs: props.bgEventSegs, businessHourSegs: props.businessHourSegs, dateSelectionSegs: props.dateSelectionSegs, eventDrag: props.eventDrag, eventResize: props.eventResize, eventSelection: props.eventSelection,
929
+ // dimensions
930
+ visibleWidth: // TODO: DRY
931
+ state.clientWidth != null && state.endScrollbarWidth != null
932
+ ? state.clientWidth + state.endScrollbarWidth
933
+ : undefined,
846
934
  // refs
847
935
  rowHeightRefMap: props.rowHeightRefMap }))));
848
936
  }
@@ -856,14 +944,11 @@ FullCalendar.DayGrid = (function (exports, core, internal$1, preact) {
856
944
  this.footerScrollerRef = preact.createRef();
857
945
  // Sizing
858
946
  // -----------------------------------------------------------------------------------------------
859
- this.handleWidth = (width) => {
860
- this.setState({ width });
947
+ this.handleClientWidth = (clientWidth) => {
948
+ this.setState({ clientWidth });
861
949
  };
862
- this.handleLeftScrollbarWidth = (leftScrollbarWidth) => {
863
- this.setState({ leftScrollbarWidth });
864
- };
865
- this.handleRightScrollbarWidth = (rightScrollbarWidth) => {
866
- this.setState({ rightScrollbarWidth });
950
+ this.handleEndScrollbarWidth = (endScrollbarWidth) => {
951
+ this.setState({ endScrollbarWidth });
867
952
  };
868
953
  }
869
954
  render() {
@@ -873,37 +958,29 @@ FullCalendar.DayGrid = (function (exports, core, internal$1, preact) {
873
958
  const stickyHeaderDates = !props.forPrint && internal$1.getStickyHeaderDates(options);
874
959
  const stickyFooterScrollbar = !props.forPrint && internal$1.getStickyFooterScrollbar(options);
875
960
  const colCnt = props.cellRows[0].length;
876
- const [canvasWidth, colWidth] = computeColWidth(colCnt, props.dayMinWidth, state.width);
961
+ const [canvasWidth, colWidth] = computeColWidth(colCnt, props.dayMinWidth, state.clientWidth);
877
962
  return (preact.createElement(preact.Fragment, null,
878
- options.dayHeaders && (preact.createElement(internal$1.Scroller, { horizontal: true, hideScrollbars: true, elClassNames: [
879
- 'fc-daygrid-header',
880
- 'fc-rowgroup',
881
- stickyHeaderDates ? 'fc-sticky-header' : ''
882
- ], ref: this.headerScrollerRef },
883
- preact.createElement(DayGridHeader, { headerTiers: props.headerTiers, renderHeaderContent: props.renderHeaderContent, getHeaderModelKey: props.getHeaderModelKey,
884
- // dimensions
885
- colWidth: colWidth, width: canvasWidth, paddingLeft: state.leftScrollbarWidth, paddingRight: state.rightScrollbarWidth }))),
886
- preact.createElement(internal$1.Scroller, { vertical: verticalScrollbars, horizontal: true, hideScrollbars: stickyFooterScrollbar, widthRef: this.handleWidth, leftScrollbarWidthRef: this.handleLeftScrollbarWidth, rightScrollbarWidthRef: this.handleRightScrollbarWidth, elClassNames: [
887
- 'fc-daygrid-body',
888
- 'fc-rowgroup',
889
- 'fc-flex-column',
890
- verticalScrollbars ? 'fc-liquid' : '',
891
- ], ref: this.bodyScrollerRef },
892
- preact.createElement(DayGridRows // .fc-grow
893
- , { dateProfile: props.dateProfile, todayRange: props.todayRange, cellRows: props.cellRows, forPrint: props.forPrint, isHitComboAllowed: props.isHitComboAllowed,
963
+ options.dayHeaders && (preact.createElement("div", { className: 'fc-print-header' },
964
+ preact.createElement(internal$1.Scroller, { horizontal: true, hideScrollbars: true, className: internal$1.joinClassNames('fc-daygrid-header fc-flex-row fc-border-b', stickyHeaderDates && 'fc-table-header-sticky'), ref: this.headerScrollerRef },
965
+ preact.createElement(DayGridHeader, { headerTiers: props.headerTiers, colWidth: colWidth, width: canvasWidth }),
966
+ Boolean(state.endScrollbarWidth) && (preact.createElement("div", { className: 'fc-border-s fc-filler', style: { minWidth: state.endScrollbarWidth } }))))),
967
+ preact.createElement(internal$1.Scroller, { vertical: verticalScrollbars, horizontal: true, hideScrollbars: stickyFooterScrollbar ||
968
+ props.forPrint // prevents blank space in print-view on Safari
969
+ , className: internal$1.joinClassNames('fc-daygrid-body',
970
+ // HACK for Safari. Can't do break-inside:avoid with flexbox items, likely b/c it's not standard:
971
+ // https://stackoverflow.com/a/60256345
972
+ !props.forPrint && 'fc-flex-col', verticalScrollbars && 'fc-liquid'), ref: this.bodyScrollerRef, clientWidthRef: this.handleClientWidth, endScrollbarWidthRef: this.handleEndScrollbarWidth },
973
+ preact.createElement(DayGridRows, { dateProfile: props.dateProfile, todayRange: props.todayRange, cellRows: props.cellRows, forPrint: props.forPrint, isHitComboAllowed: props.isHitComboAllowed, className: 'fc-grow', dayMaxEvents: props.forPrint ? undefined : options.dayMaxEvents, dayMaxEventRows: options.dayMaxEventRows,
894
974
  // content
895
975
  fgEventSegs: props.fgEventSegs, bgEventSegs: props.bgEventSegs, businessHourSegs: props.businessHourSegs, dateSelectionSegs: props.dateSelectionSegs, eventDrag: props.eventDrag, eventResize: props.eventResize, eventSelection: props.eventSelection,
896
976
  // dimensions
897
- colWidth: colWidth, width: canvasWidth,
977
+ colWidth: colWidth, width: canvasWidth, visibleWidth: // TODO: DRY
978
+ state.clientWidth != null && state.endScrollbarWidth != null
979
+ ? state.clientWidth + state.endScrollbarWidth
980
+ : undefined,
898
981
  // refs
899
982
  rowHeightRefMap: props.rowHeightRefMap })),
900
- Boolean(stickyFooterScrollbar) && (preact.createElement(internal$1.Scroller, { ref: this.footerScrollerRef, horizontal: true, elClassNames: ['fc-sticky-footer'], elStyle: {
901
- marginTop: '-1px', // HACK
902
- } },
903
- preact.createElement("div", { style: {
904
- width: canvasWidth,
905
- height: '1px', // HACK
906
- } })))));
983
+ Boolean(stickyFooterScrollbar) && (preact.createElement(internal$1.StickyFooterScrollbar, { canvasWidth: canvasWidth, scrollerRef: this.footerScrollerRef }))));
907
984
  }
908
985
  // Lifecycle
909
986
  // -----------------------------------------------------------------------------------------------
@@ -925,12 +1002,11 @@ FullCalendar.DayGrid = (function (exports, core, internal$1, preact) {
925
1002
  // Scrolling
926
1003
  // -----------------------------------------------------------------------------------------------
927
1004
  updateSyncedScroller() {
928
- const { isRtl } = this.context;
929
1005
  this.syncedScroller.handleChildren([
930
1006
  this.headerScrollerRef.current,
931
1007
  this.bodyScrollerRef.current,
932
1008
  this.footerScrollerRef.current,
933
- ], isRtl);
1009
+ ]);
934
1010
  }
935
1011
  }
936
1012
 
@@ -939,119 +1015,59 @@ FullCalendar.DayGrid = (function (exports, core, internal$1, preact) {
939
1015
  super(...arguments);
940
1016
  // ref
941
1017
  this.scrollerRef = preact.createRef();
942
- this.rowHeightRefMap = new internal$1.RefMap();
943
- // Scrolling
944
- // -----------------------------------------------------------------------------------------------
945
- this.timeScrollResponder = new internal$1.ScrollResponder((_time) => {
946
- // HACK to scroll to day
1018
+ this.rowHeightRefMap = new internal$1.RefMap(() => {
1019
+ internal$1.afterSize(this.updateScrollY);
1020
+ });
1021
+ // internal
1022
+ this.scrollDate = null;
1023
+ this.updateScrollY = () => {
947
1024
  const rowHeightMap = this.rowHeightRefMap.current;
948
1025
  const scroller = this.scrollerRef.current;
949
- const scrollTop = computeTopFromDate(this.props.dateProfile.currentDate, this.props.cellRows, rowHeightMap);
950
- if (scrollTop != null) {
951
- scroller.scrollTo({ y: scrollTop });
952
- return true;
1026
+ // Since updateScrollY is called by rowHeightRefMap, could be called with null during cleanup,
1027
+ // and the scroller might not exist
1028
+ if (scroller && this.scrollDate) {
1029
+ let scrollTop = computeTopFromDate(this.scrollDate, this.props.cellRows, rowHeightMap, 1);
1030
+ if (scrollTop != null) {
1031
+ if (scrollTop) {
1032
+ scrollTop++; // clear top border
1033
+ }
1034
+ scroller.scrollTo({ y: scrollTop });
1035
+ }
953
1036
  }
954
- return false;
955
- });
1037
+ };
1038
+ this.clearScroll = () => {
1039
+ this.scrollDate = null;
1040
+ };
956
1041
  }
957
1042
  render() {
958
1043
  const { props, context } = this;
959
1044
  const { options } = context;
960
1045
  const commonLayoutProps = Object.assign(Object.assign({}, props), { scrollerRef: this.scrollerRef, rowHeightRefMap: this.rowHeightRefMap });
961
- return (preact.createElement(internal$1.ViewContainer, { viewSpec: context.viewSpec, elClasses: [props.className, 'fc-flex-column', 'fc-border'] }, options.dayMinWidth ? (preact.createElement(DayGridLayoutPannable, Object.assign({}, commonLayoutProps, { dayMinWidth: options.dayMinWidth }))) : (preact.createElement(DayGridLayoutNormal, Object.assign({}, commonLayoutProps)))));
1046
+ return (preact.createElement(internal$1.ViewContainer, { viewSpec: context.viewSpec, className: internal$1.joinClassNames(props.className, 'fc-print-root fc-border') }, options.dayMinWidth ? (preact.createElement(DayGridLayoutPannable, Object.assign({}, commonLayoutProps, { dayMinWidth: options.dayMinWidth }))) : (preact.createElement(DayGridLayoutNormal, Object.assign({}, commonLayoutProps)))));
962
1047
  }
963
1048
  // Lifecycle
964
1049
  // -----------------------------------------------------------------------------------------------
965
1050
  componentDidMount() {
966
- const { context } = this;
967
- const { options } = context;
968
- context.emitter.on('_timeScrollRequest', this.timeScrollResponder.handleScroll);
969
- this.timeScrollResponder.handleScroll(options.scrollTime);
1051
+ this.resetScroll();
1052
+ this.scrollerRef.current.addScrollEndListener(this.clearScroll);
970
1053
  }
971
1054
  componentDidUpdate(prevProps) {
972
- const { options } = this.context;
973
- if (prevProps.dateProfile !== this.props.dateProfile && options.scrollTimeReset) {
974
- this.timeScrollResponder.handleScroll(options.scrollTime);
975
- }
976
- else {
977
- this.timeScrollResponder.drain();
1055
+ if (prevProps.dateProfile !== this.props.dateProfile && this.context.options.scrollTimeReset) {
1056
+ this.resetScroll();
978
1057
  }
979
1058
  }
980
1059
  componentWillUnmount() {
981
- this.context.emitter.off('_timeScrollRequest', this.timeScrollResponder.handleScroll);
982
- }
983
- }
984
-
985
- const WEEKDAY_FORMAT = internal$1.createFormatter({ weekday: 'long' });
986
- class DayOfWeekHeaderCell extends internal$1.BaseComponent {
987
- constructor() {
988
- super(...arguments);
989
- // ref
990
- this.innerElRef = preact.createRef();
991
- }
992
- render() {
993
- let { props, context } = this;
994
- let { dateEnv, theme, viewApi, options } = context;
995
- let date = internal$1.addDays(new Date(259200000), props.dow); // start with Sun, 04 Jan 1970 00:00:00 GMT
996
- let dateMeta = {
997
- dow: props.dow,
998
- isDisabled: false,
999
- isFuture: false,
1000
- isPast: false,
1001
- isToday: false,
1002
- isOther: false,
1003
- };
1004
- let text = dateEnv.format(date, props.dayHeaderFormat);
1005
- let renderProps = Object.assign(Object.assign(Object.assign(Object.assign({ date }, dateMeta), { view: viewApi }), props.extraRenderProps), { text });
1006
- return (preact.createElement(internal$1.ContentContainer, { elTag: 'div', elClasses: [
1007
- ...internal$1.getDayClassNames(dateMeta, theme),
1008
- ...(props.extraClassNames || []),
1009
- 'fc-header-cell',
1010
- 'fc-cell',
1011
- props.colWidth != null ? '' : 'fc-liquid',
1012
- 'fc-flex-column',
1013
- 'fc-align-center',
1014
- ], elAttrs: props.extraDataAttrs, elStyle: {
1015
- width: props.colWidth != null // TODO: DRY
1016
- ? props.colWidth * (props.colSpan || 1)
1017
- : undefined,
1018
- }, renderProps: renderProps, generatorName: "dayHeaderContent", customGenerator: options.dayHeaderContent, defaultGenerator: renderInner, classNameGenerator: options.dayHeaderClassNames, didMount: options.dayHeaderDidMount, willUnmount: options.dayHeaderWillUnmount }, (InnerContent) => (preact.createElement("div", { ref: this.innerElRef, className: [
1019
- 'fc-flex-column',
1020
- props.isSticky ? 'fc-sticky-x' : '',
1021
- ].join(' ') },
1022
- preact.createElement(InnerContent, { elTag: "a", elClasses: [
1023
- 'fc-cell-inner',
1024
- 'fc-padding-sm',
1025
- ], elAttrs: {
1026
- 'aria-label': dateEnv.format(date, WEEKDAY_FORMAT),
1027
- } })))));
1028
- }
1029
- componentDidMount() {
1030
- const innerEl = this.innerElRef.current; // TODO: make dynamic with useEffect
1031
- // TODO: only attach this if refs props present
1032
- this.disconectInnerHeight = internal$1.watchHeight(innerEl, (height) => {
1033
- internal$1.setRef(this.props.innerHeightRef, height);
1034
- });
1035
- }
1036
- componentWillUnmount() {
1037
- this.disconectInnerHeight();
1038
- }
1039
- }
1040
-
1041
- function createDayHeaderFormatter(explicitFormat, datesRepDistinctDays, dateCnt) {
1042
- return explicitFormat || computeFallbackHeaderFormat(datesRepDistinctDays, dateCnt);
1043
- }
1044
- // Computes a default column header formatting string if `colFormat` is not explicitly defined
1045
- function computeFallbackHeaderFormat(datesRepDistinctDays, dayCnt) {
1046
- // if more than one week row, or if there are a lot of columns with not much space,
1047
- // put just the day numbers will be in each cell
1048
- if (!datesRepDistinctDays || dayCnt > 10) {
1049
- return internal$1.createFormatter({ weekday: 'short' }); // "Sat"
1060
+ this.scrollerRef.current.removeScrollEndListener(this.clearScroll);
1050
1061
  }
1051
- if (dayCnt > 1) {
1052
- return internal$1.createFormatter({ weekday: 'short', month: 'numeric', day: 'numeric', omitCommas: true }); // "Sat 11/12"
1062
+ // Scrolling
1063
+ // -----------------------------------------------------------------------------------------------
1064
+ resetScroll() {
1065
+ this.scrollDate = this.props.dateProfile.currentDate;
1066
+ this.updateScrollY();
1067
+ // updateScrollX
1068
+ const scroller = this.scrollerRef.current;
1069
+ scroller.scrollTo({ x: 0 });
1053
1070
  }
1054
- return internal$1.createFormatter({ weekday: 'long' }); // "Saturday"
1055
1071
  }
1056
1072
 
1057
1073
  class DayGridView extends internal$1.BaseComponent {
@@ -1059,7 +1075,7 @@ FullCalendar.DayGrid = (function (exports, core, internal$1, preact) {
1059
1075
  super(...arguments);
1060
1076
  // memo
1061
1077
  this.buildDayTableModel = internal$1.memoize(buildDayTableModel);
1062
- this.buildHeaderTiers = internal$1.memoize(buildHeaderTiers);
1078
+ this.buildDateRowConfigs = internal$1.memoize(buildDateRowConfigs);
1063
1079
  this.createDayHeaderFormatter = internal$1.memoize(createDayHeaderFormatter);
1064
1080
  // internal
1065
1081
  this.slicer = new DayTableSlicer();
@@ -1069,27 +1085,16 @@ FullCalendar.DayGrid = (function (exports, core, internal$1, preact) {
1069
1085
  const { options } = context;
1070
1086
  const dayTableModel = this.buildDayTableModel(props.dateProfile, context.dateProfileGenerator);
1071
1087
  const datesRepDistinctDays = dayTableModel.rowCnt === 1;
1072
- const headerTiers = this.buildHeaderTiers(dayTableModel.headerDates, datesRepDistinctDays);
1073
- const slicedProps = this.slicer.sliceProps(props, props.dateProfile, options.nextDayThreshold, context, dayTableModel);
1074
1088
  const dayHeaderFormat = this.createDayHeaderFormatter(context.options.dayHeaderFormat, datesRepDistinctDays, dayTableModel.colCnt);
1075
- return (preact.createElement(internal$1.NowTimer, { unit: "day" }, (nowDate, todayRange) => (preact.createElement(DayGridLayout, { dateProfile: props.dateProfile, todayRange: todayRange, cellRows: dayTableModel.cellRows, forPrint: props.forPrint, className: 'fc-daygrid-view',
1076
- // header content
1077
- headerTiers: headerTiers, renderHeaderContent: (model, tier, innerHeightRef, colWidth) => {
1078
- if (model.date) {
1079
- return (preact.createElement(DateHeaderCell, Object.assign({}, model, { dateProfile: props.dateProfile, todayRange: todayRange, navLink: dayTableModel.colCnt > 1, dayHeaderFormat: dayHeaderFormat, colSpan: model.colSpan, colWidth: colWidth })));
1080
- }
1081
- else {
1082
- return (preact.createElement(DayOfWeekHeaderCell, Object.assign({}, model, { dayHeaderFormat: dayHeaderFormat, colSpan: model.colSpan, colWidth: colWidth })));
1083
- }
1084
- }, getHeaderModelKey: (model) => {
1085
- // can use model.key???
1086
- if (model.date) {
1087
- return model.date.toUTCString();
1088
- }
1089
- return model.dow;
1090
- },
1091
- // body content
1092
- fgEventSegs: slicedProps.fgEventSegs, bgEventSegs: slicedProps.bgEventSegs, businessHourSegs: slicedProps.businessHourSegs, dateSelectionSegs: slicedProps.dateSelectionSegs, eventDrag: slicedProps.eventDrag, eventResize: slicedProps.eventResize, eventSelection: slicedProps.eventSelection }))));
1089
+ const slicedProps = this.slicer.sliceProps(props, props.dateProfile, options.nextDayThreshold, context, dayTableModel);
1090
+ return (preact.createElement(internal$1.NowTimer, { unit: "day" }, (nowDate, todayRange) => {
1091
+ const headerTiers = this.buildDateRowConfigs(dayTableModel.headerDates, datesRepDistinctDays, props.dateProfile, todayRange, dayHeaderFormat, context);
1092
+ return (preact.createElement(DayGridLayout, { dateProfile: props.dateProfile, todayRange: todayRange, cellRows: dayTableModel.cellRows, forPrint: props.forPrint, className: 'fc-daygrid',
1093
+ // header content
1094
+ headerTiers: headerTiers,
1095
+ // body content
1096
+ fgEventSegs: slicedProps.fgEventSegs, bgEventSegs: slicedProps.bgEventSegs, businessHourSegs: slicedProps.businessHourSegs, dateSelectionSegs: slicedProps.dateSelectionSegs, eventDrag: slicedProps.eventDrag, eventResize: slicedProps.eventResize, eventSelection: slicedProps.eventSelection }));
1097
+ }));
1093
1098
  }
1094
1099
  }
1095
1100
 
@@ -1131,7 +1136,7 @@ FullCalendar.DayGrid = (function (exports, core, internal$1, preact) {
1131
1136
  return { start, end };
1132
1137
  }
1133
1138
 
1134
- var css_248z = ":root{--fc-daygrid-event-dot-width:8px}.fc-daygrid-week-number{background-color:var(--fc-neutral-bg-color);color:var(--fc-neutral-text-color);min-width:1.5em;padding:2px;position:absolute;text-align:center;top:0;z-index:5}.fc-daygrid-cell.fc-day-today{background-color:var(--fc-today-bg-color)}.fc-daygrid-row-spacious .fc-daygrid-cell-inner{min-height:3em}.fc-daygrid-cell-header{display:flex;flex-direction:row-reverse}.fc-day-other .fc-daygrid-cell-header{opacity:.3}.fc-daygrid-cell-number{padding:4px;position:relative;z-index:4}.fc-daygrid-month-start{font-size:1.1em;font-weight:700}.fc-daygrid-cell-footer{align-items:flex-start;display:flex;flex-direction:column;font-size:.85em;margin:0 2px}.fc-daygrid-row-spacious .fc-daygrid-cell-footer{margin-bottom:1em!important}.fc-daygrid-row-compact .fc-daygrid-cell-footer{align-items:stretch}.fc-daygrid-more-link{border-radius:3px;cursor:pointer;line-height:1;margin-top:1px;max-width:100%;overflow:hidden;padding:2px;position:relative;white-space:nowrap;z-index:4}.fc-daygrid-more-link:hover{background-color:rgba(0,0,0,.1)}.fc-daygrid-row-compact .fc-daygrid-more-link{border:1px solid var(--fc-event-border-color);padding:1px}.fc-daygrid-cell .fc-non-business{z-index:1}.fc-daygrid-cell .fc-bg-event{z-index:2}.fc-daygrid-cell .fc-highlight{z-index:3}.fc-more-popover .fc-popover-body{min-width:220px;padding:10px}.fc-daygrid-event{border-radius:3px;font-size:var(--fc-small-font-size);margin-top:1px;z-index:6}.fc-daygrid-event.fc-event-mirror{z-index:7}.fc-direction-ltr .fc-daygrid-event.fc-event-start,.fc-direction-rtl .fc-daygrid-event.fc-event-end{margin-left:2px}.fc-direction-ltr .fc-daygrid-event.fc-event-end,.fc-direction-rtl .fc-daygrid-event.fc-event-start{margin-right:2px}.fc-direction-ltr .fc-daygrid-event .fc-event-time{margin-right:3px}.fc-direction-rtl .fc-daygrid-event .fc-event-time{margin-left:3px}.fc-direction-ltr .fc-daygrid-block-event:not(.fc-event-start),.fc-direction-rtl .fc-daygrid-block-event:not(.fc-event-end){border-bottom-left-radius:0;border-left-width:0;border-top-left-radius:0}.fc-direction-ltr .fc-daygrid-block-event:not(.fc-event-end),.fc-direction-rtl .fc-daygrid-block-event:not(.fc-event-start){border-bottom-right-radius:0;border-right-width:0;border-top-right-radius:0}.fc-daygrid-block-event .fc-event-time{font-weight:700}.fc-daygrid-block-event .fc-event-time,.fc-daygrid-block-event .fc-event-title{padding:1px}.fc-daygrid-dot-event{align-items:center;direction:row;display:flex;padding:2px 0;position:relative}.fc-daygrid-dot-event.fc-event-mirror,.fc-daygrid-dot-event:hover{background:rgba(0,0,0,.1)}.fc-daygrid-event-dot{border:calc(var(--fc-daygrid-event-dot-width)/2) solid var(--fc-event-border-color);border-radius:calc(var(--fc-daygrid-event-dot-width)/2);box-sizing:content-box;height:0;margin:0 4px;width:0}.fc-daygrid-dot-event .fc-event-time,.fc-daygrid-dot-event .fc-event-title{overflow:hidden;white-space:nowrap}.fc-daygrid-dot-event .fc-event-title{flex-basis:0;flex-grow:1;font-weight:700;min-width:0}";
1139
+ var css_248z = ":root{--fc-daygrid-event-dot-width:8px}.fc-daygrid-day.fc-day-today{background-color:var(--fc-today-bg-color)}.fc-daygrid-day-header{display:flex;flex-direction:row-reverse}.fc-day-other .fc-daygrid-day-header{opacity:.3}.fc-daygrid-day-number{padding:4px;position:relative}.fc-daygrid-month-start{font-size:1.1em;font-weight:700}.fc-daygrid-day-body{display:flex;flex-direction:column;margin-bottom:1px}.fc-daygrid-day-body-tall{margin-bottom:1em;min-height:2em}.fc-daygrid-day-body:only-child{margin-top:2px}.fc-daygrid-more-link{border-radius:3px;cursor:pointer;font-size:var(--fc-small-font-size);margin:0 2px 1px;max-width:100%;overflow:hidden;padding:2px;position:relative;white-space:nowrap}.fc-daygrid-more-link:hover{background-color:rgba(0,0,0,.1)}.fc-daygrid-more-link-button{align-self:flex-start}.fc-daygrid-more-link-block{border:1px solid var(--fc-event-border-color);padding:1px}.fc-daygrid-week-number{background-color:var(--fc-neutral-bg-color);color:var(--fc-neutral-text-color);min-width:1.5em;padding:2px;position:absolute;text-align:center;top:0}.fc-more-popover .fc-popover-body{min-width:220px;padding:10px}.fc-daygrid-event{border-radius:3px;font-size:var(--fc-small-font-size);margin-bottom:1px}.fc-media-print .fc-daygrid-event{overflow:hidden!important;white-space:nowrap!important}.fc-direction-ltr .fc-daygrid-event.fc-event-start,.fc-direction-rtl .fc-daygrid-event.fc-event-end{margin-left:2px}.fc-direction-ltr .fc-daygrid-event.fc-event-end,.fc-direction-rtl .fc-daygrid-event.fc-event-start{margin-right:2px}.fc-direction-ltr .fc-daygrid-event .fc-event-time{margin-right:3px}.fc-direction-rtl .fc-daygrid-event .fc-event-time{margin-left:3px}.fc-direction-ltr .fc-daygrid-block-event:not(.fc-event-start),.fc-direction-rtl .fc-daygrid-block-event:not(.fc-event-end){border-bottom-left-radius:0;border-left-width:0;border-top-left-radius:0}.fc-direction-ltr .fc-daygrid-block-event:not(.fc-event-end),.fc-direction-rtl .fc-daygrid-block-event:not(.fc-event-start){border-bottom-right-radius:0;border-right-width:0;border-top-right-radius:0}.fc-daygrid-block-event .fc-event-time{font-weight:700}.fc-daygrid-block-event .fc-event-time,.fc-daygrid-block-event .fc-event-title{padding:1px}.fc-daygrid-dot-event{align-items:center;direction:row;display:flex;padding:2px 0;position:relative;z-index:2}.fc-daygrid-dot-event.fc-event-mirror,.fc-daygrid-dot-event:hover{background:rgba(0,0,0,.1)}.fc-daygrid-dot-event.fc-event-selected:before{bottom:-10px;top:-10px}.fc-daygrid-event-dot{border:calc(var(--fc-daygrid-event-dot-width)/2) solid var(--fc-event-border-color);border-radius:calc(var(--fc-daygrid-event-dot-width)/2);box-sizing:content-box;height:0;margin:0 4px;width:0}.fc-daygrid-dot-event .fc-event-time,.fc-daygrid-dot-event .fc-event-title{overflow:hidden;white-space:nowrap}.fc-daygrid-dot-event .fc-event-title{flex-basis:0;flex-grow:1;font-weight:700;min-height:0;min-width:0}";
1135
1140
  internal$1.injectStyles(css_248z);
1136
1141
 
1137
1142
  var plugin = core.createPlugin({
@@ -1162,52 +1167,21 @@ FullCalendar.DayGrid = (function (exports, core, internal$1, preact) {
1162
1167
  },
1163
1168
  });
1164
1169
 
1165
- /*
1166
- TODO: is it even worth doing this "advanced" version?
1167
- */
1168
- class HeaderRowAdvanced extends internal$1.BaseComponent {
1169
- constructor() {
1170
- super(...arguments);
1171
- // ref
1172
- this.innerHeightRefMap = new internal$1.RefMap(() => {
1173
- internal$1.afterSize(this.handleInnerHeights);
1174
- });
1175
- this.handleInnerHeights = () => {
1176
- const innerHeightMap = this.innerHeightRefMap.current;
1177
- let max = 0;
1178
- for (const innerHeight of innerHeightMap.values()) {
1179
- max = Math.max(max, innerHeight);
1180
- }
1181
- if (this.currentInnerHeight !== max) {
1182
- this.currentInnerHeight = max;
1183
- internal$1.setRef(this.props.innerHeightRef, max);
1184
- }
1185
- };
1186
- }
1187
- render() {
1188
- const { props } = this;
1189
- return (preact.createElement("div", { role: 'row', className: 'fc-row', style: { height: props.height } }, props.cells.map((cell) => {
1190
- const key = props.getHeaderModelKey(cell);
1191
- return (preact.createElement(preact.Fragment, { key: props.getHeaderModelKey(cell) }, props.renderHeaderContent(cell, props.tierNum, this.innerHeightRefMap.createRef(key), // innerHeightRef
1192
- props.colWidth)));
1193
- })));
1194
- }
1195
- }
1196
-
1197
1170
  var internal = {
1198
1171
  __proto__: null,
1199
1172
  DayTableSlicer: DayTableSlicer,
1200
1173
  TableDateProfileGenerator: TableDateProfileGenerator,
1201
1174
  buildDayTableRenderRange: buildDayTableRenderRange,
1202
1175
  DayGridView: DayGridView,
1203
- DateHeaderCell: DateHeaderCell,
1204
- DayOfWeekHeaderCell: DayOfWeekHeaderCell,
1205
- HeaderRow: HeaderRow,
1206
- HeaderRowAdvanced: HeaderRowAdvanced,
1176
+ DayGridHeaderRow: DayGridHeaderRow,
1177
+ buildDateRowConfigs: buildDateRowConfigs,
1178
+ buildDateRowConfig: buildDateRowConfig,
1179
+ buildDateRenderConfig: buildDateRenderConfig,
1180
+ buildDateDataConfigs: buildDateDataConfigs,
1207
1181
  createDayHeaderFormatter: createDayHeaderFormatter,
1208
1182
  DayGridLayout: DayGridLayout,
1183
+ computeRowHeight: computeRowHeight,
1209
1184
  DayGridRow: DayGridRow,
1210
- COMPACT_CELL_WIDTH: COMPACT_CELL_WIDTH,
1211
1185
  DayGridRows: DayGridRows,
1212
1186
  buildDayTableModel: buildDayTableModel,
1213
1187
  computeColWidth: computeColWidth,