Set configuration parameters for drawing guide
765078
def _set_defaults(self):
        
        valid_locations = {'top', 'bottom', 'left', 'right'}
        horizontal_locations = {'left', 'right'}
        get_property = self.theme.themeables.property
        margin_location_lookup = {'t': 'b', 'b': 't',
                                  'l': 'r', 'r': 'l'}

        # label position
        self.label_position = self.label_position or 'right'
        if self.label_position not in valid_locations:
            msg = "label position '{}' is invalid"
            raise PlotnineError(msg.format(self.label_position))

        # label margin
        # legend_text_legend or legend_text_colorbar
        name = 'legend_text_{}'.format(
            self.__class__.__name__.split('_')[-1])
        loc = margin_location_lookup[self.label_position[0]]
        try:
            margin = get_property(name, 'margin')
        except KeyError:
            self._label_margin = 3
        else:
            self._label_margin = margin.get_as(loc, 'pt')

        # direction of guide
        if self.direction is None:
            if self.label_position in horizontal_locations:
                self.direction = 'vertical'
            else:
                self.direction = 'horizontal'

        # title position
        if self.title_position is None:
            if self.direction == 'vertical':
                self.title_position = 'top'
            elif self.direction == 'horizontal':
                self.title_position = 'left'
        if self.title_position not in valid_locations:
            msg = "title position '{}' is invalid"
            raise PlotnineError(msg.format(self.title_position))

        # title alignment
        tmp = 'left' if self.direction == 'vertical' else 'center'
        self._title_align = self._default('legend_title_align', tmp)

        # by default, direction of each guide depends on
        # the position all the guides
        try:
            position = get_property('legend_position')
        except KeyError:
            position = 'right'

        if position in {'top', 'bottom'}:
            tmp = 'horizontal'
        else:  # left, right, (default)
            tmp = 'vertical'
        self.direction = self._default('legend_direction', tmp)

        # title margin
        loc = margin_location_lookup[self.title_position[0]]
        try:
            margin = get_property('legend_title', 'margin')
        except KeyError:
            self._title_margin = 8
        else:
            self._title_margin = margin.get_as(loc, 'pt')

        # legend_margin
        try:
            self._legend_margin = get_property('legend_margin')
        except KeyError:
            self._legend_margin = 10

        # legend_entry_spacing
        try:
            self._legend_entry_spacing_x = get_property(
                'legend_entry_spacing_x')
        except KeyError:
            self._legend_entry_spacing_x = 5

        try:
            self._legend_entry_spacing_y = get_property(
                'legend_entry_spacing_y')
        except KeyError:
            self._legend_entry_spacing_y = 2
959853
private void initGraphics() {
        // Set initial size
        if (Double.compare(gauge.getPrefWidth(), 0.0) <= 0 || Double.compare(gauge.getPrefHeight(), 0.0) <= 0 ||
            Double.compare(gauge.getWidth(), 0.0) <= 0 || Double.compare(gauge.getHeight(), 0.0) <= 0) {
            if (gauge.getPrefWidth() > 0 && gauge.getPrefHeight() > 0) {
                gauge.setPrefSize(gauge.getPrefWidth(), gauge.getPrefHeight());
            } else {
                gauge.setPrefSize(PREFERRED_WIDTH, PREFERRED_HEIGHT);
            }
        }

        ring = new Path();
        ring.setFillRule(FillRule.EVEN_ODD);
        ring.setStroke(null);
        ring.setFill(Gauge.DARK_COLOR);
        ring.setEffect(new InnerShadow(BlurType.TWO_PASS_BOX, Color.rgb(255, 255, 255, 0.35), 1, 0, 0, 1));

        sectionsCanvas = new Canvas(PREFERRED_WIDTH, PREFERRED_HEIGHT);
        sectionsCtx    = sectionsCanvas.getGraphicsContext2D();

        mask = new Circle();
        mask.setStroke(null);
        mask.setFill(gauge.getBackgroundPaint());

        knob = new Circle();
        knob.setStroke(null);
        knob.setFill(gauge.getKnobColor());

        angleStep = ANGLE_RANGE / (gauge.getRange());
        double targetAngle = 180 - START_ANGLE + (gauge.getValue() - gauge.getMinValue()) * angleStep;

        needleRotate = new Rotate(180 - START_ANGLE);
        needleRotate.setAngle(Helper.clamp(180 - START_ANGLE, 180 - START_ANGLE + ANGLE_RANGE, targetAngle));

        needle = new Path();
        needle.setFillRule(FillRule.EVEN_ODD);
        needle.setStroke(null);
        needle.getTransforms().setAll(needleRotate);

        valueText = new Text(formatNumber(gauge.getLocale(), gauge.getFormatString(), gauge.getDecimals(), gauge.getMinValue()) + gauge.getUnit());
        valueText.setMouseTransparent(true);
        valueText.setTextOrigin(VPos.CENTER);
        valueText.setFill(gauge.getValueColor());
        Helper.enableNode(valueText, gauge.isValueVisible());

        titleText = new Text(gauge.getTitle());
        titleText.setTextOrigin(VPos.CENTER);
        titleText.setFill(gauge.getTitleColor());
        Helper.enableNode(titleText, !gauge.getTitle().isEmpty());

        // Add all nodes
        pane = new Pane(ring, sectionsCanvas, mask, knob, needle, valueText, titleText);

        getChildren().setAll(pane);
    }
58407
def _set_config(c):
    """"""
    func = sdl2.SDL_GL_SetAttribute
    func(sdl2.SDL_GL_RED_SIZE, c['red_size'])
    func(sdl2.SDL_GL_GREEN_SIZE, c['green_size'])
    func(sdl2.SDL_GL_BLUE_SIZE, c['blue_size'])
    func(sdl2.SDL_GL_ALPHA_SIZE, c['alpha_size'])
    func(sdl2.SDL_GL_DEPTH_SIZE, c['depth_size'])
    func(sdl2.SDL_GL_STENCIL_SIZE, c['stencil_size'])
    func(sdl2.SDL_GL_DOUBLEBUFFER, 1 if c['double_buffer'] else 0)
    samps = c['samples']
    func(sdl2.SDL_GL_MULTISAMPLEBUFFERS, 1 if samps > 0 else 0)
    func(sdl2.SDL_GL_MULTISAMPLESAMPLES, samps if samps > 0 else 0)
    func(sdl2.SDL_GL_STEREO, c['stereo'])
264161
function setMeasures(data, config, ctx, canvasheight, canvaswidth, ylabels, ylabels2, reverseLegend, reverseAxis, drawAxis, legendBox, typegraph) {
		var height = canvasheight;
		var width = canvaswidth;
		if (window.devicePixelRatio > 1) {
			height = height / window.devicePixelRatio;
			width = width / window.devicePixelRatio;
		}
		if (config.canvasBackgroundColor != "none") ctx.canvas.style.background = config.canvasBackgroundColor;
		var i, j, k;
		var borderHeight = 0;
		var borderTHeight = 0;
		var borderBHeight = 0;
		var borderRHeight = 0;
		var borderLHeight = 0;
		var graphTitleHeight = 0;
		var graphTitlePosY = 0;
		var graphSubTitleHeight = 0;
		var graphSubTitlePosY = 0;
		var footNoteHeight = 0;
		var footNotePosY = 0;
		//		ctx.widthAtSetMeasures=width;
		//		ctx.heightAtSetMeasures=height;
		var currentPosition, topNotUsableHeight, bottomNotUsableHeight, leftNotUsableWidth, rightNotUsableWidth, availableWidth, availableHeight;
		availableWidth = width;
		availableHeight = height;
		//// Step 0 : border height;
		// Borders height (and width);
		if (config.canvasBorders && config.canvasBordersSelection > 0) {
			borderHeight = Math.ceil(ctx.chartLineScale * config.canvasBordersWidth);
			if (isBorder(config.canvasBordersSelection, "TOP")) borderTHeight = borderHeight;
			if (isBorder(config.canvasBordersSelection, "BOTTOM")) borderBHeight = borderHeight;
			if (isBorder(config.canvasBordersSelection, "RIGHT")) borderRHeight = borderHeight;
			if (isBorder(config.canvasBordersSelection, "LEFT")) borderLHeight = borderHeight;
		}
		//// Step 1 : compute height/width and position of top elements;
		currentPosition = 0 + borderTHeight + Math.ceil(ctx.chartSpaceScale * config.spaceTop);
		// Title height - Title Position;
		if (config.graphTitle.trim() != "") {
			graphTitleHeight = (Math.ceil(ctx.chartTextScale * config.graphTitleFontSize)) * (config.graphTitle.split("\n").length || 1) + Math.ceil(ctx.chartSpaceScale * config.graphTitleSpaceBefore) + Math.ceil(ctx.chartSpaceScale * config.graphTitleSpaceAfter);
			graphTitlePosY = currentPosition + Math.ceil(ctx.chartSpaceScale * config.graphTitleSpaceBefore)
			if (config.graphTitleBackgroundColor != "none" || config.graphTitleBorders) {
				graphTitleHeight += (isBorder(config.graphTitleBordersSelection, "TOP") + isBorder(config.graphTitleBordersSelection, "BOTTOM")) * (Math.ceil(ctx.chartSpaceScale * config.graphTitleBordersYSpace));
				graphTitlePosY += isBorder(config.graphTitleBordersSelection, "TOP") * Math.ceil(ctx.chartSpaceScale * config.graphTitleBordersYSpace);
			}
			if (config.graphTitleBorders) {
				graphTitleHeight += (isBorder(config.graphTitleBordersSelection, "TOP") + isBorder(config.graphTitleBordersSelection, "BOTTOM")) * (Math.ceil(ctx.chartLineScale * config.graphTitleBordersWidth));
				graphTitlePosY += isBorder(config.graphTitleBordersSelection, "TOP") * Math.ceil(ctx.chartLineScale * config.graphTitleBordersWidth);
			}
			currentPosition += graphTitleHeight;
		}
		// subTitle height - position;
		if (config.graphSubTitle.trim() != "") {
			graphSubTitleHeight = (Math.ceil(ctx.chartTextScale * config.graphSubTitleFontSize)) * (config.graphSubTitle.split("\n").length || 1) + Math.ceil(ctx.chartSpaceScale * config.graphSubTitleSpaceBefore) + Math.ceil(ctx.chartSpaceScale * config.graphSubTitleSpaceAfter);
			graphSubTitlePosY = currentPosition + Math.ceil(ctx.chartSpaceScale * config.graphSubTitleSpaceBefore);
			if (config.graphSubTitleBackgroundColor != "none" || config.graphSubTitleBorders) {
				graphSubTitleHeight += 2 * (Math.ceil(ctx.chartSpaceScale * config.graphSubTitleBordersYSpace));
				graphSubTitlePosY += Math.ceil(ctx.chartSpaceScale * config.graphSubTitleBordersYSpace);
			}
			if (config.graphSubTitleBorders) {
				graphSubTitleHeight += (isBorder(config.graphTitleBordersSelection, "TOP") + isBorder(config.graphTitleBordersSelection, "BOTTOM")) * (Math.ceil(ctx.chartLineScale * config.graphSubTitleBordersWidth));
				graphSubTitlePosY += isBorder(config.graphTitleBordersSelection, "TOP") * Math.ceil(ctx.chartLineScale * config.graphSubTitleBordersWidth);
			}
			currentPosition += graphSubTitleHeight;
		}
		topNotUsableHeight = currentPosition;
		availableHeight -= topNotUsableHeight;
		//// Step 2 : compute height/width and position of bottom elements;
		currentPosition = height - borderBHeight - Math.ceil(ctx.chartSpaceScale * config.spaceBottom);
		// footNote
		if (typeof(config.footNote) != "undefined") {
			if (config.footNote.trim() != "") {
				footNoteHeight = (Math.ceil(ctx.chartTextScale * config.footNoteFontSize)) * (config.footNote.split("\n").length || 1) + Math.ceil(ctx.chartSpaceScale * config.footNoteSpaceBefore) + Math.ceil(ctx.chartSpaceScale * config.footNoteSpaceAfter);
				footNotePosY = currentPosition - Math.ceil(ctx.chartSpaceScale * config.footNoteSpaceAfter);
				if (config.footNoteBackgroundColor != "none" || config.footNoteBorders) {
					footNoteHeight += 2 * (Math.ceil(ctx.chartSpaceScale * config.footNoteBordersYSpace));
					footNotePosY -= Math.ceil(ctx.chartSpaceScale * config.footNoteBordersYSpace);
				}
				if (config.footNoteBorders) {
					footNoteHeight += (isBorder(config.footNoteBordersSelection, "TOP") + isBorder(config.footNoteBordersSelection, "BOTTOM")) * (Math.ceil(ctx.chartLineScale * config.footNoteBordersWidth));
					footNotePosY -= isBorder(config.footNoteBordersSelection, "BOTTOM") * Math.ceil(ctx.chartLineScale * config.footNoteBordersWidth);
				}
				currentPosition -= footNoteHeight;
			}
		}
		bottomNotUsableHeight = height - currentPosition;
		availableHeight -= bottomNotUsableHeight;
		//// Step 3 : compute height/width and position of left elements;
		currentPosition = 0 + borderLHeight + Math.ceil(ctx.chartSpaceScale * config.spaceLeft);
		// No left element to be drawn;
		leftNotUsableWidth = currentPosition;
		availableWidth -= leftNotUsableWidth;
		//// Step 4 : compute height/width and position of right elements;
		currentPosition = width - borderRHeight - Math.ceil(ctx.chartSpaceScale * config.spaceRight);
		// No right element to be drawn;
		rightNotUsableWidth = width - currentPosition;
		availableWidth -= rightNotUsableWidth;
		topNotUsableHeight += Math.ceil(ctx.chartSpaceScale * config.graphSpaceBefore);
		bottomNotUsableHeight += Math.ceil(ctx.chartSpaceScale * config.graphSpaceAfter);
		availableHeight -= (Math.ceil(ctx.chartSpaceScale * config.graphSpaceBefore) + Math.ceil(ctx.chartSpaceScale * config.graphSpaceAfter));
		//// Step 5  : compute widest text legend;
		var nbeltLegend = 0;
		var widestLegend = -99999999;
		var highestLegend = 0;
		var drawLegendData;
		if (typeof(config.legend) != "undefined") {
			if (config.legend == true) {
				ctx.font = (Math.ceil(ctx.chartTextScale * config.legendFontSize)).toString() + "px " + config.legendFontFamily;
				//				ctx.font = config.legendFontStyle + " " + (Math.ceil(ctx.chartTextScale*config.legendFontSize)).toString() + "px " + config.legendFontFamily;
				var textLength;
				for (i = 0; i < data.datasets.length; i++) {
					if (!config.legendDrawEmptyData) {
						drawLegendData = false;
						for (j = 0; j < data.datasets[i].data.length; j++) {
							if (typeof(1 * data.datasets[i].data[j]) == "number") {
								if (1 * data.datasets[i].data[j] != 0) drawLegendData = true;
							}
						}
					} else drawLegendData = true;
					if (drawLegendData && typeof(data.datasets[i].title) == "string") {
						if (data.datasets[i].title.trim() != "") {
							nbeltLegend++;
							textLength = ctx.measureTextMultiLine(fmtChartJS(config, data.datasets[i].title, config.fmtLegend), Math.ceil(ctx.chartTextScale * config.legendFontSize));
							widestLegend = Math.max(textLength.textWidth, widestLegend);
							highestLegend = Math.max(Math.ceil(ctx.chartTextScale * config.legendFontSize), highestLegend);
						}
					}
				}
				widestLegend += Math.ceil(ctx.chartTextScale * config.legendBlockSize) + Math.ceil(ctx.chartSpaceScale * config.legendSpaceBetweenBoxAndText);
				if (nbeltLegend == 0 || (nbeltLegend == 1 && !config.showSingleLegend)) widestLegend = 0;
			}
		}
		//// Step 6  : compute legend heights and width if legendPosY = 0 or 4 or if legendPosX = 0 or 4; 
		var legendBorderHeight = 0;
		var legendBorderWidth = 0;
		var spaceLegendHeight = 0;
		var xLegendPos = 0;
		var yLegendPos = 0;
		var nbLegendLines = 0;
		var nbLegendCols = 0;
		var legendHeight = 0;
		var legendWidth = 0;
		var msrLegend;
		if (widestLegend > -99999998) {
			if (config.legendPosY == 0 || config.legendPosY == 4) {
				var availableLegendWidth, maxLegendOnLine;
				if (config.legendPosX == 1 || config.legendPosX == 2 || config.legendPosX == 3) {
					availableLegendWidth = availableWidth - Math.ceil(ctx.chartSpaceScale * Math.ceil(ctx.chartSpaceScale * config.legendSpaceLeftText)) - Math.ceil(ctx.chartSpaceScale * config.legendSpaceRightText);
				} else {
					availableLegendWidth = width - borderRHeight - borderLHeight - Math.ceil(ctx.chartSpaceScale * config.spaceLeft) - Math.ceil(ctx.chartSpaceScale * config.spaceRight) - Math.ceil(ctx.chartSpaceScale * Math.ceil(ctx.chartSpaceScale * config.legendSpaceLeftText)) - Math.ceil(ctx.chartSpaceScale * config.legendSpaceRightText);
				}
				if (config.legendBorders == true || config.legendFillColor != "rgba(0,0,0,0)") availableLegendWidth -= (config.legendBorders * (isBorder(config.legendBordersSelection, "RIGHT") + isBorder(config.legendBordersSelection, "LEFT")) * (Math.ceil(ctx.chartLineScale * config.legendBordersWidth)) + Math.ceil(ctx.chartSpaceScale * config.legendBordersSpaceLeft) + Math.ceil(ctx.chartSpaceScale * config.legendBordersSpaceRight));
				maxLegendOnLine = Min([Math.floor((availableLegendWidth + Math.ceil(ctx.chartSpaceScale * config.legendSpaceBetweenTextHorizontal)) / (widestLegend + Math.ceil(ctx.chartSpaceScale * config.legendSpaceBetweenTextHorizontal))), config.maxLegendCols]);
				nbLegendLines = Math.ceil(nbeltLegend / maxLegendOnLine);
				nbLegendCols = Math.ceil(nbeltLegend / nbLegendLines);
				msrLegend = measureLegend(data, ctx, config, widestLegend, highestLegend, nbLegendLines, nbLegendCols, availableLegendWidth);
				legendHeight = msrLegend.legendHeight;
				if (config.legendPosY == 0) {
					yLegendPos = topNotUsableHeight - Math.ceil(ctx.chartSpaceScale * config.graphSpaceBefore);
					topNotUsableHeight += legendHeight;
				} else {
					yLegendPos = height - bottomNotUsableHeight - legendHeight;
					bottomNotUsableHeight += legendHeight;
				}
				availableHeight -= legendHeight;
			} else if (config.legendPosX == 0 || config.legendPosX == 4) {
				var availableLegendHeight, maxLegendOnCols;
				availableLegendHeight = availableHeight - Math.ceil(ctx.chartSpaceScale * Math.ceil(ctx.chartSpaceScale * config.legendSpaceBeforeText)) - Math.ceil(ctx.chartSpaceScale * config.legendSpaceAfterText);
				availableLegendWidth = availableWidth - Math.ceil(ctx.chartSpaceScale * Math.ceil(ctx.chartSpaceScale * config.legendSpaceLeftText)) - Math.ceil(ctx.chartSpaceScale * config.legendSpaceRightText);
				if (config.legendBorders == true || config.legendFillColor != "rgba(0,0,0,0)") availableLegendHeight -= (config.legendBorders * (isBorder(config.legendBordersSelection, "BOTTOM") + isBorder(config.legendBordersSelection, "TOP")) * (Math.ceil(ctx.chartLineScale * config.legendBordersWidth)) + Math.ceil(ctx.chartSpaceScale * config.legendBordersSpaceBefore) + Math.ceil(ctx.chartSpaceScale * config.legendBordersSpaceAfter));
				maxLegendOnCols = Min([Math.floor((availableLegendHeight + Math.ceil(ctx.chartSpaceScale * config.legendSpaceBetweenTextVertical)) / (highestLegend + Math.ceil(ctx.chartSpaceScale * config.legendSpaceBetweenTextVertical))), config.maxLegendLines]);
				nbLegendCols = Math.ceil(nbeltLegend / maxLegendOnCols);
				nbLegendLines = Math.ceil(nbeltLegend / nbLegendCols);
				msrLegend = measureLegend(data, ctx, config, widestLegend, highestLegend, nbLegendLines, nbLegendCols, availableLegendWidth);
				legendWidth = msrLegend.legendWidth;
				if (config.legendPosX == 0) {
					xLegendPos = leftNotUsableWidth;
					leftNotUsableWidth += legendWidth;
				} else {
					xLegendPos = width - rightNotUsableWidth - legendWidth;
					rightNotUsableWidth += legendWidth;
				}
				availableWidth -= legendWidth;
			}
		}
		//// Step 7 - Compute Y Unit height and position;
		var yAxisUnit2 = "";
		if (config.yAxisRight) {
			yAxisUnit2 = config.yAxisUnit2;
			if (yAxisUnit2 == '') yAxisUnit2 = config.yAxisUnit;
		}
		var yAxisUnitPosY = 0;
		var yAxisUnitHeight = 0;
		var yAxisUnitWidth = 0;
		var yAxisUnit2Width = 0;
		if (drawAxis && ((config.yAxisUnit.trim() != "" && config.yAxisLeft) || (yAxisUnit2.trim() != "" && config.yAxisRight))) {
			yAxisUnitHeight = (Math.ceil(ctx.chartTextScale * config.yAxisUnitFontSize)) * (config.yAxisUnit.split("\n").length || 1) + Math.ceil(ctx.chartSpaceScale * config.yAxisUnitSpaceBefore) + Math.ceil(ctx.chartSpaceScale * config.yAxisUnitSpaceAfter);
			ctx.font = config.yAxisUnitFontStyle + " " + (Math.ceil(ctx.chartTextScale * config.yAxisUnitFontSize)).toString() + "px " + config.yAxisUnitFontFamily;
			var yAxisUnitSize;
			yAxisUnitSize = ctx.measureTextMultiLine(config.yAxisUnit, (Math.ceil(ctx.chartTextScale * config.yAxisUnitFontSize)));
			yAxisUnitWidth = yAxisUnitSize.textWidth;
			yAxisUnitSize = ctx.measureTextMultiLine(yAxisUnit2, (Math.ceil(ctx.chartTextScale * config.yAxisUnitFontSize)));
			yAxisUnit2Width = yAxisUnitSize.textWidth;
			yAxisUnitPosY = topNotUsableHeight + Math.ceil(ctx.chartSpaceScale * config.yAxisUnitSpaceBefore) + yAxisUnitSize.textHeight;
			if (config.yAxisUnitBackgroundColor != "none" || config.yAxisUnitBorders) {
				yAxisUnitHeight += 2 * (Math.ceil(ctx.chartSpaceScale * config.yAxisUnitBordersYSpace));
				yAxisUnitPosY += Math.ceil(ctx.chartSpaceScale * config.yAxisUnitBordersYSpace);
			}
			if (config.yAxisUnitBorders) {
				yAxisUnitHeight += (isBorder(config.yAxisUnitBordersSelection, "TOP") + isBorder(config.yAxisUnitBordersSelection, "BOTTOM")) * (Math.ceil(ctx.chartLineScale * config.yAxisUnitBordersWidth));
				yAxisUnitPosY += isBorder(config.yAxisUnitBordersSelection, "TOP") * Math.ceil(ctx.chartLineScale * config.yAxisUnitBordersWidth);
			}
			topNotUsableHeight += yAxisUnitHeight;
			availableHeight -= yAxisUnitHeight;
		}
		//// Step 8 - compute Labels width;
		var widestXLabel = 0;
		var highestXLabel = 1;
		var widestTXLabel = 0;
		var highestTXLabel = 1;
		var xAxisLabelHeight = 0;
		var xTAxisLabelHeight = 0;
		var xAxisLabelPos = 0;
		var xTAxisLabelPos = 0;
		var widestYLabel = 0;
		var highestYLabel = 1;
		var widestYLabel2 = 0;
		var highestYLabel2 = 1;
		var yAxisLabelWidth = 0;
		var yAxisLabelPosLeft = 0;
		var yAxisLabelPosRight = 0;
		if (drawAxis) {
			var textMsr;
			// compute widest X label
			ctx.font = config.scaleFontStyle + " " + (Math.ceil(ctx.chartTextScale * config.scaleFontSize)).toString() + "px " + config.scaleFontFamily;
			widestXLabel = Math.max(1, Math.ceil(ctx.chartTextScale * config.xScaleLabelsMinimumWidth));
			widestTXLabel = widestXLabel;
			for (i = 0; i < data.labels.length; i++) {
				if (showLabels(ctx, data, config, i) === true) {
					textMsr = ctx.measureTextMultiLine(fmtChartJS(config, data.labels[i], config.fmtXLabel), (Math.ceil(ctx.chartTextScale * config.scaleFontSize)));
					//If the text length is longer - make that equal to longest text!
					widestXLabel = Math.max(textMsr.textWidth, widestXLabel);
					highestXLabel = Math.max(textMsr.textHeight, highestXLabel);
				}
			}
			if (typeof data.Labels2 == "object" && config.xAxisBottom && config.xAxisTop) {
				ctx.font = config.scaleFontStyle + " " + (Math.ceil(ctx.chartTextScale * config.scaleFontSize)).toString() + "px " + config.scaleFontFamily;
				for (i = 0; i < data.Labels2.length; i++) {
					if (showLabels(ctx, data, config, i) === true) {
						textMsr = ctx.measureTextMultiLine(fmtChartJS(config, data.Labels2[i], config.fmtTopXLabel), (Math.ceil(ctx.chartTextScale * config.scaleFontSize)));
						//If the text length is longer - make that equal to longest text!
						widestTXLabel = Math.max(textMsr.textWidth, widestTXLabel);
						highestTXLabel = Math.max(textMsr.textHeight, highestTXLabel);
					}
				}
			} else {
				widestTXLabel = widestXLabel;
				highestTXLabel = highestXLabel;
			}
			// xAxisLabel height;
			if (typeof(config.xAxisLabel) != "undefined" && config.xAxisBottom) {
				if (config.xAxisLabel.trim() != "") {
					xAxisLabelHeight = (Math.ceil(ctx.chartTextScale * config.xAxisFontSize)) * (config.xAxisLabel.split("\n").length || 1) + Math.ceil(ctx.chartSpaceScale * config.xAxisLabelSpaceBefore) + Math.ceil(ctx.chartSpaceScale * config.xAxisLabelSpaceAfter);
					xAxisLabelPos = (height - bottomNotUsableHeight) - Math.ceil(ctx.chartSpaceScale * config.xAxisLabelSpaceAfter);
					if (config.xAxisLabelBackgroundColor != "none" || config.footNoteBorders) {
						xAxisLabelHeight += 2 * (Math.ceil(ctx.chartSpaceScale * config.xAxisLabelBordersYSpace));
						xAxisLabelPos -= Math.ceil(ctx.chartSpaceScale * config.xAxisLabelBordersYSpace);
					}
					if (config.xAxisLabelBorders) {
						xAxisLabelHeight += (isBorder(config.xAxisLabelBordersSelection, "TOP") + isBorder(config.xAxisLabelBordersSelection, "BOTTOM")) * (Math.ceil(ctx.chartLineScale * config.xAxisLabelBordersWidth));
						xAxisLabelPos -= isBorder(config.xAxisLabelBordersSelection, "BOTTOM") * Math.ceil(ctx.chartLineScale * config.xAxisLabelBordersWidth);
					}
				}
			}
			var tLabelT;
			tLabelT = config.xAxisLabel;
			if (typeof(config.xTAxisLabel) != "undefined" && config.xAxisTop) {
				if (config.xTAxisLabel.trim() != "") tLabelT = config.xTAxisLabel;
			}
			if (typeof(tLabelT) != "undefined" && config.xAxisTop) {
				if (tLabelT.trim() != "") {
					xTAxisLabelHeight = (Math.ceil(ctx.chartTextScale * config.xAxisFontSize)) * (tLabelT.split("\n").length || 1) + Math.ceil(ctx.chartSpaceScale * config.xAxisLabelSpaceBefore) + Math.ceil(ctx.chartSpaceScale * config.xAxisLabelSpaceAfter);
					xTAxisLabelPos = topNotUsableHeight + Math.ceil(ctx.chartSpaceScale * config.xAxisLabelSpaceBefore);
					if (config.xAxisLabelBackgroundColor != "none") {
						xTAxisLabelHeight += 2 * (Math.ceil(ctx.chartSpaceScale * config.xAxisLabelBordersYSpace));
						xTAxisLabelPos += Math.ceil(ctx.chartSpaceScale * config.xAxisLabelBordersYSpace);
					}
					if (config.xAxisLabelBorders) {
						xTAxisLabelHeight += (isBorder(config.xAxisLabelBordersSelection, "TOP") + isBorder(config.xAxisLabelBordersSelection, "BOTTOM")) * (Math.ceil(ctx.chartLineScale * config.xAxisLabelBordersWidth));
						xTAxisLabelPos += isBorder(config.xAxisLabelBordersSelection, "TOP") * Math.ceil(ctx.chartLineScale * config.xAxisLabelBordersWidth);
					}
				}
			}
			// compute widest Y Label Width
			widestYLabel = Math.max(1, Math.ceil(ctx.chartTextScale * config.yScaleLabelsMinimumWidth));
			widestYLabel2 = widestYLabel;
			if (ylabels != null && ylabels != "nihil") {
				ctx.font = config.scaleFontStyle + " " + (Math.ceil(ctx.chartTextScale * config.scaleFontSize)).toString() + "px " + config.scaleFontFamily;
				for (i = ylabels.length - 1; i >= 0; i--) {
					if (typeof(ylabels[i]) == "string") {
						if (showYLabels(ctx, data, config, i, ylabels[i])) {
							if (ylabels[i].trim() != "") {
								//								textMsr = ctx.measureTextMultiLine(fmtChartJS(config, ylabels[i], config.fmtYLabel), (Math.ceil(ctx.chartTextScale*config.scaleFontSize)));
								textMsr = ctx.measureTextMultiLine(ylabels[i], (Math.ceil(ctx.chartTextScale * config.scaleFontSize)));
								widestYLabel = Math.max(widestYLabel, textMsr.textWidth);
								highestYLabel = Math.max(highestYLabel, textMsr.textHeight);
							}
						}
					}
				}
			}
			if (ylabels2 != null && config.yAxisRight) {
				ctx.font = config.scaleFontStyle + " " + (Math.ceil(ctx.chartTextScale * config.scaleFontSize)).toString() + "px " + config.scaleFontFamily;
				for (i = ylabels2.length - 1; i >= 0; i--) {
					if (typeof(ylabels2[i]) == "string") {
						if (showYLabels(ctx, data, config, i, ylabels2[i])) {
							//							textMsr = ctx.measureTextMultiLine(fmtChartJS(config, ylabels2[i], config.fmtYLabel2), (Math.ceil(ctx.chartTextScale*config.scaleFontSize)));
							textMsr = ctx.measureTextMultiLine(ylabels2[i], (Math.ceil(ctx.chartTextScale * config.scaleFontSize)));
							widestYLabel2 = Math.max(textMsr.textWidth, widestYLabel2);
							highestYLabel2 = Math.max(textMsr.textHeight, highestYLabel2);
						}
					}
				}
			} else {
				widestYLabel2 = widestYLabel;
				highestYLabel2 = highestYLabel;
			}
			// yAxisLabel width;
			if (typeof(config.yAxisLabel) != "undefined" && (config.yAxisRight || config.yAxisLeft)) {
				if (config.yAxisLabel.trim() != "") {
          yAxisFontSize=config.yAxisFontSize;
          if (config.yAxisRight) {
            if (config.yAxisFontSize2 > config.yAxisFontSize)yAxisFontSize=config.yAxisFontSize2;
          }
					yAxisLabelWidth = (Math.ceil(ctx.chartTextScale * yAxisFontSize)) * (config.yAxisLabel.split("\n").length || 1) + Math.ceil(ctx.chartSpaceScale * config.yAxisLabelSpaceLeft) + Math.ceil(ctx.chartSpaceScale * config.yAxisLabelSpaceRight);
					yAxisLabelPosLeft = leftNotUsableWidth + Math.ceil(ctx.chartSpaceScale * config.yAxisLabelSpaceLeft) + (Math.ceil(ctx.chartTextScale * yAxisFontSize));
					yAxisLabelPosRight = (width - rightNotUsableWidth) - Math.ceil(ctx.chartSpaceScale * config.yAxisLabelSpaceLeft) - (Math.ceil(ctx.chartTextScale * yAxisFontSize));
					if (config.yAxisLabelBackgroundColor != "none" || config.yAxisLabelBorders) {
						yAxisLabelWidth += 2 * (Math.ceil(ctx.chartSpaceScale * config.yAxisLabelBordersYSpace));
						yAxisLabelPosLeft += Math.ceil(ctx.chartSpaceScale * config.yAxisLabelBordersYSpace);
						yAxisLabelPosRight -= Math.ceil(ctx.chartSpaceScale * config.yAxisLabelBordersYSpace);
					}
					if (config.yAxisLabelBorders) {
						yAxisLabelWidth += (isBorder(config.yAxisLabelBordersSelection, "TOP") + isBorder(config.yAxisLabelBordersSelection, "BOTTOM")) * (Math.ceil(ctx.chartLineScale * config.yAxisLabelBordersWidth));
						yAxisLabelPosLeft += isBorder(config.yAxisLabelBordersSelection, "TOP") * Math.ceil(ctx.chartLineScale * config.yAxisLabelBordersWidth);
						yAxisLabelPosRight -= isBorder(config.yAxisLabelBordersSelection, "TOP") * Math.ceil(ctx.chartLineScale * config.yAxisLabelBordersWidth);
					}
				}
			}
		}
		//// Step 9 - Compute x Label rotation;
		var rotateLabels = 0;
		var rotateTLabels = 0;
		var xLabelWidth = 0;
		var xTLabelWidth = 0;
		var xLabelHeight = 0;
		var xTLabelHeight = 0;
		var xLabelPos = 0;
		var xTLabelPos = 0;
		var widestLabel, highestLabel, nblab, labelAvailableWidth;
		if (drawAxis && config.xAxisBottom) {
			labelAvailableWidth = availableWidth;
			if (reverseAxis == false) {
				widestLabel = widestXLabel;
				highestLabel = highestXLabel;
				nblab = data.labels.length;
				if (config.yAxisLeft == true) labelAvailableWidth -= (widestYLabel + Math.ceil(ctx.chartSpaceScale * config.yAxisSpaceLeft) + Math.ceil(ctx.chartSpaceScale * config.yAxisSpaceRight));
				if (config.yAxisRight == true) labelAvailableWidth -= (widestYLabel2 + Math.ceil(ctx.chartSpaceScale * config.yAxisSpaceLeft) + Math.ceil(ctx.chartSpaceScale * config.yAxisSpaceRight));
			} else {
				widestLabel = widestYLabel;
				highestLabel = highestYLabel;
				nblab = ylabels.length;
				if (config.yAxisLeft == true) labelAvailableWidth -= (widestXLabel + Math.ceil(ctx.chartSpaceScale * config.yAxisSpaceLeft) + Math.ceil(ctx.chartSpaceScale * config.yAxisSpaceRight));
				if (config.yAxisRight == true) labelAvailableWidth -= (widestTXLabel + Math.ceil(ctx.chartSpaceScale * config.yAxisSpaceLeft) + Math.ceil(ctx.chartSpaceScale * config.yAxisSpaceRight));
			}
			if (typeof(config.yAxisLabel) != "undefined") {
				if (config.yAxisLabel.trim() != "") {
					if (config.yAxisRight) labelAvailableWidth -= yAxisLabelWidth;
					if (config.yAxisLeft) labelAvailableWidth -= yAxisLabelWidth;
				}
			}
			if (config.rotateLabels == "smart") {
				rotateLabels = 0;
				if ((labelAvailableWidth + Math.ceil(ctx.chartTextScale * config.xAxisSpaceBetweenLabels)) / nblab < (widestLabel + Math.ceil(ctx.chartTextScale * config.xAxisSpaceBetweenLabels))) {
					rotateLabels = 45;
					if (labelAvailableWidth / nblab < Math.abs(Math.cos(rotateLabels * Math.PI / 180) * widestLabel)) {
						rotateLabels = 90;
					}
				}
			} else {
				rotateLabels = config.rotateLabels;
				if (rotateLabels < 0) rotateLabels = 0;
				if (rotateLabels > 180) rotateLabels = 180;
			}
			if (rotateLabels > 90) rotateLabels += 180;
			xLabelHeight = Math.abs(Math.sin(rotateLabels * Math.PI / 180) * widestLabel) + Math.abs(Math.sin((rotateLabels + 90) * Math.PI / 180) * highestLabel);
			xLabelWidth = Math.abs(Math.cos(rotateLabels * Math.PI / 180) * widestLabel) + Math.abs(Math.cos((rotateLabels + 90) * Math.PI / 180) * highestLabel);
			xLabelPos = height - bottomNotUsableHeight - xAxisLabelHeight - xLabelHeight - Math.ceil(ctx.chartSpaceScale * config.xAxisSpaceAfter);
		}
		if (drawAxis && config.xAxisTop) {
			labelAvailableWidth = availableWidth;
			if (reverseAxis == false) {
				widestLabel = widestTXLabel;
				highestLabel = highestTXLabel;
				nblab = data.labels.length;
				if (config.yAxisLeft == true) labelAvailableWidth -= (widestYLabel + Math.ceil(ctx.chartSpaceScale * config.yAxisSpaceLeft) + Math.ceil(ctx.chartSpaceScale * config.yAxisSpaceRight));
				if (config.yAxisRight == true) labelAvailableWidth -= (widestYLabel2 + Math.ceil(ctx.chartSpaceScale * config.yAxisSpaceLeft) + Math.ceil(ctx.chartSpaceScale * config.yAxisSpaceRight));
			} else {
				widestLabel = widestYLabel2;
				highestLabel = highestYLabel2;
				nblab = ylabels2.length;
				if (config.yAxisLeft == true) labelAvailableWidth -= (widestXLabel + Math.ceil(ctx.chartSpaceScale * config.yAxisSpaceLeft) + Math.ceil(ctx.chartSpaceScale * config.yAxisSpaceRight));
				if (config.yAxisRight == true) labelAvailableWidth -= (widestTXLabel + Math.ceil(ctx.chartSpaceScale * config.yAxisSpaceLeft) + Math.ceil(ctx.chartSpaceScale * config.yAxisSpaceRight));
			}
			if (typeof(config.yAxisLabel) != "undefined") {
				if (config.yAxisLabel.trim() != "") {
					if (config.yAxisRight) labelAvailableWidth -= yAxisLabelWidth;
					if (config.yAxisLeft) labelAvailableWidth -= yAxisLabelWidth;
				}
			}
			if (config.rotateTLabels == "smart") {
				rotateTLabels = 0;
				if ((labelAvailableWidth + Math.ceil(ctx.chartTextScale * config.xAxisSpaceBetweenLabels)) / nblab < (widestLabel + Math.ceil(ctx.chartTextScale * config.xAxisSpaceBetweenLabels))) {
					rotateTLabels = 45;
					if (labelAvailableWidth / nblab < Math.abs(Math.cos(rotateTLabels * Math.PI / 180) * widestLabel)) {
						rotateTLabels = 90;
					}
				}
			} else {
				rotateTLabels = config.rotateTLabels;
				if (rotateTLabels < 0) rotateTLabels = 0;
				if (rotateTLabels > 180) rotateTLabels = 180;
			}
			if (rotateLabels > 90) rotateLabels += 180;
			xTLabelHeight = Math.abs(Math.sin(rotateTLabels * Math.PI / 180) * widestLabel) + Math.abs(Math.sin((rotateTLabels + 90) * Math.PI / 180) * highestLabel);
			xTLabelWidth = Math.abs(Math.cos(rotateTLabels * Math.PI / 180) * widestLabel) + Math.abs(Math.cos((rotateTLabels + 90) * Math.PI / 180) * highestLabel);
			xTLabelPos = topNotUsableHeight + xTAxisLabelHeight + Math.ceil(ctx.chartSpaceScale * config.xAxisSpaceBefore);
		}
		// recompute availableWidth/Height with axis label width/height and label width/height;
		var prevLeftNotUsableWidth = leftNotUsableWidth;
		var prevRightNotUsableWidth = rightNotUsableWidth;
		if (drawAxis && config.yAxisLeft) {
			if (reverseAxis == false) leftNotUsableWidth += yAxisLabelWidth + widestYLabel + Math.ceil(ctx.chartSpaceScale * config.yAxisSpaceLeft) + Math.ceil(ctx.chartSpaceScale * config.yAxisSpaceRight);
			else leftNotUsableWidth += yAxisLabelWidth + widestXLabel + Math.ceil(ctx.chartSpaceScale * config.yAxisSpaceLeft) + Math.ceil(ctx.chartSpaceScale * config.yAxisSpaceRight);
		}
		if (drawAxis && config.yAxisRight) {
			if (reverseAxis == false) rightNotUsableWidth += yAxisLabelWidth + widestYLabel2 + Math.ceil(ctx.chartSpaceScale * config.yAxisSpaceLeft) + Math.ceil(ctx.chartSpaceScale * config.yAxisSpaceRight);
			else rightNotUsableWidth += yAxisLabelWidth + widestTXLabel + Math.ceil(ctx.chartSpaceScale * config.yAxisSpaceLeft) + Math.ceil(ctx.chartSpaceScale * config.yAxisSpaceRight);
		}
		availableWidth = width - leftNotUsableWidth - rightNotUsableWidth;
		if (drawAxis && config.xAxisTop) {
			if (reverseAxis == false) topNotUsableHeight += xTAxisLabelHeight + xTLabelHeight + Math.ceil(ctx.chartSpaceScale * config.xAxisSpaceBefore) + Math.ceil(ctx.chartSpaceScale * config.xAxisSpaceAfter);
			else {
				var yTLabelHeight = Math.abs(Math.sin(rotateTLabels * Math.PI / 180) * widestYLabel2) + Math.abs(Math.sin((rotateTLabels + 90) * Math.PI / 180) * highestYLabel2);
				topNotUsableHeight += xAxisLabelHeight + yTLabelHeight + Math.ceil(ctx.chartSpaceScale * config.xAxisSpaceBefore) + Math.ceil(ctx.chartSpaceScale * config.xAxisSpaceAfter);
			}
		}
		if (drawAxis && config.xAxisBottom) {
			if (reverseAxis == false) bottomNotUsableHeight += xAxisLabelHeight + xLabelHeight + Math.ceil(ctx.chartSpaceScale * config.xAxisSpaceBefore) + Math.ceil(ctx.chartSpaceScale * config.xAxisSpaceAfter);
			else {
				var yTLabelHeight = Math.abs(Math.sin(rotateLabels * Math.PI / 180) * widestYLabel) + Math.abs(Math.sin((rotateLabels + 90) * Math.PI / 180) * highestYLabel);
				bottomNotUsableHeight += xAxisLabelHeight + yTLabelHeight + Math.ceil(ctx.chartSpaceScale * config.xAxisSpaceBefore) + Math.ceil(ctx.chartSpaceScale * config.xAxisSpaceAfter);
			}
		}
		availableHeight = height - topNotUsableHeight - bottomNotUsableHeight;
		// compute space for Legend
		if (widestLegend > -99999998) {
			if (nbLegendLines == 0) { // compute nbLegendLines/nbLegendCols if not yet done;
				availableLegendWidth = availableWidth - Math.ceil(ctx.chartSpaceScale * Math.ceil(ctx.chartSpaceScale * config.legendSpaceLeftText)) - Math.ceil(ctx.chartSpaceScale * config.legendSpaceRightText);
				maxLegendOnLine = Min([Math.floor((availableLegendWidth + Math.ceil(ctx.chartSpaceScale * config.legendSpaceBetweenTextHorizontal)) / (widestLegend + Math.ceil(ctx.chartSpaceScale * config.legendSpaceBetweenTextHorizontal))), config.maxLegendCols]);
				nbLegendLines = Math.ceil(nbeltLegend / maxLegendOnLine);
				nbLegendCols = Math.ceil(nbeltLegend / nbLegendLines);
				msrLegend = measureLegend(data, ctx, config, widestLegend, highestLegend, nbLegendLines, nbLegendCols, availableLegendWidth);
			}
			legendHeight = msrLegend.legendHeight;
			legendWidth = msrLegend.legendWidth;
			switch (config.legendPosY) {
				case 0: // already computed;
					break;
				case 1:
					yLegendPos = topNotUsableHeight;
					break;
				case 2:
					yLegendPos = topNotUsableHeight + (availableHeight / 2) - legendHeight / 2;
					break;
				case -2:
					yLegendPos = height / 2 - legendHeight / 2;
					break;
				case 3:
					yLegendPos = height - bottomNotUsableHeight - legendHeight;
					break;
				case 4: // already Computed;
					break;
				default:
					yLegendPos = topNotUsableHeight;
					break;
			}
			switch (config.legendPosX) {
				case 0:
					if (config.legendPosY == 0 || config.legendPosY == 4) xLegendPos = prevLeftNotUsableWidth;
					break;
				case 1:
					xLegendPos = leftNotUsableWidth;
					break;
				case 2:
					xLegendPos = leftNotUsableWidth + (availableWidth) / 2 - legendWidth / 2;
					break;
				case -2:
					xLegendPos = width / 2 - (legendWidth / 2);
					break;
				case 3:
					xLegendPos = width - rightNotUsableWidth - legendWidth;
					break;
				case 4:
					if (config.legendPosY == 0 || config.legendPosY == 4) xLegendPos = width - prevRightNotUsableWidth - legendWidth;
					break;
				default:
					xLegendPos = width - rightNotUsableWidth;
					break;
			}
		}
		// correct space;
		if (drawAxis && config.yAxisLeft && yAxisUnitWidth > 0) leftNotUsableWidth = Math.max(leftNotUsableWidth, borderLHeight + config.spaceLeft + (config.yAxisUnitBorders && isBorder(config.yAxisUnitBordersSelection, "LEFT")) * (config.yAxisUnitBordersWidth) + (config.yAxisUnitBackgroundColor != "none" || config.yAxisUnitBorders) * Math.ceil(ctx.chartSpaceScale * config.yAxisUnitBordersYSpace) + 1 + yAxisUnitWidth / 2);
		if (drawAxis && config.yAxisRight && yAxisUnit2Width > 0) rightNotUsableWidth = Math.max(rightNotUsableWidth, borderRHeight + config.spaceRight + (config.yAxisUnitBorders && isBorder(config.yAxisUnitBordersSelection, "RIGHT")) * (config.yAxisUnitBordersWidth) + (config.yAxisUnitBackgroundColor != "none" || config.yAxisUnitBorders) * Math.ceil(ctx.chartSpaceScale * config.yAxisUnitBordersYSpace) + 1 + yAxisUnit2Width / 2);
		if (config.inGraphDataShow && (typegraph == "Line" || typegraph == "HorizontalBar" || typegraph == "HorizontalStackedBar")) {
			rightNotUsableWidth = Math.max(rightNotUsableWidth, Math.max(widestYLabel, widestYLabel2) + 1 + borderRHeight);
			leftNotUsableWidth = Math.max(leftNotUsableWidth, Math.max(widestYLabel, widestYLabel2) + 1 + borderLHeight);
		}
		if (typegraph == "Line" && (config.xAxisTop || config.xAxisBottom)) {
			rightNotUsableWidth = Math.max(rightNotUsableWidth, Math.max(config.xAxisBottom * Math.cos(rotateLabels) * widestXLabel / 2, config.xAxisTop * Math.cos(rotateTLabels) * widestTXLabel / 2) + 1 + borderRHeight);
			leftNotUsableWidth = Math.max(leftNotUsableWidth, Math.max(config.xAxisBottom * Math.cos(rotateLabels) * widestXLabel / 2, config.xAxisTop * Math.cos(rotateTLabels) * widestTXLabel / 2) + 1 + borderLHeight);
		}
		if ((typegraph == "HorizontalBar" || typegraph == "HorizontalStackedBar") && (config.xAxisTop || config.xAxisBottom)) {
			rightNotUsableWidth = Math.max(rightNotUsableWidth, config.xAxisBottom * Math.cos(rotateLabels) * widestYLabel / 2 + 1 + borderRHeight);
			leftNotUsableWidth = Math.max(leftNotUsableWidth, config.xAxisBottom * Math.cos(rotateLabels) * widestYLabel / 2 + 1 + borderLHeight);
		}
		if (typegraph == "Line" && config.inGraphDataShow) {
			topNotUsableHeight = Math.max(topNotUsableHeight, Math.max(highestYLabel, highestYLabel2) + 1 + borderTHeight);
		}
		if (typegraph == "Line" && ctx.tpchartSub == "Bubble") {
			rightNotUsableWidth = Math.max(rightNotUsableWidth, availableWidth * config.bubbleMaxRadius / 2 + 1 + borderRHeight);
			leftNotUsableWidth = Math.max(leftNotUsableWidth, availableWidth * config.bubbleMaxRadius / 2 + 1 + borderLHeight);
			topNotUsableHeight += availableHeight * config.bubbleMaxRadius / 2;
		}
		availableWidth = width - rightNotUsableWidth - leftNotUsableWidth;
		availableHeight = height - topNotUsableHeight - bottomNotUsableHeight;
		// ----------------------- DRAW EXTERNAL ELEMENTS -------------------------------------------------
		dispCrossImage(ctx, config, width / 2, height / 2, width / 2, height / 2, false, data, -1, -1);
		if (typeof config.initFunction == "function") config.initFunction("INITFUNCTION", ctx, data, null, -1, -1, {
			animationValue: 0,
			cntiter: 0,
			config: config,
			borderX: 0,
			borderY: 0,
			midPosX: 0,
			midPosY: 0
		});
		if (ylabels != "nihil") {
			// Draw Borders
			if (borderHeight > 0) {
				ctx.save();
				ctx.beginPath();
				ctx.setLineDash(lineStyleFn(config.canvasBordersStyle));
				ctx.strokeStyle = config.canvasBordersColor;
				ctx.lineWidth = borderHeight;
				ctx.setLineDash(lineStyleFn(config.canvasBordersStyle));
				ctx.strokeStyle = config.canvasBordersColor;
				ctx.fillStyle = "rgba(0,0,0,0)";
				ctx.drawRectangle({
					x: 0 + borderLHeight / 2,
					y: 0 + borderTHeight / 2,
					width: width - borderRHeight / 2 - borderLHeight / 2,
					height: height - borderTHeight / 2 - borderBHeight / 2,
					borders: true,
					bordersWidth: borderHeight,
					borderSelection: config.canvasBordersSelection,
					borderRadius: config.canvasBordersRadius,
					fill: false,
					stroke: true
				});
				ctx.setLineDash([]);
				ctx.restore();
			}
			// Draw Graph Title
			if (graphTitleHeight > 0) {
				ctx.save();
				ctx.beginPath();
				ctx.font = config.graphTitleFontStyle + " " + (Math.ceil(ctx.chartTextScale * config.graphTitleFontSize)).toString() + "px " + config.graphTitleFontFamily;
				ctx.fillStyle = config.graphTitleFontColor;
				ctx.textBaseline = "top";
				var textPos;
				switch (config.graphTitleAlign) {
					case "right":
						ctx.textAlign = "right";
						textPos = Math.ceil(ctx.chartSpaceScale * config.spaceLeft) + (width - Math.ceil(ctx.chartSpaceScale * config.spaceLeft) - Math.ceil(ctx.chartSpaceScale * config.spaceRight)) / 2;
						textPos = width - Math.ceil(ctx.chartSpaceScale * (config.spaceRight + config.graphTitleShift)) - borderRHeight;
						break;
					case "left":
						ctx.textAlign = "left";
						textPos = borderLHeight + Math.ceil(ctx.chartSpaceScale * (config.spaceLeft + config.graphTitleShift));
						break;
					default:
						ctx.textAlign = "center";
						textPos = borderLHeight + Math.ceil(ctx.chartSpaceScale * config.spaceLeft) + (width - borderRHeight - borderLHeight - Math.ceil(ctx.chartSpaceScale * config.spaceLeft) - Math.ceil(ctx.chartSpaceScale * config.spaceRight)) / 2;
						break;
				}
				setTextBordersAndBackground(ctx, config.graphTitle, (Math.ceil(ctx.chartTextScale * config.graphTitleFontSize)), textPos, graphTitlePosY, config.graphTitleBorders, config.graphTitleBordersSelection, config.graphTitleBordersColor, Math.ceil(ctx.chartLineScale * config.graphTitleBordersWidth), Math.ceil(ctx.chartSpaceScale * config.graphTitleBordersXSpace), Math.ceil(ctx.chartSpaceScale * config.graphTitleBordersYSpace), config.graphTitleBordersStyle, config.graphTitleBackgroundColor, "GRAPHTITLE", config.graphTitleBordersRadius);
				ctx.translate(textPos, graphTitlePosY);
				ctx.fillTextMultiLine(config.graphTitle, 0, 0, ctx.textBaseline, (Math.ceil(ctx.chartTextScale * config.graphTitleFontSize)), true, config.detectMouseOnText, ctx, "TITLE_TEXTMOUSE", 0, textPos, graphTitlePosY, -1, -1);
				ctx.stroke();
				ctx.restore();
			}
			// Draw Graph Sub-Title
			if (graphSubTitleHeight > 0) {
				ctx.save();
				ctx.beginPath();
				ctx.font = config.graphSubTitleFontStyle + " " + (Math.ceil(ctx.chartTextScale * config.graphSubTitleFontSize)).toString() + "px " + config.graphSubTitleFontFamily;
				ctx.fillStyle = config.graphSubTitleFontColor;
				switch (config.graphSubTitleAlign) {
					case "right":
						ctx.textAlign = "right";
						textPos = width - Math.ceil(ctx.chartSpaceScale * (config.spaceRight + config.graphSubTitleShift)) - borderRHeight;
						break;
					case "left":
						ctx.textAlign = "left";
						textPos = borderLHeight + Math.ceil(ctx.chartSpaceScale * (config.spaceLeft + config.graphSubTitleShift));
						break;
					default:
						ctx.textAlign = "center";
						textPos = borderLHeight + Math.ceil(ctx.chartSpaceScale * config.spaceLeft) + (width - borderRHeight - borderLHeight - Math.ceil(ctx.chartSpaceScale * config.spaceLeft) - Math.ceil(ctx.chartSpaceScale * config.spaceRight)) / 2;
						break;
				}
				ctx.textBaseline = "top";
				setTextBordersAndBackground(ctx, config.graphSubTitle, (Math.ceil(ctx.chartTextScale * config.graphSubTitleFontSize)), textPos, graphSubTitlePosY, config.graphSubTitleBorders, config.graphSubTitleBordersSelection, config.graphSubTitleBordersColor, Math.ceil(ctx.chartLineScale * config.graphSubTitleBordersWidth), Math.ceil(ctx.chartSpaceScale * config.graphSubTitleBordersXSpace), Math.ceil(ctx.chartSpaceScale * config.graphSubTitleBordersYSpace), config.graphSubTitleBordersStyle, config.graphSubTitleBackgroundColor, "GRAPHSUBTITLE", config.graphSubTitleBordersRadius);
				ctx.translate(textPos, graphSubTitlePosY);
				ctx.fillTextMultiLine(config.graphSubTitle, 0, 0, ctx.textBaseline, (Math.ceil(ctx.chartTextScale * config.graphSubTitleFontSize)), true, config.detectMouseOnText, ctx, "SUBTITLE_TEXTMOUSE", 0, textPos, graphSubTitlePosY, -1, -1);
				ctx.stroke();
				ctx.restore();
			}
			// Draw FootNote
			if (config.footNote.trim() != "") {
				ctx.save();
				ctx.font = config.footNoteFontStyle + " " + (Math.ceil(ctx.chartTextScale * config.footNoteFontSize)).toString() + "px " + config.footNoteFontFamily;
				ctx.fillStyle = config.footNoteFontColor;
				switch (config.footNoteAlign) {
					case "right":
						ctx.textAlign = "right";
						textPos = width - Math.ceil(ctx.chartSpaceScale * (config.spaceRight + config.footNoteShift)) - borderRHeight;
						break;
					case "left":
						ctx.textAlign = "left";
						textPos = borderLHeight + Math.ceil(ctx.chartSpaceScale * (config.spaceLeft + config.footNoteShift));
						break;
					default:
						ctx.textAlign = "center";
						textPos = leftNotUsableWidth + (availableWidth / 2);
						break;
				}
				ctx.textBaseline = "bottom";
				setTextBordersAndBackground(ctx, config.footNote, (Math.ceil(ctx.chartTextScale * config.footNoteFontSize)), textPos, footNotePosY, config.footNoteBorders, config.footNoteBordersSelection, config.footNoteBordersColor, Math.ceil(ctx.chartLineScale * config.footNoteBordersWidth), Math.ceil(ctx.chartSpaceScale * config.footNoteBordersXSpace), Math.ceil(ctx.chartSpaceScale * config.footNoteBordersYSpace), config.footNoteBordersStyle, config.footNoteBackgroundColor, "FOOTNOTE", config.footNoteBordersRadius);
				ctx.translate(textPos, footNotePosY);
				ctx.fillTextMultiLine(config.footNote, 0, 0, ctx.textBaseline, (Math.ceil(ctx.chartTextScale * config.footNoteFontSize)), true, config.detectMouseOnText, ctx, "FOOTNOTE_TEXTMOUSE", 0, textPos, footNotePosY, -1, -1);
				ctx.stroke();
				ctx.restore();
			}
			// Draw Y Axis Unit
			if (yAxisUnitHeight > 0) {
				if (config.yAxisLeft) {
					ctx.save();
					ctx.beginPath();
					ctx.font = config.yAxisUnitFontStyle + " " + (Math.ceil(ctx.chartTextScale * config.yAxisUnitFontSize)).toString() + "px " + config.yAxisUnitFontFamily;
					ctx.fillStyle = config.yAxisUnitFontColor;
					ctx.textAlign = "center";
					ctx.textBaseline = "bottom";
					setTextBordersAndBackground(ctx, config.yAxisUnit, (Math.ceil(ctx.chartTextScale * config.yAxisUnitFontSize)), leftNotUsableWidth, yAxisUnitPosY, config.yAxisUnitBorders, config.yAxisUnitBordersSelection, config.yAxisUnitBordersColor, Math.ceil(ctx.chartLineScale * config.yAxisUnitBordersWidth), Math.ceil(ctx.chartSpaceScale * config.yAxisUnitBordersXSpace), Math.ceil(ctx.chartSpaceScale * config.yAxisUnitBordersYSpace), config.yAxisUnitBordersStyle, config.yAxisUnitBackgroundColor, "YAXISUNIT", config.yAxisUnitBordersRadius);
					ctx.translate(leftNotUsableWidth, yAxisUnitPosY);
					ctx.fillTextMultiLine(config.yAxisUnit, 0, 0, ctx.textBaseline, (Math.ceil(ctx.chartTextScale * config.yAxisUnitFontSize)), true, config.detectMouseOnText, ctx, "YLEFTAXISUNIT_TEXTMOUSE", 0, leftNotUsableWidth, yAxisUnitPosY, -1, -1);
					ctx.stroke();
					ctx.restore();
				}
				if (config.yAxisRight && yAxisUnit2 != "") {
					ctx.save();
					ctx.beginPath();
					ctx.font = config.yAxisUnitFontStyle + " " + (Math.ceil(ctx.chartTextScale * config.yAxisUnitFontSize)).toString() + "px " + config.yAxisUnitFontFamily;
					ctx.fillStyle = config.yAxisUnitFontColor;
					ctx.textAlign = "center";
					ctx.textBaseline = "bottom";
					setTextBordersAndBackground(ctx, yAxisUnit2, (Math.ceil(ctx.chartTextScale * config.yAxisUnitFontSize)), width - rightNotUsableWidth, yAxisUnitPosY, config.yAxisUnitBorders, config.yAxisUnitBordersSelection, config.yAxisUnitBordersColor, Math.ceil(ctx.chartLineScale * config.yAxisUnitBordersWidth), Math.ceil(ctx.chartSpaceScale * config.yAxisUnitBordersXSpace), Math.ceil(ctx.chartSpaceScale * config.yAxisUnitBordersYSpace), config.yAxisUnitBordersStyle, config.yAxisUnitBackgroundColor, "YAXISUNIT", config.yAxisUnitBordersRadius);
					ctx.translate(width - rightNotUsableWidth, yAxisUnitPosY);
					ctx.fillTextMultiLine(yAxisUnit2, 0, 0, ctx.textBaseline, (Math.ceil(ctx.chartTextScale * config.yAxisUnitFontSize)), true, config.detectMouseOnText, ctx, "YRIGHTAXISUNIT_TEXTMOUSE", 0, width - rightNotUsableWidth, yAxisUnitPosY, -1, -1);
					ctx.stroke();
					ctx.restore();
				}
			}
			// Draw Y Axis Label
			if (yAxisLabelWidth > 0) {
				if (config.yAxisLeft) {
					ctx.save();
					ctx.beginPath();
					ctx.font = config.yAxisFontStyle + " " + (Math.ceil(ctx.chartTextScale * config.yAxisFontSize)).toString() + "px " + config.yAxisFontFamily;
					ctx.fillStyle = config.yAxisFontColor;
					ctx.textAlign = "center";
					ctx.textBaseline = "bottom";
					ctx.translate(yAxisLabelPosLeft, topNotUsableHeight + (availableHeight / 2));
					ctx.rotate(-(90 * (Math.PI / 180)));
					setTextBordersAndBackground(ctx, config.yAxisLabel, (Math.ceil(ctx.chartTextScale * config.yAxisFontSize)), 0, 0, config.yAxisLabelBorders, config.yAxisLabelBordersSelection, config.yAxisLabelBordersColor, Math.ceil(ctx.chartLineScale * config.yAxisLabelBordersWidth), Math.ceil(ctx.chartSpaceScale * config.yAxisLabelBordersXSpace), Math.ceil(ctx.chartSpaceScale * config.yAxisLabelBordersYSpace), config.yAxisLabelBordersStyle, config.yAxisLabelBackgroundColor, "YAXISLABELLEFT", config.yAxisLabelBordersRadius);
					ctx.fillTextMultiLine(config.yAxisLabel, 0, 0, ctx.textBaseline, (Math.ceil(ctx.chartTextScale * config.yAxisFontSize)), false, config.detectMouseOnText, ctx, "YLEFTAXISLABEL_TEXTMOUSE", -(90 * (Math.PI / 180)), yAxisLabelPosLeft, topNotUsableHeight + (availableHeight / 2), -1, -1);
					ctx.stroke();
					ctx.restore();
				}
				if (config.yAxisRight) {
					var yAxisLabel2 = config.yAxisLabel2;
					if (yAxisLabel2 == '') yAxisLabel2 = config.yAxisLabel;
					ctx.save();
					ctx.beginPath();
          if (config.yAxisFontSize2==0) {
            yAxisFontSize=config.yAxisFontSize;
          } else {
            yAxisFontSize=config.yAxisFontSize2;
          }
					ctx.font = config.yAxisFontStyle + " " + (Math.ceil(ctx.chartTextScale * yAxisFontSize)).toString() + "px " + config.yAxisFontFamily;
					if (config.yAxisFontColor2 == ""){
            ctx.fillStyle = config.yAxisFontColor;
          } else {
            ctx.fillStyle = config.yAxisFontColor2;
          }
					ctx.textAlign = "center";
					ctx.textBaseline = "bottom";
					ctx.translate(yAxisLabelPosRight, topNotUsableHeight + (availableHeight / 2));
					ctx.rotate(+(90 * (Math.PI / 180)));
					setTextBordersAndBackground(ctx, yAxisLabel2, (Math.ceil(ctx.chartTextScale * yAxisFontSize)), 0, 0, config.yAxisLabelBorders, config.yAxisLabelBordersSelection, config.yAxisLabelBordersColor, Math.ceil(ctx.chartLineScale * config.yAxisLabelBordersWidth), Math.ceil(ctx.chartSpaceScale * config.yAxisLabelBordersXSpace), Math.ceil(ctx.chartSpaceScale * config.yAxisLabelBordersYSpace), config.yAxisLabelBordersStyle, config.yAxisLabelBackgroundColor, "YAXISLABELLEFT", config.yAxisLabelBordersRadius);
					ctx.fillTextMultiLine(yAxisLabel2, 0, 0, ctx.textBaseline, (Math.ceil(ctx.chartTextScale * yAxisFontSize)), false, config.detectMouseOnText, ctx, "YRIGHTAXISLABEL_TEXTMOUSE", +(90 * (Math.PI / 180)), yAxisLabelPosRight, topNotUsableHeight + (availableHeight / 2), -1, -1);
					ctx.stroke();
					ctx.restore();
				}
			}
			// Draw bottom X Axis Label
			if (xAxisLabelHeight > 0) {
				if (config.xAxisBottom) {
					ctx.save();
					ctx.beginPath();
					ctx.font = config.xAxisFontStyle + " " + (Math.ceil(ctx.chartTextScale * config.xAxisFontSize)).toString() + "px " + config.xAxisFontFamily;
					ctx.fillStyle = config.xAxisFontColor;
					ctx.textAlign = "center";
					ctx.textBaseline = "bottom";
					setTextBordersAndBackground(ctx, config.xAxisLabel, (Math.ceil(ctx.chartTextScale * config.xAxisFontSize)), leftNotUsableWidth + (availableWidth / 2), xAxisLabelPos, config.xAxisLabelBorders, config.xAxisLabelBordersSelection, config.xAxisLabelBordersColor, Math.ceil(ctx.chartLineScale * config.xAxisLabelBordersWidth), Math.ceil(ctx.chartSpaceScale * config.xAxisLabelBordersXSpace), Math.ceil(ctx.chartSpaceScale * config.xAxisLabelBordersYSpace), config.xAxisLabelBordersStyle, config.xAxisLabelBackgroundColor, "XAXISLABEL", config.xAxisLabelBordersRadius);
					ctx.translate(leftNotUsableWidth + (availableWidth / 2), xAxisLabelPos);
					ctx.fillTextMultiLine(config.xAxisLabel, 0, 0, ctx.textBaseline, (Math.ceil(ctx.chartTextScale * config.xAxisFontSize)), true, config.detectMouseOnText, ctx, "XAXISLABEL_TEXTMOUSE", 0, leftNotUsableWidth + (availableWidth / 2), xAxisLabelPos, -1, -1);
					ctx.stroke();
					ctx.restore();
				}
				if (config.xAxisTop) {
					var xAxisLabel2 = config.xAxisLabel2;
					if (xAxisLabel2 == '') xAxisLabel2 = config.xAxisLabel;
					ctx.save();
					ctx.beginPath();
					ctx.font = config.xAxisFontStyle + " " + (Math.ceil(ctx.chartTextScale * config.xAxisFontSize)).toString() + "px " + config.xAxisFontFamily;
					ctx.fillStyle = config.xAxisFontColor;
					ctx.textAlign = "center";
					ctx.textBaseline = "top";
					setTextBordersAndBackground(ctx, xAxisLabel2, (Math.ceil(ctx.chartTextScale * config.xAxisFontSize)), leftNotUsableWidth + (availableWidth / 2), xTAxisLabelPos, config.xAxisLabelBorders, config.xAxisLabelBordersSelection, config.xAxisLabelBordersColor, Math.ceil(ctx.chartLineScale * config.xAxisLabelBordersWidth), Math.ceil(ctx.chartSpaceScale * config.xAxisLabelBordersXSpace), Math.ceil(ctx.chartSpaceScale * config.xAxisLabelBordersYSpace), config.xAxisLabelBordersStyle, config.xAxisLabelBackgroundColor, "XAXISLABEL", config.xAxisLabelBordersRadius);
					ctx.translate(leftNotUsableWidth + (availableWidth / 2), xTAxisLabelPos);
					ctx.fillTextMultiLine(xAxisLabel2, 0, 0, ctx.textBaseline, (Math.ceil(ctx.chartTextScale * config.xAxisFontSize)), true, config.detectMouseOnText, ctx, "XAXISLABEL_TEXTMOUSE", 0, leftNotUsableWidth + (availableWidth / 2), xAxisLabelPos, -1, -1);
					ctx.stroke();
					ctx.restore();
				}
			}
			// Draw Legend
			var legendMsr;
			if (nbeltLegend > 1 || (nbeltLegend == 1 && config.showSingleLegend)) {
				legendMsr = {
					dispLegend: true,
					xLegendPos: xLegendPos,
					yLegendPos: yLegendPos,
					nbLegendLines: nbLegendLines,
					nbLegendCols: nbLegendCols,
					reverseLegend: reverseLegend,
					legendBox: legendBox,
					widestLegend: widestLegend,
					highestLegend: highestLegend,
					legendWidth: msrLegend.legendWidth,
					legendHeight: msrLegend.legendHeight,
					legendBackgroundColorWidth: msrLegend.legendBackgroundColorWidth,
					legendBackgroundColorHeight: msrLegend.legendBackgroundColorHeight,
					legendBorderWidth: msrLegend.legendBorderWidth,
					legendBorderHeight: msrLegend.legendBorderHeight,
					legendFirstTextXPos: msrLegend.legendFirstTextXPos,
					legendFirstTextYPos: msrLegend.legendFirstTextYPos,
					legendBackgroundColorXPos: msrLegend.legendBackgroundColorXPos,
					legendBackgroundColorYPos: msrLegend.legendBackgroundColorYPos,
					legendBorderXPos: msrLegend.legendBorderXPos,
					legendBorderYPos: msrLegend.legendBorderYPos,
					elementMsr: msrLegend.elementMsr
				};
				if (config.legendPosY == 0 || config.legendPosY == 4 || config.legendPosX == 0 || config.legendPosX == 4) {
					drawLegend(legendMsr, data, config, ctx, typegraph, -1);
					legendMsr = {
						dispLegend: false
					};
				}
			} else {
				legendMsr = {
					dispLegend: false
				};
			}
		}
		clrx = leftNotUsableWidth;
		clrwidth = availableWidth;
		clry = topNotUsableHeight;
		clrheight = availableHeight;
		return {
			leftNotUsableWidth: leftNotUsableWidth,
			rightNotUsableWidth: rightNotUsableWidth,
			availableWidth: availableWidth,
			topNotUsableHeight: topNotUsableHeight,
			bottomNotUsableHeight: bottomNotUsableHeight,
			availableHeight: availableHeight,
			widestXLabel: widestXLabel,
			widestTXLabel: widestTXLabel,
			highestXLabel: highestXLabel,
			highestTXLabel: highestTXLabel,
			widestYLabel: widestYLabel,
			widestYLabel2: widestYLabel2,
			highestYLabel: highestYLabel,
			rotateLabels: rotateLabels,
			rotateTLabels: rotateTLabels,
			xLabelPos: xLabelPos,
			xTLabelPos: xTLabelPos,
			clrx: clrx,
			clry: clry,
			clrwidth: clrwidth,
			clrheight: clrheight,
			legendMsr: legendMsr
		};
	}
1301452
def configure(self, cnf={}, **kw):
        
        kw.update(cnf)
        reinit = False
        if 'orient' in kw:
            if kw['orient'] == 'vertical':
                self._style_name = self._style_name.replace('Horizontal', 'Vertical')
                if 'tickpos' not in kw:
                    self._tickpos = 'w'
            else:
                self._style_name = self._style_name.replace('Vertical', 'Horizontal')
                if 'tickpos' not in kw:
                    self._tickpos = 's'
            self.scale.configure(style=self._style_name)
            reinit = True
        if 'showvalue' in kw:
            self._showvalue = bool(kw.pop('showvalue'))
            reinit = True
        if 'tickinterval' in kw:
            self._tickinterval = kw.pop('tickinterval')
            reinit = True
        if 'tickpos' in kw:
            tickpos = kw.pop('tickpos')
            orient = kw.get('orient', str(self.cget('orient')))
            if orient == 'vertical' and tickpos not in ['w', 'e']:
                raise ValueError("For a vertical TickScale, 'tickpos' must be 'w' or 'e'.")
            elif orient == 'horizontal' and tickpos not in ['n', 's']:
                raise ValueError("For a horizontal TickScale, 'tickpos' must be 'n' or 's'.")
            elif orient in ['vertical', 'horizontal']:
                self._tickpos = tickpos
                reinit = True
        if 'labelpos' in kw:
            labelpos = kw.pop('labelpos')
            if labelpos not in ['w', 'e', 'n', 's']:
                raise ValueError("'labelpos' must be 'n', 's', 'e' or 'w'.")
            else:
                self._labelpos = labelpos
                reinit = True
        if 'resolution' in kw:
            try:
                self._resolution = float(kw.pop('resolution'))
                if self._resolution < 0:
                    raise ValueError("'resolution' must be non negative.")
            except ValueError:
                raise TypeError("'resolution' must be a float.")
        if self._tickinterval != 0 and self._resolution > self._tickinterval:
            self._tickinterval = self._resolution
            reinit = True
        if 'digits' in kw:
            digits = kw.pop('digits')
            if not isinstance(digits, int):
                raise TypeError("'digits' must be an integer.")
            elif digits < 0:
                self._digits = digits
                self._formatter = '{:g}'
                reinit = True
            else:
                self._digits = digits
                self._formatter = '{:.' + str(self._digits) + 'f}'
                interv = self._get_precision(self._tickinterval)
                resol = self._get_precision(self._resolution)
                start = kw.get('from', kw.get('from_', self._start))
                end = kw.get('to', self.scale.cget('to'))
                from_ = self._get_precision(start)
                to = self._get_precision(end)
                d = max(interv, resol, from_, to)
                if self._digits < d:
                    self._resolution = float('1e-{}'.format(self._digits))
                    self._tickinterval = round(self._tickinterval, self._digits)
                    if self._resolution > self._tickinterval:
                        self._tickinterval = self._resolution
                    kw['to'] = round(end, self._digits)
                    if 'from_' in kw:
                        del kw['from_']
                    kw['from'] = round(start, self._digits)
                reinit = True
        elif self._digits > 0:
            start = kw.get('from', kw.get('from_', self._start))
            end = kw.get('to', self.scale.cget('to'))
            from_ = self._get_precision(start)
            to = self._get_precision(end)
            interv = self._get_precision(self._tickinterval)
            resol = self._get_precision(self._resolution)
            digits = max(self._digits, interv, resol, from_, to)
            if digits != self._digits:
                self._digits = digits
                self._formatter = '{:.' + str(self._digits) + 'f}'
                reinit = True
        if 'variable' in kw:
            self._var = kw['variable']
            if not self._var:
                self._var = tk.DoubleVar(self, self.get())
                kw['variable'] = self._var
            try:
                self._var.trace_add('write', self._increment)
            except AttributeError:
                # backward compatibility
                self._var.trace('w', self._increment)

        self.scale.configure(**kw)

        if 'from_' in kw or 'from' in kw or 'to' in kw:
            self._extent = self.scale.cget('to') - self.scale.cget('from')
            self._start = self.scale.cget('from')
            reinit = True
        if 'style' in kw:
            self._style_name = kw['style']
            if not self._style_name:
                self._style_name = '%s.TScale' % (str(self.scale.cget('orient')).capitalize())
        if reinit:
            self._init()
        if 'orient' in kw:
            # needed after the reinitialization in case of orientation change
            self._apply_style()
961448
public void configure(int iterations, int burnIn, int thinInterval,
        int sampleLag) {
        ITERATIONS = iterations;
        BURN_IN = burnIn;
        THIN_INTERVAL = thinInterval;
        SAMPLE_LAG = sampleLag;
    }
651128
private void initCanvas() {
        GraphicsEnvironment ge = GraphicsEnvironment.getLocalGraphicsEnvironment();
        if (ge.isHeadless()) {
            setPreferredSize(new Dimension(1600,1200));

        }

        setLayout(new BorderLayout());
        
        canvas = new MathCanvas();
        add(canvas, BorderLayout.CENTER);

        initContextMenauAndToolBar();
        
        // set a new dismiss delay to a really big value, default is 4 sec.
        //ToolTipManager.sharedInstance().setDismissDelay(Integer.MAX_VALUE);
    }
775356
public void setParameters(Parameterization config) {
    // Clear errors after each step, so they don't consider themselves failed
    // because of earlier errors.
    logTab.setParameters(config);
    // config.clearErrors();
    inputTab.setParameters(config);
    // config.clearErrors();
    algTab.setParameters(config);
    // config.clearErrors();
    evalTab.setParameters(config);
    // config.clearErrors();
    outTab.setParameters(config);
    // config.clearErrors();
  }
281426
def _set_config(c):
    """"""
    glformat = QGLFormat()
    glformat.setRedBufferSize(c['red_size'])
    glformat.setGreenBufferSize(c['green_size'])
    glformat.setBlueBufferSize(c['blue_size'])
    glformat.setAlphaBufferSize(c['alpha_size'])
    if QT5_NEW_API:
        # Qt5 >= 5.4.0 - below options automatically enabled if nonzero.
        glformat.setSwapBehavior(glformat.DoubleBuffer if c['double_buffer']
                                 else glformat.SingleBuffer)
    else:
        # Qt4 and Qt5 < 5.4.0 - buffers must be explicitly requested.
        glformat.setAccum(False)
        glformat.setRgba(True)
        glformat.setDoubleBuffer(True if c['double_buffer'] else False)
        glformat.setDepth(True if c['depth_size'] else False)
        glformat.setStencil(True if c['stencil_size'] else False)
        glformat.setSampleBuffers(True if c['samples'] else False)
    glformat.setDepthBufferSize(c['depth_size'] if c['depth_size'] else 0)
    glformat.setStencilBufferSize(c['stencil_size'] if c['stencil_size']
                                  else 0)
    glformat.setSamples(c['samples'] if c['samples'] else 0)
    glformat.setStereo(c['stereo'])
    return glformat
962869
private void setPreferredWidth() {
    Element root = component.getDocument().getDefaultRootElement();
    int lines = root.getElementCount();
    int digits = Math.max(String.valueOf(lines).length(), minimumDisplayDigits);

    // Update sizes when number of digits in the line number changes

    if (lastDigits != digits) {
      lastDigits = digits;
      FontMetrics fontMetrics = getFontMetrics(getFont());
      int width = fontMetrics.charWidth('0') * digits;
      Insets insets = getInsets();
      int preferredWidth = insets.left + insets.right + width;

      Dimension d = getPreferredSize();
      d.setSize(preferredWidth, HEIGHT);
      setPreferredSize(d);
      setSize(d);
    }
  }
186957
def configure(self, cfg, handler, path=""):

        

        # configure simple value attributes (str, int etc.)
        for name, attr in handler.attributes():
            if cfg.get(name) is not None:
                continue
            if attr.expected_type not in [list, dict]:
                cfg[name] = self.set(handler, attr, name, path, cfg)
            elif attr.default is None and not hasattr(handler, "configure_%s" % name):
                self.action_required.append(("%s.%s: %s" % (path, name, attr.help_text)).strip("."))

        # configure attributes that have complex handlers defined
        # on the config Handler class (class methods prefixed by
        # configure_ prefix
        for name, attr in handler.attributes():
            if cfg.get(name) is not None:
                continue
            if hasattr(handler, "configure_%s" % name):
                fn = getattr(handler, "configure_%s" % name)
                fn(self, cfg, "%s.%s"% (path, name))
                if attr.expected_type in [list, dict] and not cfg.get(name):
                    try:
                        del cfg[name]
                    except KeyError:
                        pass
503166
def set_display_config(cls, config): # pragma: no cover
        
        cls.DISPLAY_CONFIG = DisplayConfig(
            show_approx_str=config.show_approx_str,
            base_config=config.base_config,
            digits_config=config.digits_config,
            strip_config=config.strip_config
        )
428372
public void layout (Graphics2D gfx, SceneObject tipFor, Rectangle boundary)
    {
        layout(gfx, ICON_PAD, EXTRA_PAD);
        bounds = new Rectangle(_size);

        // locate the most appropriate tip layout
        for (int ii = 0, ll = _layouts.size(); ii < ll; ii++) {
            LayoutReg reg = _layouts.get(ii);
            String act = tipFor.info.action == null ? "" : tipFor.info.action;
            if (act.startsWith(reg.prefix)) {
                reg.layout.layout(gfx, boundary, tipFor, this);
                break;
            }
        }
    }
399707
def setup(app):
    """"""
    sphinx_compatibility._app = app

    app.add_config_value('sphinx_gallery_conf', DEFAULT_GALLERY_CONF, 'html')
    for key in ['plot_gallery', 'abort_on_example_error']:
        app.add_config_value(key, get_default_config_value(key), 'html')

    try:
        app.add_css_file('gallery.css')
    except AttributeError:  # Sphinx < 1.8
        app.add_stylesheet('gallery.css')

    # Sphinx < 1.6 calls it `_extensions`, >= 1.6 is `extensions`.
    extensions_attr = '_extensions' if hasattr(
        app, '_extensions') else 'extensions'
    if 'sphinx.ext.autodoc' in getattr(app, extensions_attr):
        app.connect('autodoc-process-docstring', touch_empty_backreferences)

    app.connect('builder-inited', generate_gallery_rst)
    app.connect('build-finished', copy_binder_files)
    app.connect('build-finished', summarize_failing_examples)
    app.connect('build-finished', embed_code_links)
    metadata = {'parallel_read_safe': True,
                'parallel_write_safe': False,
                'version': _sg_version}
    return metadata
387472
def _set_config(c):
    """"""
    gl_attribs = [glcanvas.WX_GL_RGBA,
                  glcanvas.WX_GL_DEPTH_SIZE, c['depth_size'],
                  glcanvas.WX_GL_STENCIL_SIZE, c['stencil_size'],
                  glcanvas.WX_GL_MIN_RED, c['red_size'],
                  glcanvas.WX_GL_MIN_GREEN, c['green_size'],
                  glcanvas.WX_GL_MIN_BLUE, c['blue_size'],
                  glcanvas.WX_GL_MIN_ALPHA, c['alpha_size']]
    gl_attribs += [glcanvas.WX_GL_DOUBLEBUFFER] if c['double_buffer'] else []
    gl_attribs += [glcanvas.WX_GL_STEREO] if c['stereo'] else []
    return gl_attribs
903065
private void initGraphics() {
        // Set initial size
        if (Double.compare(gauge.getPrefWidth(), 0.0) <= 0 || Double.compare(gauge.getPrefHeight(), 0.0) <= 0 ||
            Double.compare(gauge.getWidth(), 0.0) <= 0 || Double.compare(gauge.getHeight(), 0.0) <= 0) {
            if (gauge.getPrefWidth() > 0 && gauge.getPrefHeight() > 0) {
                gauge.setPrefSize(gauge.getPrefWidth(), gauge.getPrefHeight());
            } else {
                gauge.setPrefSize(PREFERRED_WIDTH, PREFERRED_HEIGHT);
            }
        }

        backgroundInnerShadow = new InnerShadow(BlurType.TWO_PASS_BOX, Color.rgb(10, 10, 10, 0.45), 8, 0.0, 8.0, 0.0);

        sectionsAndAreasCanvas = new Canvas();
        sectionsAndAreasCtx    = sectionsAndAreasCanvas.getGraphicsContext2D();

        tickMarkCanvas = new Canvas();
        tickMarkCtx    = tickMarkCanvas.getGraphicsContext2D();

        ledCanvas = new Canvas();
        ledCtx    = ledCanvas.getGraphicsContext2D();
        Helper.enableNode(ledCanvas, gauge.isLedVisible());

        thresholdTooltip = new Tooltip("Threshold\n(" + String.format(locale, formatString, gauge.getThreshold()) + ")");
        thresholdTooltip.setTextAlignment(TextAlignment.CENTER);

        threshold = new Path();
        Helper.enableNode(threshold, gauge.isThresholdVisible());
        Tooltip.install(threshold, thresholdTooltip);

        average = new Path();
        Helper.enableNode(average, gauge.isAverageVisible());

        markerPane = new Pane();

        lcd = new Rectangle(0.3 * PREFERRED_WIDTH, 0.014 * PREFERRED_HEIGHT);
        lcd.setArcWidth(0.0125 * PREFERRED_HEIGHT);
        lcd.setArcHeight(0.0125 * PREFERRED_HEIGHT);
        lcd.relocate((PREFERRED_WIDTH - lcd.getWidth()) * 0.5, 0.44 * PREFERRED_HEIGHT);
        Helper.enableNode(lcd, gauge.isLcdVisible() && gauge.isValueVisible());

        needleRotate = new Rotate(180 - startAngle);
        needleRotate.setAngle(needleRotate.getAngle() + (gauge.getValue() - oldValue - minValue) * angleStep);
        needle              = new Path();
        needle.setFillRule(FillRule.EVEN_ODD);
        needle.getTransforms().setAll(needleRotate);
        needle.setStrokeType(StrokeType.INSIDE);
        needle.setStroke(Color.TRANSPARENT);

        buttonTooltip    = new Tooltip();
        buttonTooltip.setTextAlignment(TextAlignment.CENTER);

        knobCanvas = new Canvas();
        knobCtx    = knobCanvas.getGraphicsContext2D();
        knobCanvas.setPickOnBounds(false);
        Helper.enableNode(knobCanvas, gauge.isKnobVisible());

        dropShadow = new DropShadow();
        dropShadow.setColor(Color.rgb(0, 0, 0, 0.25));
        dropShadow.setBlurType(BlurType.TWO_PASS_BOX);
        dropShadow.setRadius(0.015 * PREFERRED_WIDTH);
        dropShadow.setOffsetY(0.015 * PREFERRED_WIDTH);

        shadowGroup = new Group(needle, knobCanvas);
        shadowGroup.setEffect(gauge.isShadowsEnabled() ? dropShadow : null);

        titleText = new Text(gauge.getTitle());
        titleText.setTextOrigin(VPos.CENTER);
        titleText.setMouseTransparent(true);
        Helper.enableNode(titleText, !gauge.getTitle().isEmpty());

        subTitleText = new Text(gauge.getSubTitle());
        subTitleText.setTextOrigin(VPos.CENTER);
        subTitleText.setMouseTransparent(true);
        Helper.enableNode(subTitleText, !gauge.getSubTitle().isEmpty());

        unitText = new Text(gauge.getUnit());
        unitText.setMouseTransparent(true);
        unitText.setTextOrigin(VPos.CENTER);
        unitText.setMouseTransparent(true);
        Helper.enableNode(unitText, !gauge.getUnit().isEmpty());

        valueText = new Text(formatNumber(gauge.getLocale(), gauge.getFormatString(), gauge.getDecimals(), gauge.getCurrentValue()));
        valueText.setMouseTransparent(true);
        valueText.setTextOrigin(VPos.CENTER);
        valueText.setMouseTransparent(true);
        Helper.enableNode(valueText, gauge.isValueVisible());

        // Set initial value
        double targetAngle = 180 - startAngle + (gauge.getCurrentValue() - minValue) * angleStep;
        targetAngle        = Helper.clamp(180 - startAngle, 180 - startAngle + angleRange, targetAngle);
        needleRotate.setAngle(targetAngle);

        rotateNeedle(gauge.getCurrentValue());

        // Add all nodes
        pane = new Pane(sectionsAndAreasCanvas,
                        tickMarkCanvas,
                        markerPane,
                        ledCanvas,
                        lcd,
                        titleText,
                        subTitleText,
                        unitText,
                        valueText,
                        shadowGroup);
        pane.setBorder(new Border(new BorderStroke(gauge.getBorderPaint(), BorderStrokeStyle.SOLID, new CornerRadii(1024), new BorderWidths(gauge.getBorderWidth()))));
        pane.setBackground(new Background(new BackgroundFill(gauge.getBackgroundPaint(), new CornerRadii(1024), Insets.EMPTY)));

        getChildren().setAll(pane);
    }
1312531
private function _set_params()
    {
        // Get values from request
        $params = \Request::route('params');
        $filepath = $this->config['abs_path'] . '/' . \Request::route('imagepath');
        
        // echo $params; exit;
        
        // If enforcing params, ensure it's a match
        if ($this->config['enforce_presets'] && !in_array($params, $this->config['presets'])) {
            abort(404);
        }
        
        $image = new Image();
        $image->configure(config('image'));
        if (function_exists('exif_read_data')) {
            $this->image = $image->make($filepath)->orientate();
        } else {
            $this->image = $image->make($filepath);
        }
        
        // The parameters are separated by hyphens
        $raw_params = explode('-', $params);
        
        // Update param values from passed values
        foreach ($raw_params as $raw_param) {
            $name = $raw_param[0];
            $value = substr($raw_param, 1, strlen($raw_param) - 1);
            
            if ($name == 'c') {
                $this->url_params[$name] = TRUE;
                
                // When croping, we must have a width and height to pass to imagecreatetruecolor method
                // Make width the height or vice versa if either is not passed
                if (empty($this->url_params['w'])) {
                    $this->url_params['w'] = $this->url_params['h'];
                }
                if (empty($this->url_params['h'])) {
                    $this->url_params['h'] = $this->url_params['w'];
                }
            } elseif (key_exists($name, $this->url_params)) {
                // Remaining expected params (w, h, q)
                $this->url_params[$name] = $value;
            } else {
                // Watermarks or invalid params
                $this->url_params[$raw_param] = $raw_param;
            }
        }
        
        // Do not scale up images
        if (! $this->config['scale_up']) {
            if ($this->url_params['w'] > $this->image->width()) {
                $this->url_params['w'] = $this->image->width();
            }
            if ($this->url_params['h'] > $this->image->height()) {
                $this->url_params['h'] = $this->image->height();
            }
        }
        
        // Must have at least a width or height
        if (empty($this->url_params['w']) and empty($this->url_params['h'])) {
            throw new HTTP_Exception_404('The requested URL :uri was not found on this server.', array(
                ':uri' => Request::$current->uri()
            ));
        }
        
        // Set the url filepath
        $this->source_file = $filepath;
    }