/**
* Kendo UI v2016.1.112 (http://www.telerik.com/kendo-ui)
* Copyright 2016 Telerik AD. All rights reserved.
*
* Kendo UI commercial licenses may be obtained at
* http://www.telerik.com/purchase/license-agreement/kendo-ui-complete
* If you do not own a commercial license, this file shall be governed by the trial license terms.
*/
(function (f, define) {
define('kendo.groupable', [
'kendo.core',
'kendo.draganddrop'
], f);
}(function () {
var __meta__ = {
id: 'groupable',
name: 'Groupable',
category: 'framework',
depends: [
'core',
'draganddrop'
],
advanced: true
};
(function ($, undefined) {
var kendo = window.kendo, Widget = kendo.ui.Widget, proxy = $.proxy, isRtl = false, NS = '.kendoGroupable', CHANGE = 'change', indicatorTmpl = kendo.template('
', { useWithBlock: false }), hint = function (target) {
return $('').css({
width: target.width(),
paddingLeft: target.css('paddingLeft'),
paddingRight: target.css('paddingRight'),
lineHeight: target.height() + 'px',
paddingTop: target.css('paddingTop'),
paddingBottom: target.css('paddingBottom')
}).html(target.attr(kendo.attr('title')) || target.attr(kendo.attr('field'))).prepend('');
}, dropCue = $('');
function dropCueOffsetTop(element) {
return element.position().top + 3;
}
var Groupable = Widget.extend({
init: function (element, options) {
var that = this, group = kendo.guid(), intializePositions = proxy(that._intializePositions, that), draggable, horizontalCuePosition, dropCuePositions = that._dropCuePositions = [];
Widget.fn.init.call(that, element, options);
isRtl = kendo.support.isRtl(element);
horizontalCuePosition = isRtl ? 'right' : 'left';
that.draggable = draggable = that.options.draggable || new kendo.ui.Draggable(that.element, {
filter: that.options.draggableElements,
hint: hint,
group: group
});
that.groupContainer = $(that.options.groupContainer, that.element).kendoDropTarget({
group: draggable.options.group,
dragenter: function (e) {
if (that._canDrag(e.draggable.currentTarget)) {
e.draggable.hint.find('.k-drag-status').removeClass('k-denied').addClass('k-add');
dropCue.css('top', dropCueOffsetTop(that.groupContainer)).css(horizontalCuePosition, 0).appendTo(that.groupContainer);
}
},
dragleave: function (e) {
e.draggable.hint.find('.k-drag-status').removeClass('k-add').addClass('k-denied');
dropCue.remove();
},
drop: function (e) {
var targetElement = e.draggable.currentTarget, field = targetElement.attr(kendo.attr('field')), title = targetElement.attr(kendo.attr('title')), sourceIndicator = that.indicator(field), dropCuePositions = that._dropCuePositions, lastCuePosition = dropCuePositions[dropCuePositions.length - 1], position;
if (!targetElement.hasClass('k-group-indicator') && !that._canDrag(targetElement)) {
return;
}
if (lastCuePosition) {
position = that._dropCuePosition(kendo.getOffset(dropCue).left + parseInt(lastCuePosition.element.css('marginLeft'), 10) * (isRtl ? -1 : 1) + parseInt(lastCuePosition.element.css('marginRight'), 10));
if (position && that._canDrop($(sourceIndicator), position.element, position.left)) {
if (position.before) {
position.element.before(sourceIndicator || that.buildIndicator(field, title));
} else {
position.element.after(sourceIndicator || that.buildIndicator(field, title));
}
that._change();
}
} else {
that.groupContainer.append(that.buildIndicator(field, title));
that._change();
}
}
}).kendoDraggable({
filter: 'div.k-group-indicator',
hint: hint,
group: draggable.options.group,
dragcancel: proxy(that._dragCancel, that),
dragstart: function (e) {
var element = e.currentTarget, marginLeft = parseInt(element.css('marginLeft'), 10), elementPosition = element.position(), left = isRtl ? elementPosition.left - marginLeft : elementPosition.left + element.outerWidth();
intializePositions();
dropCue.css({
top: dropCueOffsetTop(that.groupContainer),
left: left
}).appendTo(that.groupContainer);
this.hint.find('.k-drag-status').removeClass('k-denied').addClass('k-add');
},
dragend: function () {
that._dragEnd(this);
},
drag: proxy(that._drag, that)
}).on('click' + NS, '.k-button', function (e) {
e.preventDefault();
that._removeIndicator($(this).parent());
}).on('click' + NS, '.k-link', function (e) {
var current = $(this).parent(), newIndicator = that.buildIndicator(current.attr(kendo.attr('field')), current.attr(kendo.attr('title')), current.attr(kendo.attr('dir')) == 'asc' ? 'desc' : 'asc');
current.before(newIndicator).remove();
that._change();
e.preventDefault();
});
draggable.bind([
'dragend',
'dragcancel',
'dragstart',
'drag'
], {
dragend: function () {
that._dragEnd(this);
},
dragcancel: proxy(that._dragCancel, that),
dragstart: function (e) {
var element, marginRight, left;
if (!that.options.allowDrag && !that._canDrag(e.currentTarget)) {
e.preventDefault();
return;
}
intializePositions();
if (dropCuePositions.length) {
element = dropCuePositions[dropCuePositions.length - 1].element;
marginRight = parseInt(element.css('marginRight'), 10);
left = element.position().left + element.outerWidth() + marginRight;
} else {
left = 0;
}
},
drag: proxy(that._drag, that)
});
that.dataSource = that.options.dataSource;
if (that.dataSource && that._refreshHandler) {
that.dataSource.unbind(CHANGE, that._refreshHandler);
} else {
that._refreshHandler = proxy(that.refresh, that);
}
if (that.dataSource) {
that.dataSource.bind('change', that._refreshHandler);
that.refresh();
}
},
refresh: function () {
var that = this, dataSource = that.dataSource;
if (that.groupContainer) {
that.groupContainer.empty().append($.map(dataSource.group() || [], function (item) {
var fieldName = item.field;
var attr = kendo.attr('field');
var element = that.element.find(that.options.filter).filter(function () {
return $(this).attr(attr) === fieldName;
});
return that.buildIndicator(item.field, element.attr(kendo.attr('title')), item.dir);
}).join(''));
}
that._invalidateGroupContainer();
},
destroy: function () {
var that = this;
Widget.fn.destroy.call(that);
that.groupContainer.off(NS);
if (that.groupContainer.data('kendoDropTarget')) {
that.groupContainer.data('kendoDropTarget').destroy();
}
if (that.groupContainer.data('kendoDraggable')) {
that.groupContainer.data('kendoDraggable').destroy();
}
if (!that.options.draggable) {
that.draggable.destroy();
}
if (that.dataSource && that._refreshHandler) {
that.dataSource.unbind('change', that._refreshHandler);
that._refreshHandler = null;
}
that.groupContainer = that.element = that.draggable = null;
},
options: {
name: 'Groupable',
filter: 'th',
draggableElements: 'th',
messages: { empty: 'Drag a column header and drop it here to group by that column' }
},
indicator: function (field) {
var indicators = $('.k-group-indicator', this.groupContainer);
return $.grep(indicators, function (item) {
return $(item).attr(kendo.attr('field')) === field;
})[0];
},
buildIndicator: function (field, title, dir) {
return indicatorTmpl({
field: field.replace(/"/g, '\''),
dir: dir,
title: title,
ns: kendo.ns
});
},
descriptors: function () {
var that = this, indicators = $('.k-group-indicator', that.groupContainer), aggregates, names, field, idx, length;
aggregates = that.element.find(that.options.filter).map(function () {
var cell = $(this), aggregate = cell.attr(kendo.attr('aggregates')), member = cell.attr(kendo.attr('field'));
if (aggregate && aggregate !== '') {
names = aggregate.split(',');
aggregate = [];
for (idx = 0, length = names.length; idx < length; idx++) {
aggregate.push({
field: member,
aggregate: names[idx]
});
}
}
return aggregate;
}).toArray();
return $.map(indicators, function (item) {
item = $(item);
field = item.attr(kendo.attr('field'));
return {
field: field,
dir: item.attr(kendo.attr('dir')),
aggregates: aggregates || []
};
});
},
_removeIndicator: function (indicator) {
var that = this;
indicator.remove();
that._invalidateGroupContainer();
that._change();
},
_change: function () {
var that = this;
if (that.dataSource) {
that.dataSource.group(that.descriptors());
}
},
_dropCuePosition: function (position) {
var dropCuePositions = this._dropCuePositions;
if (!dropCue.is(':visible') || dropCuePositions.length === 0) {
return;
}
position = Math.ceil(position);
var lastCuePosition = dropCuePositions[dropCuePositions.length - 1], left = lastCuePosition.left, right = lastCuePosition.right, marginLeft = parseInt(lastCuePosition.element.css('marginLeft'), 10), marginRight = parseInt(lastCuePosition.element.css('marginRight'), 10);
if (position >= right && !isRtl || position < left && isRtl) {
position = {
left: lastCuePosition.element.position().left + (!isRtl ? lastCuePosition.element.outerWidth() + marginRight : -marginLeft),
element: lastCuePosition.element,
before: false
};
} else {
position = $.grep(dropCuePositions, function (item) {
return item.left <= position && position <= item.right || isRtl && position > item.right;
})[0];
if (position) {
position = {
left: isRtl ? position.element.position().left + position.element.outerWidth() + marginRight : position.element.position().left - marginLeft,
element: position.element,
before: true
};
}
}
return position;
},
_drag: function (event) {
var position = this._dropCuePosition(event.x.location);
if (position) {
dropCue.css({
left: position.left,
right: 'auto'
});
}
},
_canDrag: function (element) {
var field = element.attr(kendo.attr('field'));
return element.attr(kendo.attr('groupable')) != 'false' && field && (element.hasClass('k-group-indicator') || !this.indicator(field));
},
_canDrop: function (source, target, position) {
var next = source.next(), result = source[0] !== target[0] && (!next[0] || target[0] !== next[0] || (!isRtl && position > next.position().left || isRtl && position < next.position().left));
return result;
},
_dragEnd: function (draggable) {
var that = this, field = draggable.currentTarget.attr(kendo.attr('field')), sourceIndicator = that.indicator(field);
if (draggable !== that.options.draggable && !draggable.dropped && sourceIndicator) {
that._removeIndicator($(sourceIndicator));
}
that._dragCancel();
},
_dragCancel: function () {
dropCue.remove();
this._dropCuePositions = [];
},
_intializePositions: function () {
var that = this, indicators = $('.k-group-indicator', that.groupContainer), left;
that._dropCuePositions = $.map(indicators, function (item) {
item = $(item);
left = kendo.getOffset(item).left;
return {
left: parseInt(left, 10),
right: parseInt(left + item.outerWidth(), 10),
element: item
};
});
},
_invalidateGroupContainer: function () {
var groupContainer = this.groupContainer;
if (groupContainer && groupContainer.is(':empty')) {
groupContainer.html(this.options.messages.empty);
}
}
});
kendo.ui.plugin(Groupable);
}(window.kendo.jQuery));
return window.kendo;
}, typeof define == 'function' && define.amd ? define : function (a1, a2, a3) {
(a3 || a2)();
}));