diff --git a/addons/web/static/src/js/views/pivot/pivot_controller.js b/addons/web/static/src/js/views/pivot/pivot_controller.js
index 48b5fb033fa..a573a6fa4cb 100644
--- a/addons/web/static/src/js/views/pivot/pivot_controller.js
+++ b/addons/web/static/src/js/views/pivot/pivot_controller.js
@@ -336,7 +336,8 @@ var PivotController = AbstractController.extend({
var col_id = $target.data('id');
var measure = $target.data('measure');
var isAscending = $target.hasClass('o_pivot_measure_row_sorted_asc');
- this.model.sortRows(col_id, measure, isAscending);
+ var dataType = $target.data('data_type');
+ this.model.sortRows(col_id, measure, isAscending, dataType);
this.update({}, {reload: false});
},
/**
diff --git a/addons/web/static/src/js/views/pivot/pivot_model.js b/addons/web/static/src/js/views/pivot/pivot_model.js
index 1a0d3625440..5a6423fbe34 100644
--- a/addons/web/static/src/js/views/pivot/pivot_model.js
+++ b/addons/web/static/src/js/views/pivot/pivot_model.js
@@ -457,16 +457,23 @@ var PivotModel = AbstractModel.extend({
* @param {any} col_id
* @param {any} measure
* @param {any} descending
+ * @param {'data'|'comparisonData'|'variation'} [dataType]
*/
- sortRows: function (col_id, measure, descending) {
+ sortRows: function (col_id, measure, descending, dataType) {
var cells = this.data.cells;
+ var comparisonFunction = compare;
+ if (this.data.compare) {
+ dataType = dataType || 'data';
+ comparisonFunction = specialCompare;
+ }
this._traverseTree(this.data.main_row.root, function (header) {
- header.children.sort(compare);
+ header.children.sort(comparisonFunction);
});
this.data.sorted_column = {
id: col_id,
measure: measure,
order: descending ? 'desc' : 'asc',
+ dataType: dataType,
};
function _getValue (id1, id2) {
if ((id1 in cells) && (id2 in cells[id1])) {
@@ -476,12 +483,26 @@ var PivotModel = AbstractModel.extend({
}
function compare (row1, row2) {
- var values1 = _getValue(row1.id, col_id),
- values2 = _getValue(row2.id, col_id),
- value1 = values1 ? values1[measure] : 0,
- value2 = values2 ? values2[measure] : 0;
+ var values1 = _getValue(row1.id, col_id);
+ var values2 = _getValue(row2.id, col_id);
+ var value1 = values1 ? values1[measure] : 0;
+ var value2 = values2 ? values2[measure] : 0;
return descending ? value1 - value2 : value2 - value1;
}
+ function specialCompare (row1, row2) {
+ var values1 = _getValue(row1.id, col_id);
+ var values2 = _getValue(row2.id, col_id);
+ var value1 = values1 ? values1[measure] : {data: 0, comparisonData: 0, variation: {magnitude: 0}};
+ var value2 = values2 ? values2[measure] : {data: 0, comparisonData: 0, variation: {magnitude: 0}};
+ if (dataType === 'variation') {
+ return descending ?
+ value1[dataType].magnitude - value2[dataType].magnitude:
+ value2[dataType].magnitude - value1[dataType].magnitude;
+ }
+ return descending ?
+ value1[dataType] - value2[dataType]:
+ value2[dataType] - value1[dataType];
+ }
},
/**
* Toggle the active state for a given measure, then reload the data.
diff --git a/addons/web/static/src/js/views/pivot/pivot_renderer.js b/addons/web/static/src/js/views/pivot/pivot_renderer.js
index 68f2f4bf86d..d49550ab81e 100644
--- a/addons/web/static/src/js/views/pivot/pivot_renderer.js
+++ b/addons/web/static/src/js/views/pivot/pivot_renderer.js
@@ -116,6 +116,8 @@ var PivotRenderer = AbstractRenderer.extend({
_renderHeaders: function ($thead, headers, nbrCols) {
var self = this;
var i, j, cell, $row, $cell;
+ var measure, dataType;
+ var id, measureCellIds = [];
var groupbyLabels = _.map(this.state.colGroupBys, function (gb) {
return self.state.fields[gb.split(':')[0]].string;
@@ -144,10 +146,13 @@ var PivotRenderer = AbstractRenderer.extend({
$cell.data('id', cell.id);
}
if (cell.measure) {
+ measure = cell.measure;
+ measureCellIds.push(cell.id);
$cell.addClass('o_pivot_measure_row text-muted')
- .text(this.state.fields[cell.measure].string);
- $cell.data('id', cell.id).data('measure', cell.measure);
- if (!this.compare && cell.id === this.state.sortedColumn.id && cell.measure === this.state.sortedColumn.measure) {
+ .text(this.state.fields[measure].string);
+ $cell.data('id', cell.id).data('measure', measure);
+ if (cell.id === this.state.sortedColumn.id &&
+ measure === this.state.sortedColumn.measure) {
$cell.addClass('o_pivot_measure_row_sorted_' + this.state.sortedColumn.order);
if (this.state.sortedColumn.order == 'asc') {
$cell.attr('aria-sorted', 'ascending');
@@ -167,12 +172,30 @@ var PivotRenderer = AbstractRenderer.extend({
}
if (this.compare) {
var colLabels = [this.timeRangeDescription, this.comparisonTimeRangeDescription, 'Variation'];
+ var dataTypes = ['data', 'comparisonData', 'variation'];
$row = $('
');
for (i = 0; i < 3 * nbrCols; i++) {
+ id = measureCellIds[~~(i / 3)];
+ measure = this.state.measures[(~~(i / 3)) % this.state.measures.length];
+ dataType = dataTypes[i % 3];
$cell = $('| ')
+ .addClass('o_pivot_measure_row text-muted')
+ .data('data_type', dataType)
+ .data('id', id)
+ .data('measure', measure)
.text(colLabels[i % 3])
.attr('rowspan', 1)
.attr('colspan', 1);
+ if (dataType === this.state.sortedColumn.dataType &&
+ id === this.state.sortedColumn.id &&
+ measure === this.state.sortedColumn.measure) {
+ $cell.addClass('o_pivot_measure_row_sorted_' + this.state.sortedColumn.order);
+ if (this.state.sortedColumn.order === 'asc') {
+ $cell.attr('aria-sorted', 'ascending');
+ } else {
+ $cell.attr('aria-sorted', 'descending');
+ }
+ }
$row.append($cell);
}
$thead.append($row);
diff --git a/addons/web/static/tests/views/pivot_tests.js b/addons/web/static/tests/views/pivot_tests.js
index 8642a1e8e35..a665f91af10 100644
--- a/addons/web/static/tests/views/pivot_tests.js
+++ b/addons/web/static/tests/views/pivot_tests.js
@@ -1417,7 +1417,7 @@ QUnit.module('Views', {
actionManager.destroy();
});
- QUnit.test('export data in excel with comparison', function (assert) {
+ QUnit.test('export data in excel with comparison', function (assert) {
assert.expect(10);
this.data.partner.records[0].date = '2016-12-15';
@@ -1572,5 +1572,147 @@ QUnit.module('Views', {
unpatchDate();
actionManager.destroy();
});
+
+ QUnit.module('Sort in comparison mode', {
+ beforeEach: function () {
+ this.data.partner.records[0].date = '2016-12-15';
+ this.data.partner.records[1].date = '2016-12-17';
+ this.data.partner.records[2].date = '2016-11-22';
+ this.data.partner.records[3].date = '2016-11-03';
+
+ this.data.partner.fields.company_type = {string: "Company Type", type: "selection", selection: [["company", "Company"], ["individual", "individual"]], searchable: true, store: true, sortable: true};
+
+ this.data.partner.records[0].company_type = 'company';
+ this.data.partner.records[1].company_type = 'individual';
+ this.data.partner.records[2].company_type = 'company';
+ this.data.partner.records[3].company_type = 'individual';
+
+
+ this.unpatchDate = patchDate(2016, 11, 20, 1, 0, 0);
+
+ this.actualResult = function () {
+ var actualResult = $('.o_pivot .o_pivot_cell_value div').map(function() {
+ return $( this ).text();
+ }).get().join();
+ return actualResult;
+ };
+
+ // create an action manager to test the interactions with the search view
+ this.actionManager = createActionManager({
+ data: this.data,
+ archs: {
+ 'partner,false,pivot': '' +
+ '' +
+ '' +
+ '' +
+ '',
+ 'partner,false,search': '',
+ },
+ debug: 1,
+ });
+
+ this.actionManager.doAction({
+ res_model: 'partner',
+ type: 'ir.actions.act_window',
+ views: [[false, 'pivot']],
+ flags: {
+ pivot: {
+ additionalMeasures: ['product_id'],
+ }
+ }
+ });
+
+ // open time range menu
+ testUtils.dom.click($('.o_control_panel .o_time_range_menu_button'));
+ // select 'Today' as range
+ testUtils.fields.editInput($('.o_control_panel .o_time_range_selector'), 'this_month');
+ // check checkbox 'Compare To'
+ testUtils.dom.click($('.o_control_panel .o_time_range_menu .o_comparison_checkbox'));
+ // Click on 'Apply' button
+ testUtils.dom.click($('.o_control_panel .o_time_range_menu .o_apply_range'));
+ // We are in comparison mode
+ },
+ afterEach: function () {
+ this.unpatchDate();
+ this.actionManager.destroy();
+ },
+ }, function () {
+ QUnit.test('when clicking on measure, sort by "This Month" (period of interest)', function (assert) {
+ assert.expect(1);
+
+ // click on 'Foo' in column Total/Company
+ testUtils.dom.click($('.o_pivot_measure_row').eq(0));
+ var results = [
+ "12", "17", "-29.41%", "1", "2", "-50%", "13", "19", "-31.58%",
+ "12", "0", "100%", "12", "0" , "100%",
+ "1", "0", "100%", "1" , "0", "100%",
+ "0", "17", "-100%", "0", "17", "-100%",
+ "0", "2", "-100%", "0" , "2" , "-100%"
+ ];
+ assert.strictEqual(this.actualResult(), results.join());
+ });
+
+ QUnit.test(
+ 'click on a period of interest header sort according to the appropriate column ' +
+ 'first in ascending order then in descending order',
+ function (assert) {
+ assert.expect(2);
+
+ // click on 'This Month' in column Total/Individual/Foo
+ testUtils.dom.click($('.o_pivot_measure_row').eq(6));
+ var results = [
+ "12", "17", "-29.41%", "1", "2", "-50%", "13", "19", "-31.58%",
+ "1", "0", "100%", "1" , "0", "100%",
+ "12", "0", "100%", "12", "0" , "100%",
+ "0", "17", "-100%", "0", "17", "-100%",
+ "0", "2", "-100%", "0" , "2" , "-100%"
+ ];
+ var actualResult = $('.o_pivot .o_pivot_cell_value div').text();
+ assert.strictEqual(actualResult, results.join(''));
+
+ // click once again on 'This Month' in column Total/Individual/Foo
+ testUtils.dom.click($('.o_pivot_measure_row').eq(6));
+ results = [
+ "12", "17", "-29.41%", "1", "2", "-50%", "13", "19", "-31.58%",
+ "12", "0", "100%", "12", "0" , "100%",
+ "0", "17", "-100%", "0", "17", "-100%",
+ "0", "2", "-100%", "0" , "2" , "-100%",
+ "1", "0", "100%", "1" , "0", "100%"
+ ];
+ assert.strictEqual(this.actualResult(), results.join());
+ });
+
+ QUnit.test('click on a period of comparison header sort according to appropriate column',
+ function (assert) {
+ assert.expect(1);
+
+ // click on 'Previous Period' in column Total/Individual/Foo
+ testUtils.dom.click($('.o_pivot_measure_row').eq(7));
+ var results = [
+ "12", "17", "-29.41%", "1", "2", "-50%", "13", "19", "-31.58%",
+ "0", "2", "-100%", "0" , "2" , "-100%",
+ "12", "0", "100%", "12", "0" , "100%",
+ "1", "0", "100%", "1" , "0", "100%",
+ "0", "17", "-100%", "0", "17", "-100%"
+ ];
+ assert.strictEqual(this.actualResult(), results.join());
+ });
+
+ QUnit.test('click on a variation header sort according to appropriate column',
+ function (assert) {
+ assert.expect(1);
+
+ // click on 'Variation' in column Total/Individual/Foo
+ testUtils.dom.click($('.o_pivot_measure_row').eq(11));
+ var results = [
+ "12", "17", "-29.41%", "1", "2", "-50%", "13", "19", "-31.58%",
+ "12", "0", "100%", "12", "0" , "100%",
+ "1", "0", "100%", "1" , "0", "100%",
+ "0", "17", "-100%", "0", "17", "-100%",
+ "0", "2", "-100%", "0" , "2" , "-100%"
+ ];
+ assert.strictEqual(this.actualResult(), results.join());
+ });
+ });
});
});
|