diff --git a/src/controllers/controller.bar.js b/src/controllers/controller.bar.js index 554497b3053..882ab1a89cd 100644 --- a/src/controllers/controller.bar.js +++ b/src/controllers/controller.bar.js @@ -497,14 +497,33 @@ export default class BarController extends DatasetController { } _getAxis() { - const axis = {}; + const {chart} = this; + const scales = chart.scales; const firstScaleAxisId = this.getFirstScaleIdForIndexAxis(); - for (const dataset of this.chart.data.datasets) { - axis[valueOrDefault( - this.chart.options.indexAxis === 'x' ? dataset.xAxisID : dataset.yAxisID, firstScaleAxisId - )] = true; + const processedAxisIds = new Set(); + const processedStacks = new Set(); + const axis = []; + + for (const dataset of chart.data.datasets) { + const axisId = valueOrDefault( + chart.options.indexAxis === 'x' ? dataset.xAxisID : dataset.yAxisID, + firstScaleAxisId + ); + + if (!processedAxisIds.has(axisId)) { + processedAxisIds.add(axisId); + const scale = scales[axisId]; + const stack = scale && scale.options.stack; + + if (isNullOrUndef(stack)) { + axis.push(axisId); + } else if (!processedStacks.has(stack)) { + processedStacks.add(stack); + axis.push(axisId); + } + } } - return Object.keys(axis); + return axis; } /** @@ -639,15 +658,35 @@ export default class BarController extends DatasetController { const skipNull = options.skipNull; const maxBarThickness = valueOrDefault(options.maxBarThickness, Infinity); let center, size; - const axisCount = this._getAxisCount(); + if (ruler.grouped) { const stackCount = skipNull ? this._getStackCount(index) : ruler.stackCount; + const axisGroups = this._getAxis(); + const axisCount = axisGroups.length; const range = options.barThickness === 'flex' ? computeFlexCategoryTraits(index, ruler, options, stackCount * axisCount) : computeFitCategoryTraits(index, ruler, options, stackCount * axisCount); - const axisID = this.chart.options.indexAxis === 'x' ? this.getDataset().xAxisID : this.getDataset().yAxisID; - const axisNumber = this._getAxis().indexOf(valueOrDefault(axisID, this.getFirstScaleIdForIndexAxis())); - const stackIndex = this._getStackIndex(this.index, this._cachedMeta.stack, skipNull ? index : undefined) + axisNumber; + + const dataset = this.getDataset(); + const axisID = this.chart.options.indexAxis === 'x' ? dataset.xAxisID : dataset.yAxisID; + const firstScaleId = this.getFirstScaleIdForIndexAxis(); + const actualAxisID = valueOrDefault(axisID, firstScaleId); + const axisScale = this.chart.scales[actualAxisID]; + const axisStack = axisScale && axisScale.options.stack; + + let axisNumber = axisGroups.indexOf(actualAxisID); + if (axisNumber === -1 && defined(axisStack)) { + for (let i = 0; i < axisGroups.length; i++) { + const groupScale = this.chart.scales[axisGroups[i]]; + if (groupScale && groupScale.options.stack === axisStack) { + axisNumber = i; + break; + } + } + } + axisNumber = Math.max(axisNumber, 0); + + const stackIndex = this._getStackIndex(this.index, this._cachedMeta.stack, skipNull ? index : undefined) + axisNumber * stackCount; center = range.start + (range.chunk * stackIndex) + (range.chunk / 2); size = Math.min(maxBarThickness, range.chunk * range.ratio); } else { diff --git a/src/scales/scale.category.js b/src/scales/scale.category.js index 3d773a8a8c2..8e9a2dec022 100644 --- a/src/scales/scale.category.js +++ b/src/scales/scale.category.js @@ -1,5 +1,5 @@ import Scale from '../core/core.scale.js'; -import {isNullOrUndef, valueOrDefault, _limitValue} from '../helpers/index.js'; +import {isNullOrUndef, valueOrDefault, _limitValue, defined} from '../helpers/index.js'; const addIfString = (labels, raw, index, addedLabels) => { if (typeof raw === 'string') { @@ -54,6 +54,7 @@ export default class CategoryScale extends Scale { } init(scaleOptions) { + const data = this.chart.data; const added = this._addedLabels; if (added.length) { const labels = this.getLabels(); @@ -64,7 +65,12 @@ export default class CategoryScale extends Scale { } this._addedLabels = []; } + super.init(scaleOptions); + + if (defined(this.options.stack) && !scaleOptions.labels && !data[this.isHorizontal() ? 'xLabels' : 'yLabels']) { + this.options.labels = this.options.labels || []; + } } parse(raw, index) {