Custom Grid Drawing in Charting for JavaScript

In this blog post we will look in short at the steps to build this JavaScript area chart with custom grid:

The line chart uses DateTimeSeries for the data and a standard GridType for the major grid lines. The auxiliary grid lines among them are made with custom drawing: we will discuss in details the code for that.

The sample uses MindFusion Charting library for JavaScript, which also supports TypeScript.

You can see the sample online at https://mindfusion.eu/samples/javascript/chart/CustomGrid/DateTimeSeries.html

I. General Setup

The chart requires several JavaScript files to be included. These are:

<script src="../Scripts/drawing.js" type="text/javascript"></script>
<script src="../Scripts/controls.js" type="text/javascript"></script>
<script src="../Scripts/common.js" type="text/javascript"></script>
<script src="../Scripts/common-collections.js" type="text/javascript"></script>
<script src="../Scripts/charting.js" type="text/javascript"></script>

We add them at the end of the web page, where we want to render the chart, straight before the closing BODY tag. The chart itsel needs a DIV element to render itself onto. It is important hat the DIV has an id. We add one to the web page:

<div id="content" style="top: 60px; bottom: 24px; overflow-y: scroll;">
	<div style="position: absolute; left: 0px; top: 0px; bottom: 0px; right: 0px">
		<canvas id="chart" style="width: 100%; height: 100%; display: block;">
		</canvas>
	</div>
</div>

II. Chart Initialization

We create the Chart as an instance of the AreaChart class. First, we must get the HTML element that represents it and then we get its size. This element is used in the chart constructor – we cannot create any type of Chart without it:

var chartEl = document.getElementById('chart');
chartEl.width = chartEl.offsetParent.clientWidth;
chartEl.height = chartEl.offsetParent.clientHeight;
var chart = new Controls.AreaChart(chartEl);

The data for the chart is a Series instance. The Series interface is implemented by various classes that allow you to choose the best one regarding your data type and project goals. In our case we use JavaScript Date objects as data for the X-axis, which is why we’ve chosen the DateTimeSeries to represent the data for our chart.

// create sample data
var data = new Collections.ObservableCollection();

var years = new Collections.List();
var dt = new Date(new Date().getFullYear() - 10, 11, 31);
for (; ; )
{
	if (dt.getFullYear() > new Date().getFullYear())
		break;
	years.add(new Date(dt.setFullYear(dt.getFullYear() + 1)));
}

var income = new Collections.List([52, 63.2, 35.6, 47.8, 39, 50, 29, 79, 101, 120, 112]);

var series = new Charting.DateTimeSeries(
	years, income, years.item(0), years.item(years.count() - 1));

The DateTimeSeries instance has a variety of properties, including minValue and maxValue, which we will set. They set the values that correspond to the MinDate and MaxDate in the series. We also use the dateTimeFormat property and customDateTimeFormat to further specify how our DateTimeSeries shall look.

Each chart Axis has properties that specify its scale: minValue, maxVaue and interval Axes can have a title The labels at the X-axis can be hidden with the showXCoordinates property.

chart.showXCoordinates = false;

chart.xAxis.title = "";
chart.xAxis.minValue = 0;
chart.xAxis.maxValue = 1;
chart.xAxis.interval = 0.1;
chart.yAxis.minValue = 0;
chart.yAxis.maxValue = 130;
chart.yAxis.interval = 10;

III. The Grid

The default grid of the chart is set with the gridType property. The types of grid are members of the GridType enumeration. We customize the grid with the gridLineColor and the gridColor1 and gridColor2 properties for the grid stripes. The default grid draws lines and stripes between the scale divisions of the axes. We want to customize it to draw 4 more lines between the default lines for each interval. This functionality is not supported out of the box and we need to use custom drawing for that.

The method that we need to overwrite is called drawGrid. There we get the drawing context, which we can use to perform drawing of graphic primitives. Because this is method that draws the grid, we need to call the default grid drawing code, if we want to see the default grid drawn next to our custom grid drawing code. We do it this way:

let originalDrawGrid = Charting.Plot2D.prototype.drawGrid;

Charting.Plot2D.prototype.drawGrid = function(context) 
{

     // draw the default grid
     originalDrawGrid.call(this, context);

}

Now we need to get the two axis: X and Y, and use their scale coordinates to calculate the additional points, which we will use for grid drawing.

let xAxis = this.xAxis == null ? context.xAxis : this.xAxis;
let yAxis = this.yAxis == null ? context.yAxis : this.yAxis;

Then, in a cycle, we draw 5 additional lines for each interval, as long as we haven’t reached the last coordinate of the axis:

let gridPen = new Drawing.Pen("#e8e8e8");

	let prevY = null;
	let steps = 5;
	yAxis.enumerateIntervals(this.pinGrid, (y, yi) => {
		var pixelY = yAxis.mapValueToPixelY(y, this.actualHeight);

		if (prevY != null) {
			var dy = (prevY - pixelY) / steps;
			let yy = prevY + dy;
			for (var i = 0; i < steps - 1; i++, yy += dy)
				context.graphics.drawLine(gridPen, 0, yy, this.actualWidth, yy);
		}

		prevY = pixelY;
	}, true);

The mapValueToPixelY method is worth noting, because it is a useful public method, which converts a numeric value on the axis to a physical coordinate. The chart length can be taken from the actualHeight and actualWidth properties.

With that our custom drawing method is ready. There is one method we need to call in order to see any type of chart rendered – the draw method.

chart.draw();

You can download the source code for this chart, together will all libraries used from this link:

Area Chart with Custom Grid in JavaScript: Download the Sample

Technical support is available through MindFusion discussion board at https://mindfusion.eu/Forum/YaBB.pl?board=jschart_disc.

About Charting for JavaScript: MindFusion library for interactive charts and gauges. It supports all common chart types including 3D bar charts. Charts can have a grid, a legend, unlimited number of axes and series. Scroll, zoom and pan are supported out of the box. You can easily create your own chart series by implementing the Series interface.
The gauges library is part of Charting for JavaScript. It supports oval and linear gauge with several types of labels and ticks. Various samples show you how the implement the gauges to create and customize all popular gauge types: car dashboard, clock, thermometer, compass etc. Learn more about Charting and Gauges for JavaScript at https://mindfusion.eu/javascript-chart.html.