Skip to content

Commit 1e1dc55

Browse files
authored
Merge pull request #160 from ctrl-q/allow-date-range
feat: Support multiple dates
2 parents dacb493 + 5467d36 commit 1e1dc55

File tree

3 files changed

+35
-14
lines changed

3 files changed

+35
-14
lines changed

README.md

+20
Original file line numberDiff line numberDiff line change
@@ -75,6 +75,26 @@ See [advanced Templated usage example](https://github.com/cloud-atlas-ai/obsidia
7575

7676
You can see the available fields an the [Event interface](https://github.com/cloud-atlas-ai/obsidian-ics/blob/master/src/IEvent.ts).
7777

78+
### Full Calendar
79+
80+
```javascript
81+
const { renderCalendar } = app.plugins.getPlugin("obsidian-full-calendar");
82+
const thisWeek = Array.from({length: 7}).map((_, weekday) => moment().set({weekday}).format("YYYY-MM-DD"))
83+
const icsPlugin = app.plugins.getPlugin('ics')
84+
const events = (await icsPlugin.getEvents(...thisWeek))
85+
.map(event => {
86+
const start = moment.unix(event.utime)
87+
const [endHours, endMinutes] = event.endTime.split(":")
88+
return {
89+
start: start.toDate(),
90+
end: start.set({hour: endHours, minute: endMinutes}).toDate(),
91+
title: event.summary,
92+
}
93+
}
94+
)
95+
renderCalendar(this.container, {events}).render()
96+
```
97+
7898
## Support
7999

80100
If you want to support my work, you can [buy me a coffee](https://www.buymeacoffee.com/muness)

src/icalUtils.ts

+13-12
Original file line numberDiff line numberDiff line change
@@ -42,7 +42,7 @@ function isExcluded(recurrenceDate: moment.Moment, exdateArray: moment.Moment[])
4242
return exdateArray.some(exDate => exDate.isSame(recurrenceDate, 'day'));
4343
}
4444

45-
function processRecurrenceOverrides(event: any, dayToMatch: string, excludedDates: moment.Moment[], matchingEvents: any[]) {
45+
function processRecurrenceOverrides(event: any, sortedDaysToMatch: string[], excludedDates: moment.Moment[], matchingEvents: any[]) {
4646
for (const date in event.recurrences) {
4747
const recurrence = event.recurrences[date];
4848
const recurrenceMoment = moment(date).startOf('day');
@@ -56,20 +56,20 @@ function processRecurrenceOverrides(event: any, dayToMatch: string, excludedDate
5656
recurrence.recurrent = true;
5757

5858
// Check if this override matches the dayToMatch
59-
if (moment(recurrence.start).isSame(dayToMatch, "day")) {
59+
if (moment(recurrence.start).isBetween(sortedDaysToMatch.first(), sortedDaysToMatch.last(), "day", "[]")) {
6060
console.debug(`Adding recurring event with override: ${recurrence.summary} on ${recurrenceMoment.format('YYYY-MM-DD')}`);
6161
recurrence.eventType = "recurring override";
6262
matchingEvents.push(recurrence);
6363
}
6464
}
6565
}
6666

67-
function processRecurringRules(event: any, dayToMatch: string, excludedDates: moment.Moment[], matchingEvents: any[]) {
68-
const localStartOfYesterday = moment(dayToMatch).subtract(1, 'day').startOf('day').toDate();
69-
const localEndOfTomorrow = moment(dayToMatch).add(1, 'day').endOf('day').toDate();
67+
function processRecurringRules(event: any, sortedDaysToMatch: string[], excludedDates: moment.Moment[], matchingEvents: any[]) {
68+
const localStartOfRange = moment(sortedDaysToMatch.first()).subtract(1, 'day').startOf('day').toDate();
69+
const localEndOfRange = moment(sortedDaysToMatch.last()).add(1, 'day').endOf('day').toDate();
7070

7171
// Get recurrence dates within the range
72-
const recurrenceDates = event.rrule.between(localStartOfYesterday, localEndOfTomorrow, true);
72+
const recurrenceDates = event.rrule.between(localStartOfRange, localEndOfRange, true);
7373

7474
recurrenceDates.forEach(recurrenceDate => {
7575
const recurrenceMoment = tz(recurrenceDate, event.rrule.origOptions.tzid || 'UTC');
@@ -87,7 +87,7 @@ function processRecurringRules(event: any, dayToMatch: string, excludedDates: mo
8787
delete clonedEvent.rrule;
8888
clonedEvent.recurrent = true;
8989

90-
if (moment(clonedEvent.start).isSame(dayToMatch, 'day')) {
90+
if (moment(clonedEvent.start).isBetween(sortedDaysToMatch.first(), sortedDaysToMatch.last(), 'day', '[]')) {
9191
console.debug(`Adding recurring event: ${clonedEvent.summary} ${clonedEvent.start} - ${clonedEvent.end}`);
9292
console.debug("Excluded dates:", excludedDates.map(date => date.format('YYYY-MM-DD')));
9393

@@ -102,7 +102,8 @@ function shouldIncludeOngoing(event: any, dayToMatch: string): boolean {
102102
return moment(dayToMatch).isBetween(moment(event.start), moment(event.end), "day");
103103
}
104104

105-
export function filterMatchingEvents(icsArray: any[], dayToMatch: string, showOngoing: boolean) {
105+
export function filterMatchingEvents(icsArray: any[], daysToMatch: string[], showOngoing: boolean) {
106+
const sortedDaysToMatch = [...daysToMatch].sort();
106107
return icsArray.reduce((matchingEvents, event) => {
107108
// Skip canceled parent events
108109
if (event.status && event.status.toUpperCase() === "CANCELLED") {
@@ -127,16 +128,16 @@ export function filterMatchingEvents(icsArray: any[], dayToMatch: string, showOn
127128

128129
// Process recurrence overrides to populate matching events and excluded dates
129130
if (event.recurrences) {
130-
processRecurrenceOverrides(event, dayToMatch, excludedDates, matchingEvents);
131+
processRecurrenceOverrides(event, sortedDaysToMatch, excludedDates, matchingEvents);
131132
}
132133

133134
// Process recurring rules, skipping overridden dates
134135
if (event.rrule) {
135-
processRecurringRules(event, dayToMatch, excludedDates, matchingEvents);
136+
processRecurringRules(event, sortedDaysToMatch, excludedDates, matchingEvents)
136137
}
137138

138139
// Process non-recurring events
139-
if (!event.recurrences && !event.rrule && moment(event.start).isSame(dayToMatch, "day")) {
140+
if (!event.recurrences && !event.rrule && moment(event.start).isBetween(sortedDaysToMatch.first(), sortedDaysToMatch.last(), "day", "[]")) {
140141
console.debug("Adding one-off event:", {
141142
summary: event.summary,
142143
start: event.start,
@@ -149,7 +150,7 @@ export function filterMatchingEvents(icsArray: any[], dayToMatch: string, showOn
149150
}
150151

151152
// Include ongoing events
152-
if (showOngoing && shouldIncludeOngoing(event, dayToMatch)) {
153+
if (showOngoing && daysToMatch.some(dayToMatch => shouldIncludeOngoing(event, dayToMatch))) {
153154
matchingEvents.push(event);
154155
}
155156

src/main.ts

+2-2
Original file line numberDiff line numberDiff line change
@@ -68,7 +68,7 @@ export default class ICSPlugin extends Plugin {
6868
}
6969

7070

71-
async getEvents(date: string): Promise<IEvent[]> {
71+
async getEvents(...dates: string[]): Promise<IEvent[]> {
7272
let events: IEvent[] = [];
7373
let errorMessages: string[] = []; // To store error messages
7474

@@ -97,7 +97,7 @@ export default class ICSPlugin extends Plugin {
9797

9898
// Exception handling for parsing and filtering
9999
try {
100-
dateEvents = dateEvents = filterMatchingEvents(icsArray, date, calendarSetting.format.showOngoing)
100+
dateEvents = dateEvents = filterMatchingEvents(icsArray, dates, calendarSetting.format.showOngoing)
101101
.filter(e => this.excludeTransparentEvents(e, calendarSetting))
102102
.filter(e => this.excludeDeclinedEvents(e, calendarSetting));
103103

0 commit comments

Comments
 (0)