SwarmOnline / Ext.ux.TouchCalendar

Sencha Touch Calendar component
113 stars 47 forks source link

hasManu based events store not displaying event bars properly #11

Closed sharpmonkey closed 11 years ago

sharpmonkey commented 11 years ago

Scenario: Model.Event (id, user_id) Model.User (id) User hasMany Events

calendar store is set to user.events() store, which contains user_id filter

when bars are rendered with TouchCalendarEvents all bars take up whole month (displayed days) since sencha store doesn't support multiple filters (or I didn't know how to make them work).

My fix in Ext.ux.TouchCalendarEvents.js was to remove store.filterBy (line 305) and replace it with the same condition inside store.each, before eventBarIndex. Removed store.clearFilter() (line 384) as well.

Changed source function:

   generateEventBars: function () {
        /**
        * @property {Ext.data.Store} eventBarStore Store to store the Event Bar definitions. It is defined 
        * with the Ext.ux.CalendarEventBarModel model.
        * @private
        */
        this.eventBarStore = Ext.create('Ext.data.Store', {
            model: 'Ext.ux.CalendarEventBarModel',
            data: []
        });

        var dates = this.calendar.getStore();
        var store = this.calendar.eventStore;
        var eventBarRecord;

        // Loop through Calendar's date collection of visible dates
        dates.each(function (dateObj) {
            var currentDate = dateObj.get('date'),
        currentDateTime = Ext.Date.clearTime(currentDate, true).getTime(),
        takenDatePositions = []; // stores 'row positions' that are taken on current date

            // sort the Events Store so we have a consistent ordering to ensure no overlaps
            store.sort(this.startEventField, 'ASC');

            // Loop through currentDate's Events
            store.each(function (event) {

                // Filter event that is happening on the currentDate
                var startDate = Ext.Date.clearTime(event.get(this.startEventField), true).getTime();
                var endDate = Ext.Date.clearTime(event.get(this.endEventField), true).getTime();
                if (!(startDate <= currentDateTime && currentDateTime <= endDate))
                    return;

                // Find any Event Bar record in the EventBarStore for the current Event's record (using internalID)
                var eventBarIndex = this.eventBarStore.findBy(function (record, id) {
                    return record.get('EventID') === event.internalId;
                }, this);

                // if an EventBarRecord was found then it is a multiple day Event so we must link them
                if (eventBarIndex > -1) {
                    eventBarRecord = this.eventBarStore.getAt(eventBarIndex); // get the actual EventBarRecord

                    // recurse down the linked EventBarRecords to get the last record in the chain for
                    // wrapping Events
                    while (eventBarRecord.linked().getCount() > 0) {
                        eventBarRecord = eventBarRecord.linked().getAt(eventBarRecord.linked().getCount() - 1);
                    }

                    // if currentDate is at the start of the week then we must create a new EventBarRecord
                    // to represent the new bar on the next row.
                    if (currentDate.getDay() === this.calendar.weekStart) {
                        // push the inherited BarPosition of the parent 
                        // EventBarRecord onto the takenDatePositions array
                        takenDatePositions.push(eventBarRecord.get('BarPosition'));

                        // create a new EventBar record 
                        var wrappedEventBarRecord = Ext.ModelMgr.create({
                            EventID: event.internalId,
                            Date: currentDate,
                            BarLength: 1,
                            BarPosition: eventBarRecord.get('BarPosition'),
                            Colour: eventBarRecord.get('Colour'),
                            Record: event
                        }, 'Ext.ux.CalendarEventBarModel');

                        // add it as a linked EventBar of the parent
                        eventBarRecord.linked().add(wrappedEventBarRecord);
                    }
                    else {
                        // add the inherited BarPosition to the takenDatePositions array
                        takenDatePositions.push(eventBarRecord.get('BarPosition'));

                        // increment the BarLength value for this day
                        eventBarRecord.set('BarLength', eventBarRecord.get('BarLength') + 1);
                    }
                }
                else {
                    // get the next free bar position
                    var barPos = this.getNextFreePosition(takenDatePositions);

                    // push it onto array so it isn't reused
                    takenDatePositions.push(barPos);

                    // create new EventBar record
                    eventBarRecord = Ext.ModelMgr.create({
                        EventID: event.internalId,
                        Date: currentDate,
                        BarLength: 1,
                        BarPosition: barPos,
                        Colour: this.getRandomColour(),
                        Record: event
                    }, 'Ext.ux.CalendarEventBarModel');

                    // add EventBar record to main store
                    this.eventBarStore.add(eventBarRecord);
                }

            }, this);
        }, this);
    },
Stuart98 commented 11 years ago

Thanks for the bug report and patch! I will try and integrate it as soon as possible.