UNPKG

@progress/kendo-ui

Version:

This package is part of the [Kendo UI for jQuery](http://www.telerik.com/kendo-ui) suite.

1,454 lines (1,167 loc) 177 kB
module.exports = /******/ (function(modules) { // webpackBootstrap /******/ // The module cache /******/ var installedModules = {}; /******/ // The require function /******/ function __webpack_require__(moduleId) { /******/ // Check if module is in cache /******/ if(installedModules[moduleId]) /******/ return installedModules[moduleId].exports; /******/ // Create a new module (and put it into the cache) /******/ var module = installedModules[moduleId] = { /******/ exports: {}, /******/ id: moduleId, /******/ loaded: false /******/ }; /******/ // Execute the module function /******/ modules[moduleId].call(module.exports, module, module.exports, __webpack_require__); /******/ // Flag the module as loaded /******/ module.loaded = true; /******/ // Return the exports of the module /******/ return module.exports; /******/ } /******/ // expose the modules object (__webpack_modules__) /******/ __webpack_require__.m = modules; /******/ // expose the module cache /******/ __webpack_require__.c = installedModules; /******/ // __webpack_public_path__ /******/ __webpack_require__.p = ""; /******/ // Load entry module and return exports /******/ return __webpack_require__(0); /******/ }) /************************************************************************/ /******/ ({ /***/ 0: /***/ (function(module, exports, __webpack_require__) { module.exports = __webpack_require__(1282); /***/ }), /***/ 3: /***/ (function(module, exports) { module.exports = function() { throw new Error("define cannot be used indirect"); }; /***/ }), /***/ 1003: /***/ (function(module, exports) { module.exports = require("./kendo.dom"); /***/ }), /***/ 1015: /***/ (function(module, exports) { module.exports = require("./kendo.data"); /***/ }), /***/ 1282: /***/ (function(module, exports, __webpack_require__) { var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;(function(f, define){ !(__WEBPACK_AMD_DEFINE_ARRAY__ = [ __webpack_require__(1003), __webpack_require__(1015) ], __WEBPACK_AMD_DEFINE_FACTORY__ = (f), __WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ? (__WEBPACK_AMD_DEFINE_FACTORY__.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__)) : __WEBPACK_AMD_DEFINE_FACTORY__), __WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__)); })(function(){ var __meta__ = { // jshint ignore:line id: "pivotgrid", name: "PivotGrid", category: "web", description: "The PivotGrid widget is a data summarization tool.", depends: [ "dom", "data", "data.xml", "sortable" ], features: [{ id: "pivotgrid-configurator", name: "Configurator", description: "The PivotConfigurator widget allows the user to select data slices displayed in PivotGrid", depends: [ "pivot.configurator" ] }, { id: "pivotgrid-filtering", name: "Filtering", description: "Support for filtering", depends: [ "pivot.fieldmenu" ] }, { id: "pivotgrid-excel-export", name: "Excel export", description: "Export pivot grid data as Excel spreadsheet", depends: [ "ooxml" ] }, { id: "pivotgrid-pdf-export", name: "PDF export", description: "Export pivot grid data as PDF", depends: [ "pdf", "drawing" ] }, { id: "mobile-scroller", name: "Mobile scroller", description: "Support for kinetic scrolling in mobile device", depends: [ "mobile.scroller" ] }] }; /*jshint eqnull: true*/ (function($, undefined) { var kendo = window.kendo, ui = kendo.ui, Class = kendo.Class, Widget = ui.Widget, DataSource = kendo.data.DataSource, outerWidth = kendo._outerWidth, outerHeight = kendo._outerHeight, toString = {}.toString, identity = function(o) { return o; }, map = $.map, extend = $.extend, isFunction = kendo.isFunction, CHANGE = "change", ERROR = "error", MEASURES = "Measures", PROGRESS = "progress", STATERESET = "stateReset", AUTO = "auto", DIV = "<div/>", NS = ".kendoPivotGrid", ROW_TOTAL_KEY = "__row_total__", DATABINDING = "dataBinding", DATABOUND = "dataBound", EXPANDMEMBER = "expandMember", COLLAPSEMEMBER = "collapseMember", STATE_EXPANDED = "k-i-collapse", STATE_COLLAPSED = "k-i-expand", HEADER_TEMPLATE = "<span>#: data.member.caption || data.member.name #</span>", KPISTATUS_TEMPLATE = '<span class="k-icon k-i-kpi-status-#=data.dataItem.value > 0 ? \"open\" : data.dataItem.value < 0 ? \"deny\" : \"hold\"#" title="#:data.dataItem.value#"></span>', KPITREND_TEMPLATE = '<span class="k-icon k-i-kpi-trend-#=data.dataItem.value > 0 ? \"increase\" : data.dataItem.value < 0 ? \"decrease\" : \"equal\"#" title="#:data.dataItem.value#"></span>', DATACELL_TEMPLATE = '#= data.dataItem ? kendo.htmlEncode(data.dataItem.fmtValue || data.dataItem.value) || "&nbsp;" : "&nbsp;" #', LAYOUT_TABLE = '<table class="k-pivot-layout">' + '<tr>' + '<td>' + '<div class="k-pivot-rowheaders"></div>' + '</td>' + '<td>' + '<div class="k-pivot-table k-state-default"></div>' + '</td>' + '</tr>' + '</table>'; var AXIS_ROWS = "rows"; var AXIS_COLUMNS = "columns"; function normalizeMeasures(measure) { var descriptor = typeof measure === "string" ? [{ name: measure }] : measure; var descriptors = toString.call(descriptor) === "[object Array]" ? descriptor : (descriptor !== undefined ? [descriptor] : []); return map(descriptors, function(d) { if (typeof d === "string") { return { name: d }; } return { name: d.name, type: d.type }; }); } function normalizeMembers(member) { var descriptor = typeof member === "string" ? [{ name: [member], expand: false }] : member; var descriptors = toString.call(descriptor) === "[object Array]" ? descriptor : (descriptor !== undefined ? [descriptor] : []); return map(descriptors, function(d) { if (typeof d === "string") { return { name: [d], expand: false }; } return { name: (toString.call(d.name) === "[object Array]" ? d.name.slice() : [d.name]), expand: d.expand }; }); } function normalizeName(name) { if (name.indexOf(" ") !== -1) { name = '["' + name + '"]'; } return name; } function accumulateMembers(accumulator, rootTuple, tuple, level) { var idx, length; var children; var member; if (!tuple) { tuple = rootTuple; } if (!level) { level = 0; } member = tuple.members[level]; if (!member || member.measure) { //return if no member or measure return; } children = member.children; length = children.length; if (tuple === rootTuple) { accumulator[kendo.stringify([member.name])] = !!length; } else if (length) { accumulator[kendo.stringify(buildPath(tuple, level))] = true; } if (length) { for (idx = 0; idx < length; idx++) { accumulateMembers(accumulator, rootTuple, children[idx], level); } } accumulateMembers(accumulator, rootTuple, tuple, level + 1); } function descriptorsForAxes(tuples) { var result = {}; if (tuples.length) { accumulateMembers(result, tuples[0]); } var descriptors = []; for (var k in result) { descriptors.push({ name: $.parseJSON(k), expand: result[k] }); } return descriptors; } function addMissingPathMembers(members, axis) { var tuples = axis.tuples || []; var firstTuple = tuples[0]; if (firstTuple && members.length < firstTuple.members.length) { var tupleMembers = firstTuple.members; for (var idx = 0; idx < tupleMembers.length; idx++) { if (tupleMembers[idx].measure) { continue; } var found = false; for (var j = 0; j < members.length; j++) { if (getName(members[j]).indexOf(tupleMembers[idx].hierarchy) === 0) { found = true; break; } } if (!found) { members.push({ name: [tupleMembers[idx].name], expand: false }); //calling normalize here to make name from string to array } } } } function tupleToDescriptors(tuple) { var result = []; var members = tuple.members; for (var idx = 0; idx < members.length; idx++) { if (members[idx].measure) { continue; } //make tuple name an array result.push({ name: [members[idx].name], expand: members[idx].children.length > 0}); } return result; } function descriptorsForMembers(axis, members, measures) { axis = axis || {}; addMissingPathMembers(members, axis); if (measures.length > 1) { members.push({ name: MEASURES, measure: true, children: normalizeMembers(measures) }); } var tupletoSearch = { members: members }; if (axis.tuples) { var result = findExistingTuple(axis.tuples, tupletoSearch); if (result.tuple) { members = tupleToDescriptors(result.tuple); } } return members; } function createAggregateGetter(m) { var measureGetter = kendo.getter(m.field, true); return function(aggregatorContext, state) { return m.aggregate(measureGetter(aggregatorContext.dataItem), state, aggregatorContext); }; } function isNumber(val) { return typeof val === "number" && !isNaN(val); } function isDate(val) { return val && val.getTime; } var functions = { sum: function(value, state) { var accumulator = state.accumulator; if (!isNumber(accumulator)) { accumulator = value; } else if (isNumber(value)) { accumulator += value; } return accumulator; }, count: function(value, state) { return (state.accumulator || 0) + 1; }, average: { aggregate: function(value, state) { var accumulator = state.accumulator; if (state.count === undefined) { state.count = 0; } if (!isNumber(accumulator)) { accumulator = value; } else if (isNumber(value)) { accumulator += value; } if (isNumber(value)) { state.count++; } return accumulator; }, result: function(state) { var accumulator = state.accumulator; if (isNumber(accumulator)) { accumulator = accumulator / state.count; } return accumulator; } }, max: function(value, state) { var accumulator = state.accumulator; if (!isNumber(accumulator) && !isDate(accumulator)) { accumulator = value; } if(accumulator < value && (isNumber(value) || isDate(value))) { accumulator = value; } return accumulator; }, min: function(value, state) { var accumulator = state.accumulator; if (!isNumber(accumulator) && !isDate(accumulator)) { accumulator = value; } if(accumulator > value && (isNumber(value) || isDate(value))) { accumulator = value; } return accumulator; } }; var PivotCubeBuilder = Class.extend({ init: function(options) { this.options = extend({}, this.options, options); this.dimensions = this._normalizeDescriptors("field", this.options.dimensions); this.measures = this._normalizeDescriptors("name", this.options.measures); }, _normalizeDescriptors: function(keyField, descriptors) { descriptors = descriptors || {}; var fields = {}; var field; if (toString.call(descriptors) === "[object Array]") { for (var idx = 0, length = descriptors.length; idx < length; idx++) { field = descriptors[idx]; if (typeof field === "string") { fields[field] = {}; } else if (field[keyField]) { fields[field[keyField]] = field; } } descriptors = fields; } return descriptors; }, _rootTuples: function(rootNames, measureAggregators) { var aggregatorsLength = measureAggregators.length || 1; var dimensionsSchema = this.dimensions || []; var root, name, parts; var measureIdx = 0; var idx; var rootNamesLength = rootNames.length; var result = []; var keys = []; if (rootNamesLength || measureAggregators.length) { for (measureIdx = 0; measureIdx < aggregatorsLength; measureIdx++) { root = { members: [] }; for (idx = 0; idx < rootNamesLength; idx++) { name = rootNames[idx]; parts = name.split("&"); root.members[root.members.length] = { children: [], caption: (dimensionsSchema[name] || {}).caption || "All", name: name, levelName: name, levelNum: "0", hasChildren: true, parentName: parts.length > 1 ? parts[0] : undefined, hierarchy: name }; } if (aggregatorsLength > 1) { root.members[root.members.length] = { children: [], caption: (measureAggregators[measureIdx]).caption, name: measureAggregators[measureIdx].descriptor.name, levelName: "MEASURES", levelNum: "0", hasChildren: false, parentName: undefined, hierarchy: "MEASURES" }; } result[result.length] = root; } keys.push(ROW_TOTAL_KEY); } return { keys: keys, tuples: result }; }, _expandedTuples: function(map, expanded, measureAggregators) { var aggregatorsLength = measureAggregators.length || 1; var dimensionsSchema = this.dimensions || []; var measureIdx; var tuple; var key; var mapItem; var current; var currentKeys; var accumulator = []; var accumulatorKeys = []; var memberInfo; var expandedNames; var parts; var name; var idx; for (key in map) { mapItem = map[key]; memberInfo = this._findExpandedMember(expanded, mapItem.uniquePath); current = accumulator[memberInfo.index] || []; currentKeys = accumulatorKeys[memberInfo.index] || []; expandedNames = memberInfo.member.names; for (measureIdx = 0; measureIdx < aggregatorsLength; measureIdx++) { tuple = { members: [] }; for (idx = 0; idx < expandedNames.length; idx++) { if (idx === memberInfo.member.expandedIdx) { tuple.members[tuple.members.length] = { children: [], caption: mapItem.value, name: mapItem.name, hasChildren: false, levelNum: 1, levelName: mapItem.parentName + mapItem.name, parentName: mapItem.parentName, hierarchy: mapItem.parentName + mapItem.name }; if (measureIdx === 0) { currentKeys.push(buildPath(tuple, idx).join("")); } } else { name = expandedNames[idx]; parts = name.split("&"); tuple.members[tuple.members.length] = { children: [], caption: (dimensionsSchema[name] || {}).caption || "All", name: name, levelName: name, levelNum: "0", hasChildren: true, parentName: parts.length > 1 ? parts[0] : undefined, hierarchy: name }; } } if (aggregatorsLength > 1) { tuple.members[tuple.members.length] = { children: [], caption: measureAggregators[measureIdx].caption, name: measureAggregators[measureIdx].descriptor.name, levelName: "MEASURES", levelNum: "0", hasChildren: true, parentName: undefined, hierarchy: "MEASURES" }; } current[current.length] = tuple; } accumulator[memberInfo.index] = current; accumulatorKeys[memberInfo.index] = currentKeys; } return { keys: accumulatorKeys, tuples: accumulator }; }, _findExpandedMember: function(members, parentName) { for (var idx = 0; idx < members.length; idx++) { if (members[idx].uniquePath === parentName) { return { member: members[idx], index: idx }; } } }, _asTuples: function(map, descriptor, measureAggregators) { measureAggregators = measureAggregators || []; var rootInfo = this._rootTuples(descriptor.root, measureAggregators); var expandedInfo = this._expandedTuples(map, descriptor.expanded, measureAggregators); return { keys: [].concat.apply(rootInfo.keys, expandedInfo.keys), tuples: [].concat.apply(rootInfo.tuples, expandedInfo.tuples) }; }, _measuresInfo: function(measures, rowAxis) { var idx = 0; var length = measures && measures.length; var aggregateNames = []; var resultFuncs= {}; var formats = {}; var descriptors = (this.measures || {}); var measure; var name; for (; idx < length; idx++) { name = measures[idx].descriptor.name; measure = descriptors[name] || {}; aggregateNames.push(name); if (measure.result) { resultFuncs[name] = measure.result; } if (measure.format) { formats[name] = measure.format; } } return { names: aggregateNames, formats: formats, resultFuncs: resultFuncs, rowAxis: rowAxis }; }, _toDataArray: function(map, measuresInfo, rowKeys, columnKeys) { var result = []; var aggregates; var name, i, j, k, n; var row, column, columnKey; var rowMeasureNamesLength = 1; var rowMeasureNames = []; var columnMeasureNames; var rowLength = rowKeys.length || 1; var columnLength = columnKeys.length || 1; if (measuresInfo.rowAxis) { rowMeasureNames = measuresInfo.names; rowMeasureNamesLength = rowMeasureNames.length; } else { columnMeasureNames = measuresInfo.names; } for (i = 0; i < rowLength; i++) { row = map[rowKeys[i] || ROW_TOTAL_KEY]; for (n = 0; n < rowMeasureNamesLength; n++) { if (measuresInfo.rowAxis) { columnMeasureNames = [rowMeasureNames[n]]; } for (j = 0; j < columnLength; j++) { columnKey = columnKeys[j] || ROW_TOTAL_KEY; column = row.items[columnKey]; if (columnKey === ROW_TOTAL_KEY) { aggregates = row.aggregates; } else { aggregates = column ? column.aggregates : {}; } for (k = 0; k < columnMeasureNames.length; k++) { name = columnMeasureNames[k]; this._addData(result, aggregates[name], measuresInfo.formats[name], measuresInfo.resultFuncs[name]); } } } } return result; }, _addData: function(result, value, format, resultFunc) { var fmtValue = ""; var ordinal; if (value) { value = resultFunc ? resultFunc(value) : value.accumulator; fmtValue = format ? kendo.format(format, value) : value; } ordinal = result.length; result[ordinal] = { ordinal: ordinal, value: value || "", fmtValue: fmtValue }; }, _matchDescriptors: function(dataItem, descriptor, getters) { var parts; var parentField; var expectedValue; var names = descriptor.names; var idx = descriptor.expandedIdx; var value; while (idx > 0) { parts = names[--idx].split("&"); if (parts.length > 1) { parentField = parts[0]; expectedValue = parts[1]; value = getters[parentField](dataItem); value = (value !== undefined && value !== null) ? value.toString() : value; if (value != expectedValue) { return false; } } } return true; }, _calculateAggregate: function(measureAggregators, aggregatorContext, totalItem) { var result = {}; var state; var name; for (var measureIdx = 0; measureIdx < measureAggregators.length; measureIdx++) { name = measureAggregators[measureIdx].descriptor.name; state = totalItem.aggregates[name] || { }; state.accumulator = measureAggregators[measureIdx].aggregator(aggregatorContext, state); result[name] = state; } return result; }, _processColumns: function(measureAggregators, descriptors, getters, columns, aggregatorContext, rowTotal, state, updateColumn) { var value; var descriptor; var column; var totalItem; var key, name, parentName, path; var dataItem = aggregatorContext.dataItem; var idx = 0; for (; idx < descriptors.length; idx++) { descriptor = descriptors[idx]; //checks whether the dataItem is relevant to the descriptors if (!this._matchDescriptors(dataItem, descriptor, getters)) { continue; } path = descriptor.names.slice(0, descriptor.expandedIdx).join(""); name = descriptor.names[descriptor.expandedIdx]; value = getters[name](dataItem); value = (value !== undefined && value !== null) ? value.toString() : value; parentName = name; name = name + "&" + value; key = path + name; column = columns[key] || { index: state.columnIndex, parentName: parentName, name: name, uniquePath: path + parentName, value: value }; totalItem = rowTotal.items[key] || { aggregates: {} }; rowTotal.items[key] = { index: column.index, aggregates: this._calculateAggregate(measureAggregators, aggregatorContext, totalItem) }; if (updateColumn) { if (!columns[key]) { state.columnIndex++; } columns[key] = column; } } }, _measureAggregators: function(options) { var measureDescriptors = options.measures || []; var measures = this.measures || {}; var aggregators = []; var descriptor, measure, idx, length; var defaultAggregate, aggregate; if (measureDescriptors.length) { for (idx = 0, length = measureDescriptors.length; idx < length; idx++) { descriptor = measureDescriptors[idx]; measure = measures[descriptor.name]; defaultAggregate = null; if (measure) { aggregate = measure.aggregate; if (typeof aggregate === "string") { defaultAggregate = functions[aggregate.toLowerCase()]; if (!defaultAggregate) { throw new Error("There is no such aggregate function"); } measure.aggregate = defaultAggregate.aggregate || defaultAggregate; measure.result = defaultAggregate.result; } aggregators.push({ descriptor: descriptor, caption: measure.caption, result: measure.result, aggregator: createAggregateGetter(measure) }); } } } else { aggregators.push({ descriptor: { name: "default"}, caption: "default", aggregator: function() { return 1; } }); } return aggregators; }, _buildGetters: function(names) { var result = {}; var parts; var name; for (var idx = 0; idx < names.length; idx++) { name = names[idx]; parts = name.split("&"); if (parts.length > 1) { result[parts[0]] = kendo.getter(parts[0], true); } else { result[name] = kendo.getter(normalizeName(name), true); } } return result; }, _parseDescriptors: function (descriptors) { var parsedDescriptors = parseDescriptors(descriptors); var rootNames = getRootNames(parsedDescriptors.root); var expanded = parsedDescriptors.expanded; var result = []; for (var idx = 0; idx < expanded.length; idx++) { result.push(mapNames(expanded[idx].name, rootNames)); } return { root: rootNames, expanded: result }; }, _filter: function(data, filter) { if (!filter) { return data; } var expr; var idx = 0; var filters = filter.filters; for (; idx < filters.length; idx++) { expr = filters[idx]; if (expr.operator === "in") { filters[idx] = this._normalizeFilter(expr); } } return new kendo.data.Query(data).filter(filter).data; }, _normalizeFilter: function(filter) { var value = filter.value.split(","); var result = []; if (!value.length) { return value; } for (var idx = 0; idx < value.length; idx++) { result.push({ field: filter.field, operator: "eq", value: value[idx] }); } return { logic: "or", filters: result }; }, process: function(data, options) { data = data || []; options = options || {}; data = this._filter(data, options.filter); var measures = options.measures || []; var measuresRowAxis = options.measuresAxis === "rows"; var columnDescriptors = options.columns || []; var rowDescriptors = options.rows || []; if (!columnDescriptors.length && rowDescriptors.length && (!measures.length || (measures.length && measuresRowAxis))) { columnDescriptors = rowDescriptors; rowDescriptors = []; measuresRowAxis = false; } if (!columnDescriptors.length && !rowDescriptors.length) { measuresRowAxis = false; } if (!columnDescriptors.length && measures.length) { columnDescriptors = normalizeMembers(options.measures); } columnDescriptors = this._parseDescriptors(columnDescriptors); rowDescriptors = this._parseDescriptors(rowDescriptors); var aggregatedData = {}; var columns = {}; var rows = {}; var rowValue; var state = { columnIndex: 0 }; var measureAggregators = this._measureAggregators(options); var columnGetters = this._buildGetters(columnDescriptors.root); var rowGetters = this._buildGetters(rowDescriptors.root); var processed = false; var expandedColumns = columnDescriptors.expanded; var expandedRows = rowDescriptors.expanded; var dataItem; var aggregatorContext; var hasExpandedRows = expandedRows.length !== 0; var rowIdx, rowDescriptor, rowName, rowTotal; var key, path, parentName, value; var columnsInfo, rowsInfo; var length = data.length; var idx = 0; if (columnDescriptors.root.length || rowDescriptors.root.length) { processed = true; for (idx = 0; idx < length; idx++) { dataItem = data[idx]; aggregatorContext = { dataItem: dataItem, index: idx }; rowTotal = aggregatedData[ROW_TOTAL_KEY] || { items: {}, aggregates: {} }; this._processColumns(measureAggregators, expandedColumns, columnGetters, columns, aggregatorContext, rowTotal, state, !hasExpandedRows); rowTotal.aggregates = this._calculateAggregate(measureAggregators, aggregatorContext, rowTotal); aggregatedData[ROW_TOTAL_KEY] = rowTotal; for (rowIdx = 0; rowIdx < expandedRows.length; rowIdx++) { rowDescriptor = expandedRows[rowIdx]; if (!this._matchDescriptors(dataItem, rowDescriptor, rowGetters)) { this._processColumns(measureAggregators, expandedColumns, columnGetters, columns, aggregatorContext, { items: {}, aggregates: {} }, state, true); continue; } path = rowDescriptor.names.slice(0, rowDescriptor.expandedIdx).join(""); rowName = rowDescriptor.names[rowDescriptor.expandedIdx]; parentName = rowName; rowValue = rowGetters[rowName](dataItem); rowValue = rowValue !== undefined ? rowValue.toString() : rowValue; rowName = rowName + "&" + rowValue; key = path + rowName; rows[key] = { uniquePath: path + parentName, parentName: parentName, name: rowName, value: rowValue }; value = aggregatedData[key] || { items: {}, aggregates: {} }; this._processColumns(measureAggregators, expandedColumns, columnGetters, columns, aggregatorContext, value, state, true); value.aggregates = this._calculateAggregate(measureAggregators, aggregatorContext, value); aggregatedData[key] = value; } } } if (processed && length) { if (measureAggregators.length > 1 && (!options.columns || !options.columns.length)) { columnDescriptors = { root: [], expanded: [] }; } columnsInfo = this._asTuples(columns, columnDescriptors, measuresRowAxis ? [] : measureAggregators); rowsInfo = this._asTuples(rows, rowDescriptors, measuresRowAxis ? measureAggregators : []); columns = columnsInfo.tuples; rows = rowsInfo.tuples; aggregatedData = this._toDataArray(aggregatedData, this._measuresInfo(measureAggregators, measuresRowAxis), rowsInfo.keys, columnsInfo.keys); } else { aggregatedData = columns = rows = []; } return { axes: { columns: { tuples: columns }, rows: { tuples: rows } }, data: aggregatedData }; } }); var PivotTransport = Class.extend({ init: function(options, transport) { this.transport = transport; this.options = transport.options || {}; if (!this.transport.discover) { if (isFunction(options.discover)) { this.discover = options.discover; } } }, read: function(options) { return this.transport.read(options); }, update: function(options) { return this.transport.update(options); }, create: function(options) { return this.transport.create(options); }, destroy: function(options) { return this.transport.destroy(options); }, discover: function(options) { if (this.transport.discover) { return this.transport.discover(options); } options.success({}); }, catalog: function(val) { var options = this.options || {}; if (val === undefined) { return (options.connection || {}).catalog; } var connection = options.connection || {}; connection.catalog = val; this.options.connection = connection; $.extend(this.transport.options, { connection: connection }); }, cube: function(val) { var options = this.options || {}; if (val === undefined) { return (options.connection || {}).cube; } var connection = options.connection || {}; connection.cube = val; this.options.connection = connection; extend(true, this.transport.options, { connection: connection }); } }); var PivotDataSource = DataSource.extend({ init: function(options) { var cube = ((options || {}).schema || {}).cube; var measuresAxis = "columns"; var measures; var schema = { axes: identity, cubes: identity, catalogs: identity, measures: identity, dimensions: identity, hierarchies: identity, levels: identity, members: identity }; if (cube) { schema = $.extend(schema, this._cubeSchema(cube)); this.cubeBuilder = new PivotCubeBuilder(cube); } DataSource.fn.init.call(this, extend(true, {}, { schema: schema }, options)); this.transport = new PivotTransport(this.options.transport || {}, this.transport); this._columns = normalizeMembers(this.options.columns); this._rows = normalizeMembers(this.options.rows); measures = this.options.measures || []; if (toString.call(measures) === "[object Object]") { measuresAxis = measures.axis || "columns"; measures = measures.values || []; } this._measures = normalizeMeasures(measures); this._measuresAxis = measuresAxis; this._skipNormalize = 0; this._axes = {}; }, _cubeSchema: function(cube) { return { dimensions: function() { var result = []; var dimensions = cube.dimensions; for (var key in dimensions) { result.push({ name: key, caption: dimensions[key].caption || key, uniqueName: key, defaultHierarchy: key, type: 1 }); } if (cube.measures) { result.push({ name: MEASURES, caption: MEASURES, uniqueName: MEASURES, type: 2 }); } return result; }, hierarchies: function(){ return []; }, measures: function() { var result = []; var measures = cube.measures; for (var key in measures) { result.push({ name: key, caption: key, uniqueName: key, aggregator: key }); } return result; }, members: $.proxy(function(response, restrictions) { var name = restrictions.levelUniqueName || restrictions.memberUniqueName; var schemaData = this.options.schema.data; var dataGetter = isFunction(schemaData) ? schemaData : kendo.getter(schemaData, true); var data = (this.options.data && dataGetter(this.options.data)) || this._rawData || []; var result = []; var getter; var value; var idx = 0; var distinct = {}; if (name) { name = name.split(".")[0]; } if (!restrictions.treeOp) { result.push({ caption: cube.dimensions[name].caption || name, childrenCardinality: "1", dimensionUniqueName: name, hierarchyUniqueName: name, levelUniqueName: name, name: name, uniqueName: name }); return result; } getter = kendo.getter(normalizeName(name), true); for (; idx < data.length; idx++) { value = getter(data[idx]); if ((value || value === 0) && !distinct[value]) { distinct[value] = true; result.push({ caption: value, childrenCardinality: "0", dimensionUniqueName: name, hierarchyUniqueName: name, levelUniqueName: name, name: value, uniqueName: value }); } } return result; }, this) }; }, options: { serverSorting: true, serverPaging: true, serverFiltering: true, serverGrouping: true, serverAggregates: true }, catalog: function(val) { if (val === undefined) { return this.transport.catalog(); } this.transport.catalog(val); this._mergeState({});// clears current state this._axes = {}; this.data([]); }, cube: function(val) { if (val === undefined) { return this.transport.cube(); } this.transport.cube(val); this._axes = {}; this._mergeState({});// clears current state this.data([]); }, axes: function() { return this._axes; }, columns: function(val) { if (val === undefined) { return this._columns; } this._skipNormalize += 1; this._clearAxesData = true; this._columns = normalizeMembers(val); this.query({ columns: val, rows: this.rowsAxisDescriptors(), measures: this.measures(), sort: this.sort(), filter: this.filter() }); }, rows: function(val) { if (val === undefined) { return this._rows; } this._skipNormalize += 1; this._clearAxesData = true; this._rows = normalizeMembers(val); this.query({ columns: this.columnsAxisDescriptors(), rows: val, measures: this.measures(), sort: this.sort(), filter: this.filter() }); }, measures: function(val) { if (val === undefined) { return this._measures; } this._skipNormalize += 1; this._clearAxesData = true; this.query({ columns: this.columnsAxisDescriptors(), rows: this.rowsAxisDescriptors(), measures: normalizeMeasures(val), sort: this.sort(), filter: this.filter() }); }, measuresAxis: function() { return this._measuresAxis || "columns"; }, _expandPath: function(path, axis) { var origin = axis === "columns" ? "columns" : "rows"; var other = axis === "columns" ? "rows" : "columns"; var members = normalizeMembers(path); var memberToExpand = getName(members[members.length - 1]); this._lastExpanded = origin; members = descriptorsForMembers(this.axes()[origin], members, this.measures()); for (var idx = 0; idx < members.length; idx++) { var memberName = getName(members[idx]); if (memberName === memberToExpand) { if (members[idx].expand) { return; } members[idx].expand = true; } else { members[idx].expand = false; } } var descriptors = {}; descriptors[origin] = members; descriptors[other] = this._descriptorsForAxis(other); this._query(descriptors); }, _descriptorsForAxis: function(axis) { var axes = this.axes(); var descriptors = this[axis]() || []; if (axes && axes[axis] && axes[axis].tuples && axes[axis].tuples[0]) { descriptors = descriptorsForAxes(axes[axis].tuples || []); } return descriptors; }, columnsAxisDescriptors: function() { return this._descriptorsForAxis("columns"); }, rowsAxisDescriptors: function() { return this._descriptorsForAxis("rows"); }, _process: function (data, e) { this._view = data; e = e || {}; e.items = e.items || this._view; this.trigger(CHANGE, e); }, _query: function(options) { var that = this; if (!options) { this._skipNormalize += 1; this._clearAxesData = true; } return that.query(extend({}, { page: that.page(), pageSize: that.pageSize(), sort: that.sort(), filter: that.filter(), group: that.group(), aggregate: that.aggregate(), columns: this.columnsAxisDescriptors(), rows: this.rowsAxisDescriptors(), measures: this.measures() }, options)); }, query: function(options) { var state = this._mergeState(options); if (this._data.length && this.cubeBuilder) { this._params(state); this._updateLocalData(this._pristineData); return $.Deferred().resolve().promise(); } return this.read(state); }, _mergeState: function(options) { options = DataSource.fn._mergeState.call(this, options); if (options !== undefined) {