Thursday, March 29, 2012

ZedGraph in MVC3

When I started a new web project for a client I needed some complex charts with loads of data. I had used jQPlot for client side charts, but in this project I simply had too many data.
ZedGraph is a nice free charting tool for WinForms which I used in previous desktop applications. Knowing its capabilities it would fit nice in this web project.
Below an example is shown how to use a zedgraph chart in MVC3.

First get the reference for ZedGraph from NuGet

Then create a new Controller, named ChartsController and create a new Action TestChart like with the code below.

public ActionResult TestChart()
    // create an instance of the GraphPane directly
    // don't use the zedgraph control, this isn't WinForms
    var zedGraphPane = new GraphPane();

    // Set the Titles and types
    zedGraphPane.Title.Text = "ZedGraph in MVC 3";
    zedGraphPane.XAxis.Title.Text = "Time";
    zedGraphPane.XAxis.Type = AxisType.Date;
    zedGraphPane.YAxis.Title.Text = "mm";

    // create pointseries
    PointPairList pointserie1 = new PointPairList();
    PointPairList pointserie2 = new PointPairList();

    // fill pointseries with data
    for (int i = 0; i < 200; i++)
        pointserie1.Add((double)new XDate(DateTime.Now.AddMinutes(i)), 
                1.5 + Math.Sin( (double)i * 0.2));
        pointserie2.Add((double)new XDate(DateTime.Now.AddMinutes(i)), 
            3.0 * ( 1.5 + Math.Sin( (double)i * 0.2 )));

    // link the points to the lineserie
    LineItem curve1 = zedGraphPane.AddCurve("Line 1",
            pointserie1, Color.Red, SymbolType.None);
    LineItem curve2 = zedGraphPane.AddCurve("Line 2",
            pointserie2, Color.Blue, SymbolType.None);

    // force an axischange to plot all data and recalculate all axis
    // this is normally done by the control, but this is not possible in mvc3
    Bitmap bm = new Bitmap(1, 1);
    using (Graphics g = Graphics.FromImage(bm))
    // create a stream to store a PNG-format image
    var outStream = new MemoryStream();
    // ouput graph to stream
    zedGraphPane.GetImage(640, 480, 96, true)
         .Save(outStream, System.Drawing.Imaging.ImageFormat.Png);
    // set streamposition to 0
    outStream.Position = 0;
    // return stream as file result
    return new FileStreamResult(outStream, "image/png");


The result of the chart