angular-ui / ui-calendar

A complete AngularJS directive for the Arshaw FullCalendar.
http://angular-ui.github.io/ui-calendar/
MIT License
1.49k stars 727 forks source link

myCalendar is undefined #418

Open RonAlmog opened 8 years ago

RonAlmog commented 8 years ago

the component works, but i can't reach the fullCalendar object. my html: <div ui-calendar="vm.uiConfig.calendar" class="calendar" ng-model="vm.eventSources" calendar="myCalendar"></div>

in my controller: ` vm.uiConfig = { calendar:{ lang: 'en', height: 450, editable: false, allDaySlot: false, defaultView: 'agendaWeek', timezone: 'local', minTime: '14:00', maxTime: '23:00',

    header:{
      left: 'agendaDay,agendaWeek',
      center: 'title',
      right: 'today prev,next'
    },
    dayClick: vm.dayClick,
    eventDrop: vm.alertOnDrop,
    eventResize: vm.alertOnResize,
    eventClick: vm.eventClick,
    viewRender: vm.renderView
  }    
};`

uiCalendarConfig is injected in my controller. The problem is that in the following line, the uiCalendarConfig exists, and even has calendars object in it, but it's empty. so obviously, Cannot read property 'fullCalendar' of undefined. uiCalendarConfig.calendars.myCalendar.fullCalendar('changeView', 'agendaDay' );

Any idea?

froasiooneloop commented 8 years ago

Same problem here, I can't find a way to solve it.

RonAlmog commented 8 years ago

i found a solution. not that great, but it solves the problem. give it a little wait, like this:

setTimeout(function(){ uiCalendarConfig.calendars.myCalendar.fullCalendar('changeView', 'agendaWeek' ); }, 200);

froasiooneloop commented 8 years ago

Couldn't you solve it watching that variable with angular ? Maybe better than the timeout, I'll try that way.

AlexVKO commented 8 years ago

Here is my workarround...

instead of using this

uiCalendarConfig.calendars.myCalendar.fullCalendar('removeEvents');

I using this

angular.element('.calendar').fullCalendar('removeEvents');
giquo commented 8 years ago

hi people, i deal with that some months ago Now i'm checking my code again and think on this: What if the directive use scope.$emit to indicate that the calendar exists, I mean, something that tell us that the calendar is ready, and when.

I enter to the source code and in the method

scope.initCalendar

i put some silly

scope.$emit('ui-calendar-initialized', calendar);

then in my controller i get rid of this with

$scope.$on('ui-calendar-initialized'....

what do ya think?

tsuz commented 7 years ago

It doesn't work for me anymore. This seems to be the only reliable method to receive 'onload' callback:

// watcher for on load
var calendarOnLoad = null;
var calendarOnLoadCallbacks = [];

$scope.changeView = function(view) {

    if(uiCalendarConfig.calendars.eventsCalendar) {
        // already initiated or beat the race condition, great!
       uiCalendarConfig.calendars.eventsCalendar.fullCalendar('changeView',view);
    }
    else {
        // calendar is undefined. watch for onload
        if(!calendarOnLoad) {
            calendarOnLoad = $scope.$watch(function () {
                // prevent type error which breaks the app
                try {
                    return uiCalendarConfig.calendars.eventsCalendar;
                } catch (err) {
                    return null;
                }
            }, function (calendar) {
                // uiCalendarConfig.calendars.eventsCalendar is now initiated
                if(calendar) {
                    calendarOnLoad(); // clear watcher since calendar exists
                    // call all the callbacks queued
                    calendarOnLoadCallbacks.forEach(function (fn) {
                        fn(calendar);
                    });
                }
            });
        }

        // run this calendarOnLoadCallbacks queue once calendar is initiated
        calendarOnLoadCallbacks.push(function(calendar) {
            calendar.fullCalendar('changeView',view);
        });

    }
}

$scope.changeView('agendaWeek');
$scope.changeView('month');
$scope.changeView('agendaDay');