2

I have been trying to make recurring events in fullcalendar, I really find dow feature helpful, but I really want to add date ranges to it.

In other words, dow : [1] will repeat a task for every single Monday, the problems is, I want to make it visible only in a date range I set.

Ploxer
  • 88
  • 1
  • 11
  • 1
    Does this work? http://stackoverflow.com/questions/15161654/recurring-events-in-fullcalendar/29393128#29393128 – DanielST Jul 13 '15 at 17:32

3 Answers3

3

You can not set ranges by using dow, you have to perform some custom functionality.

Lets suppose that you have fetched events data from your database which contains multiple event objects. each event object has start date end date property and also to and from properties which contains date range , isRecurring is a Boolean property which we will add true in case of recurring events otherwise it will be false.

Remember the recurring events take start and end time without date, you only need to give them time slots, like start = "16:00" and end = "20:00" You can extract time by using moment js like i did while initializing my event object

                {
                  title:'Recurring Event',
                  start: moment.utc(event.start).format('HH:mm'),
                  end: moment.utc(event.end).format('HH:mm'),
                  isRecurrring: event.isRecurring,
                  ranges: [{
                      start: moment(event.from),
                      end: moment(event.to),
                    }],
                }

I have used moment.utc() to ignore the timezone.

Now override the eventRender function while initializing your fullCalendar. Your eventRender function will be

eventRender: function(event, element, view){
    if (event.isRecurrring) {
      return (event.ranges.filter(function(range){
        return (moment(event.start).isBefore(range.end) &&
        moment(event.end).isAfter(range.start));
      }).length) > 0;
    }
  }
Amante Ninja
  • 647
  • 1
  • 6
  • 26
0

You coulded set ranges as this example:

repeatingEvents.push({
        title: "From: " + inputDateStart + " To: " + inputDateFinish,
        start: vm.timeStart,
        end: vm.timeFinish,
        dow: listDay,
        ranges: [{
            start: dateStart,
            end: dateFinish
        }]
    })

    $("#calendar").fullCalendar("refetchEvents");

So you can use both "dow" and "ranges". Hope help for you!

TVT. Jake
  • 279
  • 2
  • 7
0
function createCalendar() {
        vm.uiConfig = timeProfileFactory.getCalendarConfig();
        vm.uiConfig.calendar.eventClick = eventClick;
        vm.uiConfig.calendar.eventDrop = alertOnDrop;
        vm.uiConfig.calendar.eventResize = alertOnResize;
        vm.uiConfig.calendar.eventRender = eventRender;
        vm.uiConfig.calendar.select = selectSlot;
        vm.uiConfig.calendar.header.center = "title";

        vm.events = function(start, end, timezone, callback) {
            callback(repeatingEvents);
        }
        vm.eventSources = [vm.events];
    };

function selectSlot(start, end, jsEvent, view) {
        var allDay = !start.hasTime() && !end.hasTime();
        var offset = ((new Date()).getTimezoneOffset())/60;
        var dateStart = (new Date(start)).setHours(0, 0, 0, 0);      
        dateStart = new Date(dateStart);
        dateStart.setHours(dateStart.getHours() - offset);
        dateStart = dateStart.toISOString();

        var timeStart = (new Date(start)).toISOString();
        var timeEnd = (new Date(end)).toISOString();
        timeStart = timeStart.split('T')[0];
        timeEnd = timeEnd.split('T')[0];

        var length = repeatingEvents.length;
        if(positionEvent == -1 || repeatingEvents.length == 0) {
            positionEvent = 0;
        } else {
            positionEvent = repeatingEvents[length - 1].position + 1;
        }

        repeatingEvents.push({
            title: "From: " + start.format("DD/MM/YYYY"),
            start: start.format("HH:mm"),
            end: end.format("HH:mm"),
            dow: [new Date(start).getDay()],
            ranges: [{
                start: dateStart,
                end: null
            }],
            position: positionEvent,
            allDay: false
        });

        length++;
        if(repeatingEvents[length - 1].end == "00:00") {
            repeatingEvents[length - 1].end = "24:00";
        }
        if(allDay) {
            repeatingEvents[length - 1].allDay = true;
            repeatingEvents[length - 1].start = null;
            repeatingEvents[length - 1].end = null;
        }
        $("#calendar").fullCalendar("refetchEvents");
    };

function eventClick(event, date, jsEvent, view) {
        isOpenDialog = true;
        for(var i = 0; i < repeatingEvents.length; i++) {
            if(repeatingEvents[i].position == event.position && isOpenDialog) {
                selectIndex = i;
                vm.timeStart = repeatingEvents[i].start;
                vm.timeFinish = repeatingEvents[i].end;
                vm.dateStart = repeatingEvents[i].title.split(' ')[1];

                if(repeatingEvents[i].ranges[0].end == null) {
                    vm.dateFinish = "";
                    vm.radioValue = "never";
                } else {
                    vm.dateFinish = repeatingEvents[i].title.split(' ')[3];
                    vm.radioValue = "on";
                }

                angular.forEach(vm.checkDays, function(item) {
                    item.checked = false;
                });

                angular.forEach(event.dow, function(index) {
                    vm.checkDays[index].checked = true;
                })

                openDialog();    
                break;
            }
        }
    };

function alertOnResize(event, delta, revertFunc, jsEvent, ui, view) {
        for(var i in repeatingEvents) {
            if(repeatingEvents[i].position == event.position) {
                var timeFinish = event.end.format("HH:mm");
                if(timeFinish == "00:00") {
                    timeFinish = "24:00";
                }
                repeatingEvents[i].end = timeFinish;
                break;
            }
        }
        $("#calendar").fullCalendar("refetchEvents");
    };

function alertOnDrop(event, delta, revertFunc, jsEvent, ui, view) {
        for(var i in repeatingEvents) {
            if(repeatingEvents[i].position == event.position) {
                if(repeatingEvents[i].allDay || event.allDay) {
                    revertFunc();
                } else {
                    var timeStart = event.start.format("HH:mm");
                    var timeFinish = event.end.format("HH:mm");
                    var dateStart = repeatingEvents[i].ranges[0].start;
                    var dateFinish = repeatingEvents[i].ranges[0].end;
                    var oldTimeStart = repeatingEvents[i].start.split(':')[0]*3600 + repeatingEvents[i].start.split(':')[1]*60;
                    var newTimeStart = timeStart.split(':')[0]*3600 + timeStart.split(':')[1]*60;
                    var deltaHour = newTimeStart - oldTimeStart;
                    var deltaDay = (delta/1000 - deltaHour)/86400;
                    dateStart = new Date(dateStart);
                    dateStart.setDate(dateStart.getDate() + deltaDay);
                    dateStart = dateStart.toISOString();
                    var title;

                    if(dateFinish != null) {
                        dateFinish = new Date(dateFinish);
                        dateFinish.setDate(dateFinish.getDate() + deltaDay);
                        dateFinish = dateFinish.toISOString();
                        title = "From: " + moment(dateStart).format("DD/MM/YYYY") + " To: " + moment(dateFinish).format("DD/MM/YYYY");
                    } else {
                        title = "From: " + moment(dateStart).format("DD/MM/YYYY");
                    }

                    for(var j in event.dow) {
                        repeatingEvents[i].dow[j] = parseInt(repeatingEvents[i].dow[j]) + deltaDay;
                        if(repeatingEvents[i].dow[j] > 6) {
                            repeatingEvents[i].dow.splice(j, 1);
                        }
                    }

                    repeatingEvents[i].start = timeStart;
                    repeatingEvents[i].end = timeFinish;
                    repeatingEvents[i].ranges[0].start = dateStart;
                    repeatingEvents[i].ranges[0].end = dateFinish;
                    repeatingEvents[i].title = title;

                    if(timeFinish == "00:00") {
                        repeatingEvents[i].end = "24:00";
                    }
                    $("#calendar").fullCalendar("refetchEvents");
                }
                break;
            }
        }
    };

function eventRender(event, element, view) {
        var removeEvent = $("<i class='removeEvent icons8-delete pull-right'></i>");
        removeEvent.on("click", function() {
            isOpenDialog = false;
            vm.removeEvent(event);
        });
        element.find(".fc-content").prepend(removeEvent);

        var result;
        if(event.ranges[0].end == null) {
            result = (event.ranges.filter(function(range) {
                var startConvert = (new Date(event.start)).toISOString();
                return (event.start.isAfter(range.start) || startConvert == range.start);
            }).length) > 0;
        } else {
            result = (event.ranges.filter(function(range) {
                return (event.start.isBefore(range.end) && event.end.isAfter(range.start));
            }).length) > 0;
        }
        return result;
    };
TVT. Jake
  • 279
  • 2
  • 7