* @private
(titleHeight, fontSize, boxWidth, itemHeight)
| 158 | * @private |
| 159 | */ |
| 160 | _fitRows(titleHeight, fontSize, boxWidth, itemHeight) { |
| 161 | const {ctx, maxWidth, options: {labels: {padding}}} = this; |
| 162 | const hitboxes = this.legendHitBoxes = []; |
| 163 | // Width of each line of legend boxes. Labels wrap onto multiple lines when there are too many to fit on one |
| 164 | const lineWidths = this.lineWidths = [0]; |
| 165 | const lineHeight = itemHeight + padding; |
| 166 | let totalHeight = titleHeight; |
| 167 | |
| 168 | ctx.textAlign = 'left'; |
| 169 | ctx.textBaseline = 'middle'; |
| 170 | |
| 171 | let row = -1; |
| 172 | let top = -lineHeight; |
| 173 | this.legendItems.forEach((legendItem, i) => { |
| 174 | const itemWidth = boxWidth + (fontSize / 2) + ctx.measureText(legendItem.text).width; |
| 175 | |
| 176 | if (i === 0 || lineWidths[lineWidths.length - 1] + itemWidth + 2 * padding > maxWidth) { |
| 177 | totalHeight += lineHeight; |
| 178 | lineWidths[lineWidths.length - (i > 0 ? 0 : 1)] = 0; |
| 179 | top += lineHeight; |
| 180 | row++; |
| 181 | } |
| 182 | |
| 183 | hitboxes[i] = {left: 0, top, row, width: itemWidth, height: itemHeight}; |
| 184 | |
| 185 | lineWidths[lineWidths.length - 1] += itemWidth + padding; |
| 186 | }); |
| 187 | |
| 188 | return totalHeight; |
| 189 | } |
| 190 | |
| 191 | _fitCols(titleHeight, labelFont, boxWidth, _itemHeight) { |
| 192 | const {ctx, maxHeight, options: {labels: {padding}}} = this; |