}
// Increase sizes here
- if (display) {
- ctx.font = labelFont.string;
+ if (!display) {
+ me.width = minSize.width = me.height = minSize.height = 0;
+ return;
+ }
+ ctx.font = labelFont.string;
- if (isHorizontal) {
- // Labels
-
- // Width of each line of legend boxes. Labels wrap onto multiple lines when there are too many to fit on one
- var lineWidths = me.lineWidths = [0];
- var totalHeight = 0;
-
- ctx.textAlign = 'left';
- ctx.textBaseline = 'middle';
-
- helpers.each(me.legendItems, function(legendItem, i) {
- var boxWidth = getBoxWidth(labelOpts, fontSize);
- var width = boxWidth + (fontSize / 2) + ctx.measureText(legendItem.text).width;
-
- if (i === 0 || lineWidths[lineWidths.length - 1] + width + 2 * labelOpts.padding > minSize.width) {
- totalHeight += fontSize + labelOpts.padding;
- lineWidths[lineWidths.length - (i > 0 ? 0 : 1)] = 0;
- }
-
- // Store the hitbox width and height here. Final position will be updated in `draw`
- hitboxes[i] = {
- left: 0,
- top: 0,
- width: width,
- height: fontSize
- };
+ if (isHorizontal) {
+ // Labels
- lineWidths[lineWidths.length - 1] += width + labelOpts.padding;
- });
+ // Width of each line of legend boxes. Labels wrap onto multiple lines when there are too many to fit on one
+ var lineWidths = me.lineWidths = [0];
+ var totalHeight = 0;
- minSize.height += totalHeight;
+ ctx.textAlign = 'left';
+ ctx.textBaseline = 'middle';
- } else {
- var vPadding = labelOpts.padding;
- var columnWidths = me.columnWidths = [];
- var columnHeights = me.columnHeights = [];
- var totalWidth = labelOpts.padding;
- var currentColWidth = 0;
- var currentColHeight = 0;
-
- helpers.each(me.legendItems, function(legendItem, i) {
- var boxWidth = getBoxWidth(labelOpts, fontSize);
- var itemWidth = boxWidth + (fontSize / 2) + ctx.measureText(legendItem.text).width;
-
- // If too tall, go to new column
- if (i > 0 && currentColHeight + fontSize + 2 * vPadding > minSize.height) {
- totalWidth += currentColWidth + labelOpts.padding;
- columnWidths.push(currentColWidth); // previous column width
- columnHeights.push(currentColHeight);
- currentColWidth = 0;
- currentColHeight = 0;
- }
-
- // Get max width
- currentColWidth = Math.max(currentColWidth, itemWidth);
- currentColHeight += fontSize + vPadding;
-
- // Store the hitbox width and height here. Final position will be updated in `draw`
- hitboxes[i] = {
- left: 0,
- top: 0,
- width: itemWidth,
- height: fontSize
- };
- });
+ helpers.each(me.legendItems, function(legendItem, i) {
+ var boxWidth = getBoxWidth(labelOpts, fontSize);
+ var width = boxWidth + (fontSize / 2) + ctx.measureText(legendItem.text).width;
- totalWidth += currentColWidth;
- columnWidths.push(currentColWidth);
- columnHeights.push(currentColHeight);
- minSize.width += totalWidth;
- }
+ if (i === 0 || lineWidths[lineWidths.length - 1] + width + 2 * labelOpts.padding > minSize.width) {
+ totalHeight += fontSize + labelOpts.padding;
+ lineWidths[lineWidths.length - (i > 0 ? 0 : 1)] = 0;
+ }
+
+ // Store the hitbox width and height here. Final position will be updated in `draw`
+ hitboxes[i] = {
+ left: 0,
+ top: 0,
+ width: width,
+ height: fontSize
+ };
+
+ lineWidths[lineWidths.length - 1] += width + labelOpts.padding;
+ });
+
+ minSize.height += totalHeight;
+
+ } else {
+ var vPadding = labelOpts.padding;
+ var columnWidths = me.columnWidths = [];
+ var columnHeights = me.columnHeights = [];
+ var totalWidth = labelOpts.padding;
+ var currentColWidth = 0;
+ var currentColHeight = 0;
+
+ helpers.each(me.legendItems, function(legendItem, i) {
+ var boxWidth = getBoxWidth(labelOpts, fontSize);
+ var itemWidth = boxWidth + (fontSize / 2) + ctx.measureText(legendItem.text).width;
+
+ // If too tall, go to new column
+ if (i > 0 && currentColHeight + fontSize + 2 * vPadding > minSize.height) {
+ totalWidth += currentColWidth + labelOpts.padding;
+ columnWidths.push(currentColWidth); // previous column width
+ columnHeights.push(currentColHeight);
+ currentColWidth = 0;
+ currentColHeight = 0;
+ }
+
+ // Get max width
+ currentColWidth = Math.max(currentColWidth, itemWidth);
+ currentColHeight += fontSize + vPadding;
+
+ // Store the hitbox width and height here. Final position will be updated in `draw`
+ hitboxes[i] = {
+ left: 0,
+ top: 0,
+ width: itemWidth,
+ height: fontSize
+ };
+ });
+
+ totalWidth += currentColWidth;
+ columnWidths.push(currentColWidth);
+ columnHeights.push(currentColHeight);
+ minSize.width += totalWidth;
}
me.width = minSize.width;
var legendWidth = me.width;
var lineWidths = me.lineWidths;
- if (opts.display) {
- var ctx = me.ctx;
- var fontColor = valueOrDefault(labelOpts.fontColor, globalDefaults.defaultFontColor);
- var labelFont = helpers.options._parseFont(labelOpts);
- var fontSize = labelFont.size;
- var cursor;
+ if (!opts.display) {
+ return;
+ }
- // Canvas setup
- ctx.textAlign = 'left';
- ctx.textBaseline = 'middle';
- ctx.lineWidth = 0.5;
- ctx.strokeStyle = fontColor; // for strikethrough effect
- ctx.fillStyle = fontColor; // render in correct colour
- ctx.font = labelFont.string;
-
- var boxWidth = getBoxWidth(labelOpts, fontSize);
- var hitboxes = me.legendHitBoxes;
-
- // current position
- var drawLegendBox = function(x, y, legendItem) {
- if (isNaN(boxWidth) || boxWidth <= 0) {
- return;
- }
+ var ctx = me.ctx;
+ var fontColor = valueOrDefault(labelOpts.fontColor, globalDefaults.defaultFontColor);
+ var labelFont = helpers.options._parseFont(labelOpts);
+ var fontSize = labelFont.size;
+ var cursor;
+
+ // Canvas setup
+ ctx.textAlign = 'left';
+ ctx.textBaseline = 'middle';
+ ctx.lineWidth = 0.5;
+ ctx.strokeStyle = fontColor; // for strikethrough effect
+ ctx.fillStyle = fontColor; // render in correct colour
+ ctx.font = labelFont.string;
+
+ var boxWidth = getBoxWidth(labelOpts, fontSize);
+ var hitboxes = me.legendHitBoxes;
+
+ // current position
+ var drawLegendBox = function(x, y, legendItem) {
+ if (isNaN(boxWidth) || boxWidth <= 0) {
+ return;
+ }
- // Set the ctx for the box
- ctx.save();
+ // Set the ctx for the box
+ ctx.save();
- var lineWidth = valueOrDefault(legendItem.lineWidth, lineDefault.borderWidth);
- ctx.fillStyle = valueOrDefault(legendItem.fillStyle, defaultColor);
- ctx.lineCap = valueOrDefault(legendItem.lineCap, lineDefault.borderCapStyle);
- ctx.lineDashOffset = valueOrDefault(legendItem.lineDashOffset, lineDefault.borderDashOffset);
- ctx.lineJoin = valueOrDefault(legendItem.lineJoin, lineDefault.borderJoinStyle);
- ctx.lineWidth = lineWidth;
- ctx.strokeStyle = valueOrDefault(legendItem.strokeStyle, defaultColor);
+ var lineWidth = valueOrDefault(legendItem.lineWidth, lineDefault.borderWidth);
+ ctx.fillStyle = valueOrDefault(legendItem.fillStyle, defaultColor);
+ ctx.lineCap = valueOrDefault(legendItem.lineCap, lineDefault.borderCapStyle);
+ ctx.lineDashOffset = valueOrDefault(legendItem.lineDashOffset, lineDefault.borderDashOffset);
+ ctx.lineJoin = valueOrDefault(legendItem.lineJoin, lineDefault.borderJoinStyle);
+ ctx.lineWidth = lineWidth;
+ ctx.strokeStyle = valueOrDefault(legendItem.strokeStyle, defaultColor);
- if (ctx.setLineDash) {
- // IE 9 and 10 do not support line dash
- ctx.setLineDash(valueOrDefault(legendItem.lineDash, lineDefault.borderDash));
- }
+ if (ctx.setLineDash) {
+ // IE 9 and 10 do not support line dash
+ ctx.setLineDash(valueOrDefault(legendItem.lineDash, lineDefault.borderDash));
+ }
+
+ if (labelOpts && labelOpts.usePointStyle) {
+ // Recalculate x and y for drawPoint() because its expecting
+ // x and y to be center of figure (instead of top left)
+ var radius = boxWidth * Math.SQRT2 / 2;
+ var centerX = x + boxWidth / 2;
+ var centerY = y + fontSize / 2;
- if (labelOpts && labelOpts.usePointStyle) {
- // Recalculate x and y for drawPoint() because its expecting
- // x and y to be center of figure (instead of top left)
- var radius = boxWidth * Math.SQRT2 / 2;
- var centerX = x + boxWidth / 2;
- var centerY = y + fontSize / 2;
-
- // Draw pointStyle as legend symbol
- helpers.canvas.drawPoint(ctx, legendItem.pointStyle, radius, centerX, centerY, legendItem.rotation);
- } else {
- // Draw box as legend symbol
- ctx.fillRect(x, y, boxWidth, fontSize);
- if (lineWidth !== 0) {
- ctx.strokeRect(x, y, boxWidth, fontSize);
- }
+ // Draw pointStyle as legend symbol
+ helpers.canvas.drawPoint(ctx, legendItem.pointStyle, radius, centerX, centerY, legendItem.rotation);
+ } else {
+ // Draw box as legend symbol
+ ctx.fillRect(x, y, boxWidth, fontSize);
+ if (lineWidth !== 0) {
+ ctx.strokeRect(x, y, boxWidth, fontSize);
}
+ }
- ctx.restore();
+ ctx.restore();
+ };
+ var fillText = function(x, y, legendItem, textWidth) {
+ var halfFontSize = fontSize / 2;
+ var xLeft = boxWidth + halfFontSize + x;
+ var yMiddle = y + halfFontSize;
+
+ ctx.fillText(legendItem.text, xLeft, yMiddle);
+
+ if (legendItem.hidden) {
+ // Strikethrough the text if hidden
+ ctx.beginPath();
+ ctx.lineWidth = 2;
+ ctx.moveTo(xLeft, yMiddle);
+ ctx.lineTo(xLeft + textWidth, yMiddle);
+ ctx.stroke();
+ }
+ };
+
+ var alignmentOffset = function(dimension, blockSize) {
+ switch (opts.align) {
+ case 'start':
+ return labelOpts.padding;
+ case 'end':
+ return dimension - blockSize;
+ default: // center
+ return (dimension - blockSize + labelOpts.padding) / 2;
+ }
+ };
+
+ // Horizontal
+ var isHorizontal = me.isHorizontal();
+ if (isHorizontal) {
+ cursor = {
+ x: me.left + alignmentOffset(legendWidth, lineWidths[0]),
+ y: me.top + labelOpts.padding,
+ line: 0
};
- var fillText = function(x, y, legendItem, textWidth) {
- var halfFontSize = fontSize / 2;
- var xLeft = boxWidth + halfFontSize + x;
- var yMiddle = y + halfFontSize;
-
- ctx.fillText(legendItem.text, xLeft, yMiddle);
-
- if (legendItem.hidden) {
- // Strikethrough the text if hidden
- ctx.beginPath();
- ctx.lineWidth = 2;
- ctx.moveTo(xLeft, yMiddle);
- ctx.lineTo(xLeft + textWidth, yMiddle);
- ctx.stroke();
- }
+ } else {
+ cursor = {
+ x: me.left + labelOpts.padding,
+ y: me.top + alignmentOffset(legendHeight, columnHeights[0]),
+ line: 0
};
+ }
- var alignmentOffset = function(dimension, blockSize) {
- switch (opts.align) {
- case 'start':
- return labelOpts.padding;
- case 'end':
- return dimension - blockSize;
- default: // center
- return (dimension - blockSize + labelOpts.padding) / 2;
- }
- };
+ var itemHeight = fontSize + labelOpts.padding;
+ helpers.each(me.legendItems, function(legendItem, i) {
+ var textWidth = ctx.measureText(legendItem.text).width;
+ var width = boxWidth + (fontSize / 2) + textWidth;
+ var x = cursor.x;
+ var y = cursor.y;
- // Horizontal
- var isHorizontal = me.isHorizontal();
+ // Use (me.left + me.minSize.width) and (me.top + me.minSize.height)
+ // instead of me.right and me.bottom because me.width and me.height
+ // may have been changed since me.minSize was calculated
if (isHorizontal) {
- cursor = {
- x: me.left + alignmentOffset(legendWidth, lineWidths[0]),
- y: me.top + labelOpts.padding,
- line: 0
- };
- } else {
- cursor = {
- x: me.left + labelOpts.padding,
- y: me.top + alignmentOffset(legendHeight, columnHeights[0]),
- line: 0
- };
- }
-
- var itemHeight = fontSize + labelOpts.padding;
- helpers.each(me.legendItems, function(legendItem, i) {
- var textWidth = ctx.measureText(legendItem.text).width;
- var width = boxWidth + (fontSize / 2) + textWidth;
- var x = cursor.x;
- var y = cursor.y;
-
- // Use (me.left + me.minSize.width) and (me.top + me.minSize.height)
- // instead of me.right and me.bottom because me.width and me.height
- // may have been changed since me.minSize was calculated
- if (isHorizontal) {
- if (i > 0 && x + width + labelOpts.padding > me.left + me.minSize.width) {
- y = cursor.y += itemHeight;
- cursor.line++;
- x = cursor.x = me.left + alignmentOffset(legendWidth, lineWidths[cursor.line]);
- }
- } else if (i > 0 && y + itemHeight > me.top + me.minSize.height) {
- x = cursor.x = x + me.columnWidths[cursor.line] + labelOpts.padding;
+ if (i > 0 && x + width + labelOpts.padding > me.left + me.minSize.width) {
+ y = cursor.y += itemHeight;
cursor.line++;
- y = cursor.y = me.top + alignmentOffset(legendHeight, columnHeights[cursor.line]);
+ x = cursor.x = me.left + alignmentOffset(legendWidth, lineWidths[cursor.line]);
}
+ } else if (i > 0 && y + itemHeight > me.top + me.minSize.height) {
+ x = cursor.x = x + me.columnWidths[cursor.line] + labelOpts.padding;
+ cursor.line++;
+ y = cursor.y = me.top + alignmentOffset(legendHeight, columnHeights[cursor.line]);
+ }
- drawLegendBox(x, y, legendItem);
+ drawLegendBox(x, y, legendItem);
- hitboxes[i].left = x;
- hitboxes[i].top = y;
+ hitboxes[i].left = x;
+ hitboxes[i].top = y;
- // Fill the actual label
- fillText(x, y, legendItem, textWidth);
+ // Fill the actual label
+ fillText(x, y, legendItem, textWidth);
- if (isHorizontal) {
- cursor.x += width + labelOpts.padding;
- } else {
- cursor.y += itemHeight;
- }
- });
- }
+ if (isHorizontal) {
+ cursor.x += width + labelOpts.padding;
+ } else {
+ cursor.y += itemHeight;
+ }
+ });
},
/**
fit: function() {
var me = this;
var opts = me.options;
- var display = opts.display;
- var minSize = me.minSize;
- var lineCount = helpers.isArray(opts.text) ? opts.text.length : 1;
- var fontOpts = helpers.options._parseFont(opts);
- var textSize = display ? (lineCount * fontOpts.lineHeight) + (opts.padding * 2) : 0;
+ var minSize = me.minSize = {};
+ var isHorizontal = me.isHorizontal();
+ var lineCount, textSize;
- if (me.isHorizontal()) {
- minSize.width = me.maxWidth; // fill all the width
- minSize.height = textSize;
- } else {
- minSize.width = textSize;
- minSize.height = me.maxHeight; // fill all the height
+ if (!opts.display) {
+ me.width = minSize.width = me.height = minSize.height = 0;
+ return;
}
- me.width = minSize.width;
- me.height = minSize.height;
+ lineCount = helpers.isArray(opts.text) ? opts.text.length : 1;
+ textSize = lineCount * helpers.options._parseFont(opts).lineHeight + opts.padding * 2;
+ me.width = minSize.width = isHorizontal ? me.maxWidth : textSize;
+ me.height = minSize.height = isHorizontal ? textSize : me.maxHeight;
},
afterFit: noop,
var ctx = me.ctx;
var opts = me.options;
- if (opts.display) {
- var fontOpts = helpers.options._parseFont(opts);
- var lineHeight = fontOpts.lineHeight;
- var offset = lineHeight / 2 + opts.padding;
- var rotation = 0;
- var top = me.top;
- var left = me.left;
- var bottom = me.bottom;
- var right = me.right;
- var maxWidth, titleX, titleY;
-
- ctx.fillStyle = helpers.valueOrDefault(opts.fontColor, defaults.global.defaultFontColor); // render in correct colour
- ctx.font = fontOpts.string;
-
- // Horizontal
- if (me.isHorizontal()) {
- titleX = left + ((right - left) / 2); // midpoint of the width
- titleY = top + offset;
- maxWidth = right - left;
- } else {
- titleX = opts.position === 'left' ? left + offset : right - offset;
- titleY = top + ((bottom - top) / 2);
- maxWidth = bottom - top;
- rotation = Math.PI * (opts.position === 'left' ? -0.5 : 0.5);
- }
+ if (!opts.display) {
+ return;
+ }
- ctx.save();
- ctx.translate(titleX, titleY);
- ctx.rotate(rotation);
- ctx.textAlign = 'center';
- ctx.textBaseline = 'middle';
-
- var text = opts.text;
- if (helpers.isArray(text)) {
- var y = 0;
- for (var i = 0; i < text.length; ++i) {
- ctx.fillText(text[i], 0, y, maxWidth);
- y += lineHeight;
- }
- } else {
- ctx.fillText(text, 0, 0, maxWidth);
- }
+ var fontOpts = helpers.options._parseFont(opts);
+ var lineHeight = fontOpts.lineHeight;
+ var offset = lineHeight / 2 + opts.padding;
+ var rotation = 0;
+ var top = me.top;
+ var left = me.left;
+ var bottom = me.bottom;
+ var right = me.right;
+ var maxWidth, titleX, titleY;
+
+ ctx.fillStyle = helpers.valueOrDefault(opts.fontColor, defaults.global.defaultFontColor); // render in correct colour
+ ctx.font = fontOpts.string;
+
+ // Horizontal
+ if (me.isHorizontal()) {
+ titleX = left + ((right - left) / 2); // midpoint of the width
+ titleY = top + offset;
+ maxWidth = right - left;
+ } else {
+ titleX = opts.position === 'left' ? left + offset : right - offset;
+ titleY = top + ((bottom - top) / 2);
+ maxWidth = bottom - top;
+ rotation = Math.PI * (opts.position === 'left' ? -0.5 : 0.5);
+ }
- ctx.restore();
+ ctx.save();
+ ctx.translate(titleX, titleY);
+ ctx.rotate(rotation);
+ ctx.textAlign = 'center';
+ ctx.textBaseline = 'middle';
+
+ var text = opts.text;
+ if (helpers.isArray(text)) {
+ var y = 0;
+ for (var i = 0; i < text.length; ++i) {
+ ctx.fillText(text[i], 0, y, maxWidth);
+ y += lineHeight;
+ }
+ } else {
+ ctx.fillText(text, 0, 0, maxWidth);
}
+
+ ctx.restore();
}
});