@bagelink/vue 1.2.15 → 1.2.20
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/dist/components/calendar/CalendarTypes.d.ts +13 -0
- package/dist/components/calendar/CalendarTypes.d.ts.map +1 -0
- package/dist/components/calendar/Index.vue.d.ts +39 -507
- package/dist/components/calendar/Index.vue.d.ts.map +1 -1
- package/dist/components/calendar/utils.d.ts +31 -0
- package/dist/components/calendar/utils.d.ts.map +1 -0
- package/dist/components/calendar/views/AgendaView.vue.d.ts +16 -0
- package/dist/components/calendar/views/AgendaView.vue.d.ts.map +1 -0
- package/dist/components/calendar/views/DayView.vue.d.ts +50 -0
- package/dist/components/calendar/views/DayView.vue.d.ts.map +1 -0
- package/dist/components/calendar/views/MonthView.vue.d.ts +20 -0
- package/dist/components/calendar/views/MonthView.vue.d.ts.map +1 -0
- package/dist/components/calendar/views/WeekView.vue.d.ts +33 -0
- package/dist/components/calendar/views/WeekView.vue.d.ts.map +1 -0
- package/dist/components/form/BglMultiStepForm.vue.d.ts +63 -0
- package/dist/components/form/BglMultiStepForm.vue.d.ts.map +1 -0
- package/dist/components/form/index.d.ts +1 -0
- package/dist/components/form/index.d.ts.map +1 -1
- package/dist/components/form/inputs/CodeEditor/Index.vue.d.ts.map +1 -1
- package/dist/components/form/inputs/DateInput.vue.d.ts +3 -3
- package/dist/components/form/inputs/DateInput.vue.d.ts.map +1 -1
- package/dist/components/form/inputs/DatePicker.vue.d.ts +3 -3
- package/dist/components/form/inputs/DatePicker.vue.d.ts.map +1 -1
- package/dist/components/form/inputs/SelectInput.vue.d.ts.map +1 -1
- package/dist/index.cjs +2241 -3891
- package/dist/index.d.ts +1 -1
- package/dist/index.d.ts.map +1 -1
- package/dist/index.mjs +2242 -3892
- package/dist/style.css +567 -633
- package/dist/utils/BagelFormUtils.d.ts +4 -2
- package/dist/utils/BagelFormUtils.d.ts.map +1 -1
- package/dist/utils/calendar/EDate.d.ts +2 -0
- package/dist/utils/calendar/EDate.d.ts.map +1 -0
- package/dist/utils/calendar/Helpers.d.ts +19 -0
- package/dist/utils/calendar/Helpers.d.ts.map +1 -0
- package/dist/utils/calendar/constants.d.ts +3 -0
- package/dist/utils/calendar/constants.d.ts.map +1 -0
- package/dist/utils/calendar/dateUtils.d.ts +30 -0
- package/dist/utils/calendar/dateUtils.d.ts.map +1 -0
- package/dist/utils/calendar/event.interface.d.ts +32 -0
- package/dist/utils/calendar/event.interface.d.ts.map +1 -0
- package/dist/utils/calendar/time.d.ts +117 -0
- package/dist/utils/calendar/time.d.ts.map +1 -0
- package/dist/utils/calendar/types.d.ts +27 -0
- package/dist/utils/calendar/types.d.ts.map +1 -0
- package/dist/utils/calendar/typings.d.ts +87 -0
- package/dist/utils/calendar/typings.d.ts.map +1 -0
- package/dist/utils/calendar/week.d.ts +117 -0
- package/dist/utils/calendar/week.d.ts.map +1 -0
- package/package.json +1 -1
- package/src/components/calendar/CalendarTypes.ts +13 -0
- package/src/components/calendar/Index.vue +124 -389
- package/src/components/calendar/utils.ts +70 -0
- package/src/components/calendar/views/AgendaView.vue +263 -0
- package/src/components/calendar/views/DayView.vue +373 -0
- package/src/components/calendar/views/MonthView.vue +313 -0
- package/src/components/calendar/views/WeekView.vue +431 -0
- package/src/components/form/BglMultiStepForm.vue +383 -69
- package/src/components/form/index.ts +1 -0
- package/src/components/form/inputs/CodeEditor/Index.vue +11 -0
- package/src/components/form/inputs/DateInput.vue +3 -3
- package/src/components/form/inputs/DatePicker.vue +35 -30
- package/src/components/form/inputs/SelectInput.vue +2 -0
- package/src/components/form/inputs/Upload/upload.types.d.ts +0 -1
- package/src/index.ts +2 -2
- package/src/styles/inputs.css +138 -137
- package/src/styles/layout.css +3 -2
- package/src/styles/mobilLayout.css +4 -2
- package/src/utils/BagelFormUtils.ts +6 -2
- package/src/utils/calendar/EDate.ts +0 -0
- package/src/{components/calendar/helpers → utils/calendar}/Helpers.ts +6 -6
- package/src/utils/calendar/constants.ts +2 -0
- package/src/utils/{timeAgo.ts → calendar/dateUtils.ts} +38 -1
- package/src/utils/calendar/event.interface.ts +33 -0
- package/src/{components/calendar/helpers/Time.ts → utils/calendar/time.ts} +15 -15
- package/src/utils/calendar/types.ts +27 -0
- package/src/{components/calendar/typings/config.interface.ts → utils/calendar/typings.ts} +13 -6
- package/src/utils/calendar/week.ts +588 -0
- package/src/components/calendar/assets/base.css +0 -60
- package/src/components/calendar/components/header/Header.vue +0 -153
- package/src/components/calendar/components/month/AgendaEventTile.vue +0 -135
- package/src/components/calendar/components/month/AgendaEvents.vue +0 -72
- package/src/components/calendar/components/month/Day.vue +0 -256
- package/src/components/calendar/components/month/Event.vue +0 -164
- package/src/components/calendar/components/month/Month.vue +0 -241
- package/src/components/calendar/components/month/WeekDay.vue +0 -15
- package/src/components/calendar/components/partials/EventFlyout.vue +0 -430
- package/src/components/calendar/components/week/Day.vue +0 -198
- package/src/components/calendar/components/week/DayEvent.vue +0 -584
- package/src/components/calendar/components/week/DayTimeline.vue +0 -80
- package/src/components/calendar/components/week/FullDayEvent.vue +0 -121
- package/src/components/calendar/components/week/Week.vue +0 -414
- package/src/components/calendar/components/week/WeekTimeline.vue +0 -101
- package/src/components/calendar/constants.ts +0 -13
- package/src/components/calendar/helpers/DayIntervals.ts +0 -48
- package/src/components/calendar/helpers/EDate.ts +0 -18
- package/src/components/calendar/helpers/Errors.ts +0 -69
- package/src/components/calendar/helpers/EventChange.ts +0 -88
- package/src/components/calendar/helpers/EventConcurrency.ts +0 -69
- package/src/components/calendar/helpers/EventFlyoutPosition.ts +0 -96
- package/src/components/calendar/helpers/EventPosition.ts +0 -154
- package/src/components/calendar/helpers/EventsFilter.ts +0 -50
- package/src/components/calendar/helpers/Week.ts +0 -37
- package/src/components/calendar/language/index.ts +0 -41
- package/src/components/calendar/language/keys.ts +0 -99
- package/src/components/calendar/models/Event.ts +0 -112
- package/src/components/calendar/styles/_mixins.css +0 -21
- package/src/components/calendar/styles/_variables.css +0 -47
- package/src/components/calendar/typings/interfaces/day.interface.ts +0 -10
- package/src/components/calendar/typings/interfaces/event.interface.ts +0 -32
- package/src/components/calendar/typings/interfaces/full-day-events-week.type.ts +0 -8
- package/src/components/calendar/typings/interfaces/period.interface.ts +0 -5
- package/src/components/calendar/typings/interfaces/time-modes.ts +0 -11
- package/src/components/calendar/typings/types.ts +0 -27
|
@@ -1,69 +0,0 @@
|
|
|
1
|
-
import type { ConfigInterface } from '../typings/config.interface'
|
|
2
|
-
import type { EventInterface } from '../typings/interfaces/event.interface'
|
|
3
|
-
import { DATE_TIME_STRING_FULL_DAY_PATTERN, DATE_TIME_STRING_PATTERN } from '../constants'
|
|
4
|
-
|
|
5
|
-
type RecursivePartial<T> = {
|
|
6
|
-
[P in keyof T]?: RecursivePartial<T[P]>;
|
|
7
|
-
}
|
|
8
|
-
|
|
9
|
-
export default class Errors {
|
|
10
|
-
public static PREFIX = '[Qalendar warning]'
|
|
11
|
-
// public static SUFFIX = 'This is a development warning, which will never be displayed in production environments'
|
|
12
|
-
public static SUFFIX = ''
|
|
13
|
-
|
|
14
|
-
public static readonly MISSING_ID_WARNING = `${this.PREFIX} required event property 'id' is missing \n${this.SUFFIX}`
|
|
15
|
-
|
|
16
|
-
public static readonly MISSING_TITLE_WARNING = `${this.PREFIX} required event property 'title' is missing \n${this.SUFFIX}`
|
|
17
|
-
|
|
18
|
-
public static readonly MISSING_TIME_WARNING = `${this.PREFIX} required event property 'time' is missing \n${this.SUFFIX}`
|
|
19
|
-
|
|
20
|
-
public static readonly MISSING_TIME_START_WARNING = `${this.PREFIX} required event property 'time.start' is missing \n${this.SUFFIX}`
|
|
21
|
-
|
|
22
|
-
public static readonly MISSING_TIME_END_WARNING = `${this.PREFIX} required event property 'time.end' is missing \n${this.SUFFIX}`
|
|
23
|
-
|
|
24
|
-
static checkEventProperties(event: RecursivePartial<EventInterface>) {
|
|
25
|
-
// Warn if required property is missing
|
|
26
|
-
if (!event.id) console.warn(this.MISSING_ID_WARNING)
|
|
27
|
-
if (!event.title) console.warn(this.MISSING_TITLE_WARNING)
|
|
28
|
-
if (!event.time) console.warn(this.MISSING_TIME_WARNING)
|
|
29
|
-
if (!event.time?.start) console.warn(this.MISSING_TIME_START_WARNING)
|
|
30
|
-
if (!event.time?.end) console.warn(this.MISSING_TIME_END_WARNING)
|
|
31
|
-
|
|
32
|
-
if (
|
|
33
|
-
event.time?.start
|
|
34
|
-
&& event.time.end
|
|
35
|
-
&& !DATE_TIME_STRING_PATTERN.test(event.time.start)
|
|
36
|
-
&& !DATE_TIME_STRING_FULL_DAY_PATTERN.test(event.time.start)
|
|
37
|
-
) {
|
|
38
|
-
console.warn(
|
|
39
|
-
`${this.PREFIX} event property 'time.start' expects a string formatted like 'YYYY-MM-DD hh:mm', or 'YYYY-MM-DD', received ${event.time.start} \n${this.SUFFIX}`
|
|
40
|
-
)
|
|
41
|
-
}
|
|
42
|
-
if (
|
|
43
|
-
event.time?.start
|
|
44
|
-
&& event.time.end
|
|
45
|
-
&& !DATE_TIME_STRING_PATTERN.test(event.time.end)
|
|
46
|
-
&& !DATE_TIME_STRING_FULL_DAY_PATTERN.test(event.time.end)
|
|
47
|
-
) {
|
|
48
|
-
console.warn(
|
|
49
|
-
`${this.PREFIX} event property 'time.end' expects a string formatted like 'YYYY-MM-DD hh:mm', or 'YYYY-MM-DD', received ${event.time.end} \n${this.SUFFIX}`
|
|
50
|
-
)
|
|
51
|
-
}
|
|
52
|
-
}
|
|
53
|
-
|
|
54
|
-
static checkConfig(config: ConfigInterface) {
|
|
55
|
-
if (config.locale && !/^[a-z]{2}-[A-Z]{2}$/.test(config.locale)) {
|
|
56
|
-
console.warn(
|
|
57
|
-
`${this.PREFIX} config.locale expects a string of format xx-XX, received: ${config.locale}`
|
|
58
|
-
)
|
|
59
|
-
}
|
|
60
|
-
if (
|
|
61
|
-
config.defaultMode
|
|
62
|
-
&& !['month', 'week', 'day'].includes(config.defaultMode)
|
|
63
|
-
) {
|
|
64
|
-
console.warn(
|
|
65
|
-
`${this.PREFIX} config.defaultMode expects either one of the values "day", "week" or "month"`
|
|
66
|
-
)
|
|
67
|
-
}
|
|
68
|
-
}
|
|
69
|
-
}
|
|
@@ -1,88 +0,0 @@
|
|
|
1
|
-
import type { EventInterface } from '../typings/interfaces/event.interface'
|
|
2
|
-
import type Time from './Time'
|
|
3
|
-
import { DAY_MODE } from '../typings/interfaces/time-modes'
|
|
4
|
-
import { DRAG_N_RESIZE_DIRECTION } from '../typings/types'
|
|
5
|
-
|
|
6
|
-
export class EventChange {
|
|
7
|
-
private dayStart = ''
|
|
8
|
-
private dayEnd = ''
|
|
9
|
-
|
|
10
|
-
constructor(private timeInstance: Time, private date: string) {
|
|
11
|
-
this.setDayBoundariesTimeStrings()
|
|
12
|
-
}
|
|
13
|
-
|
|
14
|
-
public canEventBeMoved(event: EventInterface, direction: DRAG_N_RESIZE_DIRECTION): boolean {
|
|
15
|
-
if (this.timeInstance.dayMode !== DAY_MODE.FLEXIBLE) {
|
|
16
|
-
return this.handleNonFlexibleDays(direction, event)
|
|
17
|
-
}
|
|
18
|
-
|
|
19
|
-
return this.handleFlexibleDays(direction, event)
|
|
20
|
-
}
|
|
21
|
-
|
|
22
|
-
private handleNonFlexibleDays(direction: DRAG_N_RESIZE_DIRECTION, event: EventInterface) {
|
|
23
|
-
if (direction === DRAG_N_RESIZE_DIRECTION.FORWARDS) {
|
|
24
|
-
return this.handleForwardsMoveForNonFlexibleDays(event)
|
|
25
|
-
}
|
|
26
|
-
|
|
27
|
-
return this.handleBackwardsMoveForNonFlexibleDays(event)
|
|
28
|
-
}
|
|
29
|
-
|
|
30
|
-
private handleFlexibleDays(direction: DRAG_N_RESIZE_DIRECTION, event: EventInterface) {
|
|
31
|
-
if (direction == DRAG_N_RESIZE_DIRECTION.FORWARDS) {
|
|
32
|
-
return this.handleForwardsMoveForFlexibleDays(event)
|
|
33
|
-
}
|
|
34
|
-
|
|
35
|
-
return this.handleBackwardsMoveForFlexibleDays(event)
|
|
36
|
-
}
|
|
37
|
-
|
|
38
|
-
private handleForwardsMoveForNonFlexibleDays(event: EventInterface) {
|
|
39
|
-
const endTimePlus15Minutes = this.timeInstance.addMinutesToDateTimeString(15, event.time.end)
|
|
40
|
-
const endTimeString = this.timeInstance.timeStringFrom(endTimePlus15Minutes)
|
|
41
|
-
const newEndDateString = this.timeInstance.dateStringFrom(endTimePlus15Minutes)
|
|
42
|
-
|
|
43
|
-
if (newEndDateString > this.date) return false
|
|
44
|
-
|
|
45
|
-
return endTimeString <= this.dayEnd
|
|
46
|
-
}
|
|
47
|
-
|
|
48
|
-
private handleBackwardsMoveForNonFlexibleDays(event: EventInterface) {
|
|
49
|
-
const startTimeMinus15Minutes = this.timeInstance.addMinutesToDateTimeString(-15, event.time.start)
|
|
50
|
-
const startTimeString = this.timeInstance.timeStringFrom(startTimeMinus15Minutes)
|
|
51
|
-
const newStartDateString = this.timeInstance.dateStringFrom(startTimeMinus15Minutes)
|
|
52
|
-
|
|
53
|
-
if (newStartDateString < this.date) return false
|
|
54
|
-
|
|
55
|
-
return startTimeString >= this.dayStart
|
|
56
|
-
}
|
|
57
|
-
|
|
58
|
-
private handleForwardsMoveForFlexibleDays(event: EventInterface) {
|
|
59
|
-
const endTimePlus15Minutes = this.timeInstance.addMinutesToDateTimeString(15, event.time.end)
|
|
60
|
-
const endTimeString = this.timeInstance.timeStringFrom(endTimePlus15Minutes)
|
|
61
|
-
const newEndDateString = this.timeInstance.dateStringFrom(endTimePlus15Minutes)
|
|
62
|
-
|
|
63
|
-
if (newEndDateString === this.date) return true
|
|
64
|
-
|
|
65
|
-
return endTimeString <= this.dayEnd
|
|
66
|
-
}
|
|
67
|
-
|
|
68
|
-
private handleBackwardsMoveForFlexibleDays(event: EventInterface) {
|
|
69
|
-
const startTimeMinus15Minutes = this.timeInstance.addMinutesToDateTimeString(-15, event.time.start)
|
|
70
|
-
const startTimeString = this.timeInstance.timeStringFrom(startTimeMinus15Minutes)
|
|
71
|
-
const newStartDateString = this.timeInstance.dateStringFrom(startTimeMinus15Minutes)
|
|
72
|
-
|
|
73
|
-
if (newStartDateString > this.date) return true
|
|
74
|
-
|
|
75
|
-
return startTimeString >= this.dayStart
|
|
76
|
-
}
|
|
77
|
-
|
|
78
|
-
private setDayBoundariesTimeStrings() {
|
|
79
|
-
const startHour = this.timeInstance.getHourAndMinutesFromTimePoints(this.timeInstance.DAY_START).hour
|
|
80
|
-
const endHour = this.timeInstance.getHourAndMinutesFromTimePoints(this.timeInstance.DAY_END).hour
|
|
81
|
-
|
|
82
|
-
const startHourString = this.timeInstance.doubleDigit(startHour)
|
|
83
|
-
this.dayStart = `${startHourString}:00`
|
|
84
|
-
|
|
85
|
-
const endHourString = this.timeInstance.doubleDigit(endHour)
|
|
86
|
-
this.dayEnd = `${endHourString}:00`
|
|
87
|
-
}
|
|
88
|
-
}
|
|
@@ -1,69 +0,0 @@
|
|
|
1
|
-
import type { EventInterface } from '../typings/interfaces/event.interface'
|
|
2
|
-
|
|
3
|
-
export default class EventConcurrency {
|
|
4
|
-
protected sortEventsAccordingToStartOfTime(events: EventInterface[]) {
|
|
5
|
-
function compare(a: EventInterface, b: EventInterface) {
|
|
6
|
-
if (a.time.start < b.time.start) {
|
|
7
|
-
return -1
|
|
8
|
-
}
|
|
9
|
-
if (a.time.start > b.time.start) {
|
|
10
|
-
return 1
|
|
11
|
-
}
|
|
12
|
-
return 0
|
|
13
|
-
}
|
|
14
|
-
|
|
15
|
-
return events.sort(compare)
|
|
16
|
-
}
|
|
17
|
-
|
|
18
|
-
/**
|
|
19
|
-
* Sets the "zIndex" and "nOfPreviousConcurrentEvents" properties on an event
|
|
20
|
-
*
|
|
21
|
-
* zIndex - lets the event know with which z-index it should be displayed
|
|
22
|
-
* nOfPreviousConcurrentEvents - lets the event know, how many other, previous events, are competing for the same width
|
|
23
|
-
*/
|
|
24
|
-
calculateConcurrencyForEvents(events: EventInterface[]) {
|
|
25
|
-
const updatedEvents = this.sortEventsAccordingToStartOfTime(events)
|
|
26
|
-
if (!updatedEvents.length) return []
|
|
27
|
-
|
|
28
|
-
for (const [index, calendarEvent] of updatedEvents.entries()) {
|
|
29
|
-
if (index === 0) continue
|
|
30
|
-
|
|
31
|
-
// let _unused_previousEvent = updatedEvents[index - 1]
|
|
32
|
-
|
|
33
|
-
// Set nOfPreviousConcurrentEvents
|
|
34
|
-
let iterator = 0
|
|
35
|
-
let nOfConcurrentEvents = 0
|
|
36
|
-
while (iterator < index) {
|
|
37
|
-
if (updatedEvents[iterator].time.end > calendarEvent.time.start)
|
|
38
|
-
nOfConcurrentEvents++
|
|
39
|
-
iterator++
|
|
40
|
-
}
|
|
41
|
-
|
|
42
|
-
if (nOfConcurrentEvents)
|
|
43
|
-
updatedEvents[index].nOfPreviousConcurrentEvents = nOfConcurrentEvents
|
|
44
|
-
}
|
|
45
|
-
|
|
46
|
-
// Iterate backwards over the events, in order to tell all concurrent events how many concurrent events they have
|
|
47
|
-
for (let index = updatedEvents.length - 1; index >= 0; index--) {
|
|
48
|
-
let nOfUpcomingConcurrentEvents = 0
|
|
49
|
-
let iterator = updatedEvents.length - 1
|
|
50
|
-
|
|
51
|
-
while (iterator > index) {
|
|
52
|
-
if (
|
|
53
|
-
updatedEvents[iterator].time.start < updatedEvents[index].time.end
|
|
54
|
-
) {
|
|
55
|
-
nOfUpcomingConcurrentEvents++
|
|
56
|
-
}
|
|
57
|
-
|
|
58
|
-
iterator--
|
|
59
|
-
}
|
|
60
|
-
|
|
61
|
-
const nfOfPreviousEvents
|
|
62
|
-
= updatedEvents[index].nOfPreviousConcurrentEvents || 0
|
|
63
|
-
updatedEvents[index].totalConcurrentEvents
|
|
64
|
-
= nfOfPreviousEvents + nOfUpcomingConcurrentEvents + 1 // One for the event itself
|
|
65
|
-
}
|
|
66
|
-
|
|
67
|
-
return events
|
|
68
|
-
}
|
|
69
|
-
}
|
|
@@ -1,96 +0,0 @@
|
|
|
1
|
-
interface elementDimensions { height: number, width: number }
|
|
2
|
-
import type { DOMRect } from '../typings/types'
|
|
3
|
-
|
|
4
|
-
const calendarDomRectForVitest = {
|
|
5
|
-
x: 8,
|
|
6
|
-
y: 26,
|
|
7
|
-
width: 903,
|
|
8
|
-
height: 702,
|
|
9
|
-
top: 26,
|
|
10
|
-
right: 911,
|
|
11
|
-
bottom: 728,
|
|
12
|
-
left: 8,
|
|
13
|
-
}
|
|
14
|
-
|
|
15
|
-
export const EVENT_FLYOUT_WIDTH = 400
|
|
16
|
-
|
|
17
|
-
export default class EventFlyoutPosition {
|
|
18
|
-
calculateFlyoutPosition(
|
|
19
|
-
eventElementDOMRect: DOMRect,
|
|
20
|
-
flyoutDimensions: elementDimensions,
|
|
21
|
-
calendarDomRectParam: DOMRect | null = null
|
|
22
|
-
): { top: number | null, left: number | null } | undefined {
|
|
23
|
-
const calendarDomRect = calendarDomRectParam || calendarDomRectForVitest
|
|
24
|
-
|
|
25
|
-
// The four variables below, contain the space in pixels, from the event to the calendar border
|
|
26
|
-
// i.e. spaceTop === length from event top border, to calendar top border
|
|
27
|
-
// and spaceRight === length from event right border to calendar right border
|
|
28
|
-
const spaceTop = eventElementDOMRect.top - calendarDomRect.top
|
|
29
|
-
const spaceRight = calendarDomRect.right - eventElementDOMRect.right
|
|
30
|
-
const spaceBottom = calendarDomRect.bottom - eventElementDOMRect.bottom
|
|
31
|
-
const spaceLeft = eventElementDOMRect.left - calendarDomRect.left
|
|
32
|
-
|
|
33
|
-
const flyoutNeededWidth = flyoutDimensions.width + 10
|
|
34
|
-
|
|
35
|
-
// Set 'top' for events whose bottom is outside the viewport
|
|
36
|
-
const topWhenSpaceToBottomIsNegative
|
|
37
|
-
= spaceBottom < 0
|
|
38
|
-
? calendarDomRect.bottom - flyoutDimensions.height - 10
|
|
39
|
-
: null
|
|
40
|
-
|
|
41
|
-
const topWhenSpaceTopIsNegative
|
|
42
|
-
= spaceTop < 0 ? calendarDomRect.top + 10 : null
|
|
43
|
-
|
|
44
|
-
// Position flyout to the right of event, facing downwards, when possible
|
|
45
|
-
if (
|
|
46
|
-
spaceBottom > flyoutDimensions.height
|
|
47
|
-
&& spaceRight > flyoutNeededWidth
|
|
48
|
-
) {
|
|
49
|
-
return {
|
|
50
|
-
top: topWhenSpaceTopIsNegative || Math.round(eventElementDOMRect.top),
|
|
51
|
-
left: Math.round(eventElementDOMRect.right) + 10,
|
|
52
|
-
}
|
|
53
|
-
}
|
|
54
|
-
|
|
55
|
-
// Position flyout to the right of event, facing upwards, when too close to the bottom
|
|
56
|
-
if (spaceTop > flyoutDimensions.height && spaceRight > flyoutNeededWidth) {
|
|
57
|
-
return {
|
|
58
|
-
top: topWhenSpaceToBottomIsNegative || Math.round(eventElementDOMRect.bottom) - flyoutDimensions.height,
|
|
59
|
-
left: Math.round(eventElementDOMRect.right) + 10,
|
|
60
|
-
}
|
|
61
|
-
}
|
|
62
|
-
|
|
63
|
-
// Position flyout left of event, facing downwards, when possible
|
|
64
|
-
if (
|
|
65
|
-
spaceLeft > flyoutNeededWidth
|
|
66
|
-
&& spaceBottom > flyoutDimensions.height
|
|
67
|
-
) {
|
|
68
|
-
return {
|
|
69
|
-
top: topWhenSpaceTopIsNegative || eventElementDOMRect.top,
|
|
70
|
-
left: Math.round(
|
|
71
|
-
eventElementDOMRect.left - (flyoutDimensions.width + 10)
|
|
72
|
-
),
|
|
73
|
-
}
|
|
74
|
-
}
|
|
75
|
-
|
|
76
|
-
// Position flyout left of event, facing upwards when possible
|
|
77
|
-
if (spaceLeft > flyoutNeededWidth && spaceTop > flyoutDimensions.height) {
|
|
78
|
-
return {
|
|
79
|
-
top: topWhenSpaceToBottomIsNegative || Math.round(eventElementDOMRect.bottom - flyoutDimensions.height),
|
|
80
|
-
left: Math.round(
|
|
81
|
-
eventElementDOMRect.left - (flyoutDimensions.width + 10)
|
|
82
|
-
),
|
|
83
|
-
}
|
|
84
|
-
}
|
|
85
|
-
|
|
86
|
-
// Fallback for smaller screens - scenario 1
|
|
87
|
-
// Flyout is glued to the bottom of the calendar and horizontally centered
|
|
88
|
-
if (spaceBottom < flyoutDimensions.height) {
|
|
89
|
-
return { top: calendarDomRect.bottom - flyoutDimensions.height, left: null }
|
|
90
|
-
}
|
|
91
|
-
|
|
92
|
-
// Fallback for smaller screens - scenario 2
|
|
93
|
-
// Flyout is placed vertically based on the top of the event, and centered horizontally
|
|
94
|
-
return { top: eventElementDOMRect.top, left: null }
|
|
95
|
-
}
|
|
96
|
-
}
|
|
@@ -1,154 +0,0 @@
|
|
|
1
|
-
import type { DayInterface } from '../typings/interfaces/day.interface'
|
|
2
|
-
/**
|
|
3
|
-
* The following class contains methods for calculating where to position
|
|
4
|
-
* calendar events within a given day
|
|
5
|
-
*/
|
|
6
|
-
import type { EventInterface } from '../typings/interfaces/event.interface'
|
|
7
|
-
import type { FullDayEventsWeek } from '../typings/interfaces/full-day-events-week.type'
|
|
8
|
-
import Time from './Time'
|
|
9
|
-
|
|
10
|
-
interface eventWithJSDatesInterface extends EventInterface {
|
|
11
|
-
timeJS: {
|
|
12
|
-
start: Date
|
|
13
|
-
end: Date
|
|
14
|
-
}
|
|
15
|
-
}
|
|
16
|
-
|
|
17
|
-
export default class EventPosition extends Time {
|
|
18
|
-
/**
|
|
19
|
-
* Yields a full calendar week, with all full-day events positioned in it
|
|
20
|
-
*/
|
|
21
|
-
positionFullDayEventsInWeek(weekStart: Date, weekEnd: Date, events: EventInterface[]) {
|
|
22
|
-
// 1. add timeJS.start and timeJS.end to all objects
|
|
23
|
-
const eventsWithJSDates: eventWithJSDatesInterface[] = events.map((scheduleEvent: EventInterface) => {
|
|
24
|
-
const { year: startYear, month: startMonth, date: startDate } = this.getAllVariablesFromDateTimeString(scheduleEvent.time.start)
|
|
25
|
-
const { year: endYear, month: endMonth, date: endDate } = this.getAllVariablesFromDateTimeString(scheduleEvent.time.end)
|
|
26
|
-
scheduleEvent.timeJS = {
|
|
27
|
-
start: new Date(startYear, startMonth, startDate),
|
|
28
|
-
end: new Date(endYear, endMonth, endDate),
|
|
29
|
-
}
|
|
30
|
-
|
|
31
|
-
return scheduleEvent as eventWithJSDatesInterface
|
|
32
|
-
}).sort((a, b) => {
|
|
33
|
-
if (a.time.start < b.time.start) return -1
|
|
34
|
-
if (a.time.start > b.time.start) return 1
|
|
35
|
-
|
|
36
|
-
return 0
|
|
37
|
-
})
|
|
38
|
-
|
|
39
|
-
// 2. create a week array, where each day is represented as an object with different levels, level1, level2, level3, level4 etc.
|
|
40
|
-
// An event starts on a certain level, the first day when it occurs, and then blocks that level for the rest of its duration
|
|
41
|
-
const allDatesOfWeek = this.getDatesBetweenTwoDates(weekStart, weekEnd)
|
|
42
|
-
const week: FullDayEventsWeek = allDatesOfWeek.map(d => ({ date: d }))
|
|
43
|
-
|
|
44
|
-
for (const scheduleEvent of eventsWithJSDates) {
|
|
45
|
-
for (const [dayIndex, day] of week.entries()) {
|
|
46
|
-
const thisDayDateString = this.getDateStringFromDate(day.date)
|
|
47
|
-
|
|
48
|
-
if (
|
|
49
|
-
this.getDateStringFromDate(scheduleEvent.timeJS.start) <= thisDayDateString
|
|
50
|
-
&& this.getDateStringFromDate(scheduleEvent.timeJS.end) >= thisDayDateString
|
|
51
|
-
) {
|
|
52
|
-
// 2A. Get the first free level of the day
|
|
53
|
-
let levelToStartOn = 1
|
|
54
|
-
while (typeof week[dayIndex][`level${levelToStartOn}`] !== 'undefined') {
|
|
55
|
-
levelToStartOn++
|
|
56
|
-
}
|
|
57
|
-
|
|
58
|
-
// 2B. set the event on this day
|
|
59
|
-
let eventNDays = (Math.ceil((scheduleEvent.timeJS.end.getTime() - day.date.getTime()) / this.MS_PER_DAY) + 1) // Get difference in days, plus the first day itself
|
|
60
|
-
const remainingDaysOfWeek = (week.length - dayIndex)
|
|
61
|
-
if (eventNDays > remainingDaysOfWeek) eventNDays = remainingDaysOfWeek
|
|
62
|
-
|
|
63
|
-
week[dayIndex][`level${levelToStartOn}`] = {
|
|
64
|
-
...scheduleEvent,
|
|
65
|
-
nDays: eventNDays, // Denotes the number of days to display in the week, not the actual number of days
|
|
66
|
-
}
|
|
67
|
-
|
|
68
|
-
// 2C. And block the specified level, for the following days of the event
|
|
69
|
-
for (let i = 1; i < eventNDays; i++) {
|
|
70
|
-
week[dayIndex + i][`level${levelToStartOn}`] = 'blocked'
|
|
71
|
-
}
|
|
72
|
-
|
|
73
|
-
break
|
|
74
|
-
}
|
|
75
|
-
}
|
|
76
|
-
}
|
|
77
|
-
|
|
78
|
-
const weekWithSortedLevelsInDays = []
|
|
79
|
-
|
|
80
|
-
// 3. Sort the levels of the day objects
|
|
81
|
-
for (const day of week) {
|
|
82
|
-
weekWithSortedLevelsInDays.push(Object.keys(day).sort().reduce(
|
|
83
|
-
(obj: any, key: any) => {
|
|
84
|
-
obj[key] = day[key]
|
|
85
|
-
return obj
|
|
86
|
-
},
|
|
87
|
-
{}
|
|
88
|
-
))
|
|
89
|
-
}
|
|
90
|
-
|
|
91
|
-
return weekWithSortedLevelsInDays
|
|
92
|
-
}
|
|
93
|
-
|
|
94
|
-
positionFullDayEventsInMonth(
|
|
95
|
-
calendarMonth: DayInterface[][],
|
|
96
|
-
fullDayEvents: EventInterface[]
|
|
97
|
-
): DayInterface[][] {
|
|
98
|
-
const newMonth: DayInterface[][] = []
|
|
99
|
-
const flatMonth = calendarMonth.flat()
|
|
100
|
-
// Create a map, where each key is a dateString in the format of YYYY-MM-DD, and the value is the calendarDay. This will help us skip 2 levels of nested loops.
|
|
101
|
-
// Instead of iterating over the following units for => week of calendarMonth => day of week => event of fullDayEvents => date of allDatesOfEvent
|
|
102
|
-
// we can stay on 2 levels of nesting with for => fullDayEvent of fullDayEvents => date of allDatesOfEvent, and then see if the map has a matching date
|
|
103
|
-
const monthMap = new Map()
|
|
104
|
-
flatMonth.forEach(day => monthMap.set(this.dateStringFrom(day.dateTimeString), day))
|
|
105
|
-
// Sort events with the latest first. This will help the algorithm place the oldest events at the start of each "events" array later
|
|
106
|
-
fullDayEvents = fullDayEvents.sort((a, b) => {
|
|
107
|
-
if (a.time.start < b.time.start) return 1
|
|
108
|
-
if (a.time.start > b.time.start) return -1
|
|
109
|
-
|
|
110
|
-
return 0
|
|
111
|
-
})
|
|
112
|
-
|
|
113
|
-
for (const fullDayEvent of fullDayEvents) {
|
|
114
|
-
const { year: startYear, month: startMonth, date: startDate } = this.getAllVariablesFromDateTimeString(fullDayEvent.time.start)
|
|
115
|
-
const { year: endYear, month: endMonth, date: endDate } = this.getAllVariablesFromDateTimeString(fullDayEvent.time.end)
|
|
116
|
-
const allDatesOfEvent = this.getDatesBetweenTwoDates(
|
|
117
|
-
new Date(startYear, startMonth, startDate),
|
|
118
|
-
new Date(endYear, endMonth, endDate),
|
|
119
|
-
)
|
|
120
|
-
|
|
121
|
-
for (const date of allDatesOfEvent) {
|
|
122
|
-
const dateString = this.getDateStringFromDate(date)
|
|
123
|
-
const dateInMap = monthMap.get(dateString)
|
|
124
|
-
|
|
125
|
-
if (dateInMap) { monthMap.set(dateString, {
|
|
126
|
-
...dateInMap,
|
|
127
|
-
// Since we're iterating over the fullDayEvents sorted backwards, the earliest events will end up first (which is the wanted behavior)
|
|
128
|
-
events: [fullDayEvent, ...dateInMap.events]
|
|
129
|
-
})
|
|
130
|
-
}
|
|
131
|
-
}
|
|
132
|
-
}
|
|
133
|
-
|
|
134
|
-
let weekIterator = 0
|
|
135
|
-
|
|
136
|
-
monthMap.forEach((day) => {
|
|
137
|
-
// For the very first day, create an array for the first week, and push day onto it
|
|
138
|
-
if (!newMonth.length) { newMonth.push([day])
|
|
139
|
-
}
|
|
140
|
-
|
|
141
|
-
// When the week exists, and is not yet filled with 7 days, push day onto week
|
|
142
|
-
else if (newMonth[weekIterator] && newMonth[weekIterator].length < 7) { newMonth[weekIterator].push(day)
|
|
143
|
-
}
|
|
144
|
-
|
|
145
|
-
// When the week exists, but is full, create a new week with the day in it, and increment the week iterator
|
|
146
|
-
else if (newMonth[weekIterator] && newMonth[weekIterator].length === 7) {
|
|
147
|
-
newMonth.push([day])
|
|
148
|
-
weekIterator++
|
|
149
|
-
}
|
|
150
|
-
})
|
|
151
|
-
|
|
152
|
-
return newMonth
|
|
153
|
-
}
|
|
154
|
-
}
|
|
@@ -1,50 +0,0 @@
|
|
|
1
|
-
import type { EventInterface } from '../typings/interfaces/event.interface'
|
|
2
|
-
import type Time from './Time'
|
|
3
|
-
import { DAY_MODE } from '../typings/interfaces/time-modes'
|
|
4
|
-
|
|
5
|
-
export class EventsFilter {
|
|
6
|
-
constructor(private events: EventInterface[]) {}
|
|
7
|
-
|
|
8
|
-
public getEventsForDay(timeInstance: Time, startDateTimeString: string): EventInterface[] {
|
|
9
|
-
return this.events.filter(event => this.isEventInDayBoundaries(event, timeInstance, startDateTimeString))
|
|
10
|
-
}
|
|
11
|
-
|
|
12
|
-
private isEventInDayBoundaries(event: EventInterface, timeInstance: Time, startDateTimeString: string): boolean {
|
|
13
|
-
const eventIsInDay
|
|
14
|
-
= timeInstance.dateStringFrom(event.time.start) === timeInstance.dateStringFrom(startDateTimeString)
|
|
15
|
-
|
|
16
|
-
if (timeInstance.dayMode === DAY_MODE.REGULAR) {
|
|
17
|
-
return eventIsInDay
|
|
18
|
-
}
|
|
19
|
-
|
|
20
|
-
if (eventIsInDay && timeInstance.dayMode === DAY_MODE.SHORTENED) {
|
|
21
|
-
return this.handlePartialDayWithinOneDayBoundary(timeInstance, event)
|
|
22
|
-
}
|
|
23
|
-
|
|
24
|
-
if (timeInstance.dayMode === DAY_MODE.FLEXIBLE) {
|
|
25
|
-
return this.handleDayStretchingTwoDates(timeInstance, event, startDateTimeString, eventIsInDay)
|
|
26
|
-
}
|
|
27
|
-
|
|
28
|
-
return false
|
|
29
|
-
}
|
|
30
|
-
|
|
31
|
-
private handleDayStretchingTwoDates(timeInstance: Time, event: EventInterface, startDateTimeString: string, eventIsInDay: boolean) {
|
|
32
|
-
const { hour: dayStartHour } = timeInstance.getHourAndMinutesFromTimePoints(timeInstance.DAY_START)
|
|
33
|
-
const { hour: dayEndHour } = timeInstance.getHourAndMinutesFromTimePoints(timeInstance.DAY_END)
|
|
34
|
-
const { hour: eventStartHour } = timeInstance.getAllVariablesFromDateTimeString(event.time.start)
|
|
35
|
-
const nextDay = timeInstance.addDaysToDateTimeString(1, startDateTimeString)
|
|
36
|
-
const eventStartsInNextDay = event.time.start.substring(0, 11) === nextDay.substring(0, 11)
|
|
37
|
-
|
|
38
|
-
return eventIsInDay && eventStartHour >= dayStartHour
|
|
39
|
-
|| eventStartsInNextDay && eventStartHour < dayEndHour
|
|
40
|
-
}
|
|
41
|
-
|
|
42
|
-
private handlePartialDayWithinOneDayBoundary(timeInstance: Time, event: EventInterface) {
|
|
43
|
-
const { hour: dayStartHour } = timeInstance.getHourAndMinutesFromTimePoints(timeInstance.DAY_START)
|
|
44
|
-
const { hour: dayEndHour } = timeInstance.getHourAndMinutesFromTimePoints(timeInstance.DAY_END)
|
|
45
|
-
const { hour: eventStartHour } = timeInstance.getAllVariablesFromDateTimeString(event.time.start)
|
|
46
|
-
|
|
47
|
-
// TODO: add check for event end time overlapping the day start time
|
|
48
|
-
return eventStartHour >= dayStartHour && eventStartHour < dayEndHour
|
|
49
|
-
}
|
|
50
|
-
}
|
|
@@ -1,37 +0,0 @@
|
|
|
1
|
-
import type { EventInterface } from '../typings/interfaces/event.interface'
|
|
2
|
-
import { DAY_MODE } from '../typings/interfaces/time-modes'
|
|
3
|
-
import Helpers from './Helpers'
|
|
4
|
-
import Time from './Time'
|
|
5
|
-
|
|
6
|
-
export class WeekHelper {
|
|
7
|
-
public static getNHoursIntoDayFromHour(hour: number, timeInstance: Time): number {
|
|
8
|
-
const dayStartHour = Time.getHourFromTimePoints(timeInstance.DAY_START)
|
|
9
|
-
|
|
10
|
-
if (timeInstance.dayMode === DAY_MODE.REGULAR) return hour
|
|
11
|
-
|
|
12
|
-
if (
|
|
13
|
-
timeInstance.dayMode === DAY_MODE.SHORTENED
|
|
14
|
-
|| (timeInstance.dayMode === DAY_MODE.FLEXIBLE && hour >= dayStartHour)
|
|
15
|
-
) {
|
|
16
|
-
return hour - dayStartHour
|
|
17
|
-
}
|
|
18
|
-
|
|
19
|
-
return (24 - dayStartHour) + hour
|
|
20
|
-
}
|
|
21
|
-
|
|
22
|
-
public static eventSeparator(events: EventInterface[], time: Time) {
|
|
23
|
-
const singleDayTimedEvents: EventInterface[] = []
|
|
24
|
-
const fullDayAndMultipleDayEvents: EventInterface[] = []
|
|
25
|
-
|
|
26
|
-
for (const scheduleEvent of events) {
|
|
27
|
-
const eventType = Helpers.getEventType(scheduleEvent, time)
|
|
28
|
-
if (['SINGLE_DAY_TIMED', 'SINGLE_HYBRID_DAY_TIMED'].includes(eventType)) {
|
|
29
|
-
singleDayTimedEvents.push(scheduleEvent)
|
|
30
|
-
} else {
|
|
31
|
-
fullDayAndMultipleDayEvents.push(scheduleEvent)
|
|
32
|
-
}
|
|
33
|
-
}
|
|
34
|
-
|
|
35
|
-
return { fullDayAndMultipleDayEvents, singleDayTimedEvents }
|
|
36
|
-
}
|
|
37
|
-
}
|
|
@@ -1,41 +0,0 @@
|
|
|
1
|
-
import { languageKeys } from './keys'
|
|
2
|
-
|
|
3
|
-
export const localeMap = new Map<string, string>([
|
|
4
|
-
['de', 'de-DE'],
|
|
5
|
-
['en', 'en-US'],
|
|
6
|
-
['it', 'it-IT'],
|
|
7
|
-
['sv', 'sv-SE'],
|
|
8
|
-
['zh', 'zh-CN'],
|
|
9
|
-
['pt', 'pt-BR'],
|
|
10
|
-
['fr', 'fr-FR'],
|
|
11
|
-
['th', 'th-TH'],
|
|
12
|
-
['nl', 'nl-NL'],
|
|
13
|
-
['ru', 'ru-RU'],
|
|
14
|
-
['ar', 'ar-YE'],
|
|
15
|
-
['es', 'es-ES'],
|
|
16
|
-
['ja', 'ja-JP'],
|
|
17
|
-
['pl', 'pl-PL'],
|
|
18
|
-
['hu', 'hu-HU'],
|
|
19
|
-
['he', 'he-IL']
|
|
20
|
-
])
|
|
21
|
-
|
|
22
|
-
export function overrideShortLocaleWithLongLocale(locale: string): string {
|
|
23
|
-
if (localeMap.has(locale)) {
|
|
24
|
-
locale = localeMap.get(locale) as string
|
|
25
|
-
}
|
|
26
|
-
|
|
27
|
-
return locale
|
|
28
|
-
}
|
|
29
|
-
|
|
30
|
-
export function getLanguage(languageKeys: any, locale: string = 'en-US') {
|
|
31
|
-
locale = overrideShortLocaleWithLongLocale(locale)
|
|
32
|
-
|
|
33
|
-
return languageKeys[locale]
|
|
34
|
-
}
|
|
35
|
-
export function translate(key: string, locale: string = 'en-US') {
|
|
36
|
-
const language: { [key: string]: any } = languageKeys[key as keyof typeof languageKeys] || {}
|
|
37
|
-
|
|
38
|
-
return language[locale] || key
|
|
39
|
-
}
|
|
40
|
-
|
|
41
|
-
export { languageKeys }
|