Use Chart.js in a Tab Page

Use Chart.js in a Tab Page

by Rodney Wolford -
Number of replies: 14

I am using Moodle 3.2.4 (build 20170714). I would like to use chart.js to add interactive charts for trainee visualization of course concepts into the html content areas of my tab displays. I can see that chart.js has been added to Moodle 3.2, but I have not been able to figure out how to access it and use it.

I can see its use in reports, for example, as shown in the code below from reports/statistics display.

<iframe class="chartjs-hidden-iframe" tabindex="-1" style="width: 100%; display: block; border: 0px none; height: 0px; margin: 0px; position: absolute; left: 0px; right: 0px; top: 0px; bottom: 0px;"></iframe>

<canvas style="display: block; width: 1504px; height: 752px;" width="1504" height="752" id="yui_3_17_2_1_1500392820449_160"></canvas>

I have also found the chartjs.min.js and other javascript in lib/amd/build. But I have not been able to figure out how to put these items together on an html page in a Tab to display information to trainees.

Can anyone provide me with a sample of how this is done? In case it matters, the theme I am using is latest version of Essential.

Rod Wolford

Average of ratings: -
In reply to Rodney Wolford

Re: Use Chart.js in a Tab Page

by Howard Miller -
Picture of Core developers Picture of Documentation writers Picture of Particularly helpful Moodlers Picture of Peer reviewers Picture of Plugin developers

It's not a "user" thing. The API was added for developers to add charting facilities...

see https://docs.moodle.org/dev/Charts_API

In reply to Howard Miller

Re: Use Chart.js in a Tab Page

by Rodney Wolford -

HI Howard,

I will review the document. Thank you for directing me to it.

But my question still remains: as a "user" is it possible for me, through whatever means, to access and use these chartjs.js scripts on my pages? I assume the answer may be "yes" and I don't see any harm in offering up a few hints as to how I might do it, if it is possible. Or is it you are saying only can be implemented through PHP?

Thanks again,

Rod Wolford


In reply to Rodney Wolford

Re: Use Chart.js in a Tab Page

by Howard Miller -
Picture of Core developers Picture of Documentation writers Picture of Particularly helpful Moodlers Picture of Peer reviewers Picture of Plugin developers

It's not a "user" thing.... that would be "no". Some general purpose chart activity or similar would be needed. 

In reply to Howard Miller

Re: Use Chart.js in a Tab Page

by Rodney Wolford -

Hello Howard,

Based on your comment, I have looked elsewhere. I have been able to begin doing what I wanted by loading RGraph.js onto my site (at the root) and copying the full compliment of Chart.js files with path names into my Moodle site's "Additional HTML" area found under "Appearance" in the Administrator's area. It allows me to create .svg files and provides for incorporating the data for display into the script area for the html on a tab.

Here is code I used for my test followed by an image of the chart it generated. Just make a container, select a .js for the type of graph you want to make, put in data, and define variables. So far I think I will also be able to make this graph based on "trainee input" so they can solve problems and visualize the shape of the solutions they generate.

<div id="chart-container" style="width: 600px; height: 250px; display: inline-block"></div>
<script>
    new RGraph.SVG.Line({
        id: 'chart-container',
        data: [5,8,6,3,4,1,9,8,2,3,5,6,7,8,9,4,5,6,3,2,5,4,8,6,4,5,3,1,6,4,5],
        options: {
            backgroundGridVlinesCount: 11,
            hmargin: 0,
            textColor: 'black',
            textSize: 14,
            textFont: 'Verdana',
            filled: true,
            filledColors: ['rgba(25,51,74,0.75)'],
            colors: ['#5AF'],
            gutterLeft: 65,
            gutterRight: 40,
            gutterBottom: 50,
            gutterTop: 20,
            xaxis: false,
            yaxis: false,
            yaxisUnitsPost: 'm',
            yaxisUnitsPre: '$',
            tickmarksStyle: 'circle',
            tickmarksFill: 'black',
            tickmarksLinewidth: 1,
            tickmarksSize: 2,
            linewidth: 2,
            spline: true,
            xaxisLabels: ['Kev','John','Fred','July','Fred','Olga','Ben','Boris','Lenny','Pete','Lewis']
        }
    }).trace();
</script>

Too bad that I have to go outside Chart.js to do this. I'd rather be working inside the moodle environment. But maybe Chart.js can work like this in the future. I assume it is the <canvas> vs. <svg> formats?

Regards,

Rod Wolford

In reply to Rodney Wolford

Re: Use Chart.js in a Tab Page

by Howard Miller -
Picture of Core developers Picture of Documentation writers Picture of Particularly helpful Moodlers Picture of Peer reviewers Picture of Plugin developers

This is very speculative as I haven't had a proper look at chart.js yet, but it could be possible to build a filter that allows chart data to be embedded in a page in some fashion. 

That would be fun smile

In reply to Howard Miller

Re: Use Chart.js in a Tab Page

by Rodney Wolford -

Howard,

I'm glad you see some potential. It only took me a couple of hours to figure out how to add RGraph to my site and use it. So I am sure someone with more experience would find it a piece of cake.

BTW I did notice your message referenced chart.js for the filter, whereas I used RGraph.js. So I guess you are thinking that a similar outcome is possible with Chart.js? I probably won't look further, because time doesn't permit and RGraph is solving my problem. But I'd be curious.

Regards,

Rod

p.s. I have already been able to implement "tool tips" in RGraph.js which permits very nice click-on text displays with animated display of chart information.

In reply to Rodney Wolford

Re: Use Chart.js in a Tab Page

by AL Rachels -
Picture of Core developers Picture of Particularly helpful Moodlers Picture of Plugin developers Picture of Testers

Hi Rodney,

I saw your original post just yesterday and today with just a few lines of extra code to get the data and to set the chart title, xy axis labels, series, etc., I now have nice dynamic bar charts on the two grade pages of a plugin (MooTyper) I maintain. Hovering the mouse over a bar automatically shows details for that bar.

It really surprised me how easy it was to add to an output page that was already part of the plugin to begin with. Like Howard, I think it would be pretty easy to build a filter for adding chart data for embedding, especially using a Generico filter or a PoodLL widget.

In reply to AL Rachels

Re: Use Chart.js in a Tab Page

by Rodney Wolford -

Hi AL.

Glad the post helped you. As you can see, I am doing this with RGraph.js, not with Chart.js. I have been unable to figure out how to make it work with Chart.js (I am barely capable of imitation, yet alone design). Perhaps you could share what code you used to make it possible?

Regards,

Rod Wolford

In reply to Rodney Wolford

Re: Use Chart.js in a Tab Page

by AL Rachels -
Picture of Core developers Picture of Particularly helpful Moodlers Picture of Plugin developers Picture of Testers
In the code I use four arrays  to get the data I want to use for the chart. The program is looping through the database to get all the results and put the data into the appropriate array:


            $labels[] = $fcol;  // This gets the exercise number.
            $serieshitsperminute[] = format_float($gr->hitsperminute); // Get the hits per minute value.
            $seriesprecision[] = format_float($gr->precisionfield);  // Get the precision percentage value.
            $serieswpm[] = $gr->wpm; // Get the corrected words per minute rate.

Then it is just a matter of passing the data to the chart api:



echo $htmlout;    // Output the normal grade table of results.
if ($grds != false) {  // If there are NOT any grades, DON'T draw the chart.
    // Create the info the api needs passed to it for each series I want to chart.
    $serie1 = new core\chart_series(get_string('hitsperminute', 'mootyper'), $serieshitsperminute);
    $serie2 = new core\chart_series(get_string('precision', 'mootyper'), $seriesprecision);
    $serie3 = new core\chart_series(get_string('wpm', 'mootyper'), $serieswpm);

    $chart = new core\chart_bar();  // Tell the api I want a bar chart.
    $chart->set_horizontal(true); // Calling set_horizontal() passing true as parameter will display horizontal bar charts.
    $chart->set_title(get_string('charttitlemyowngrades', 'mootyper')); // Tell the api what I want for a the chart title.
    $chart->add_series($serie1);  // Pass the hits per minute data to the api.
    $chart->add_series($serie2);  // Pass the precision data to the api.
    $chart->add_series($serie3);  // Pass the words per minute data to the api.
    $chart->set_labels($labels);  // Pass the exercise number data to the api.
    $chart->get_xaxis(0, true)->set_label("Range");  // Pass a label to add to the x-axis.
    $chart->get_yaxis(0, true)->set_label(get_string('fexercise', 'mootyper')); // Pass the label to add to the y-axis.
    echo $OUTPUT->render($chart); // Draw the chart on the output page.
}
echo $OUTPUT->footer();   // This line prints the normal Moodle footer
This is the result showing my normal grade table for a single user.  The link at the bottom, Show chart data, is optional. If I select one of my headings to reorder the grade table, the chart is automatically redrawn to reflect the new view. :

Using essentially the same code a teacher gets a chart depending on what they select which will also include student names.

In reply to AL Rachels

Re: Use Chart.js in a Tab Page

by Rodney Wolford -

Hello AL,

Thanks for the view of your code, but what you are doing is beyond my ability. I believe I recognize this as php. If so, I assume it is running at the application level.

What I have been trying to achieve is running at the html page level inside of the moodle text editor. For me that means using html and javascript in an html page in a student's lesson, as my example shows. This is more of an adhoc use to achieve an instructional aim, with different table types implemented in different lessons based on lesson content, whereas what you are achieving is a consistent and regulated display of information written to the database based on student activities.

In your work I do see a path call to core\ chart and maybe that gives me a hint as to how access chart.js. I have been trying to call chart.js from the /amd folder without success. That is why I created a folder for RGraph.js, which resides outside my moodle site at the root of my system, to which I have been making calls inside my javascript. Maybe if I look inside the moodle core area I will see paths that will give me access to the chart.js. I'd much rather be using chart.js, as it is part of moodle, whereas RGraph.js is not.

I like what you have done, and I think you clearly show how the interactive charts are accessible beyond the built in moodle functions.

Regards,

Rod Wolford


In reply to Rodney Wolford

Re: Use Chart.js in a Tab Page

by AL Rachels -
Picture of Core developers Picture of Particularly helpful Moodlers Picture of Plugin developers Picture of Testers

Hi Rod,

"I believe I recognize this as php. If so, I assume it is running at the application level." - Yes this is php and part of the code to generate a page showing grades of an individual user (first picture) and all grades of all users (second picture) of a MooTyper activity.

"Maybe if I look inside the moodle core area I will see paths that will give me access to the chart.js." - No need really to know the paths. You just provide the information in a variable to each one of the lines you want to use that start with $chart-> and and then use the echo $OUTPUT->render($chart) and Moodle will automatically do the rest.

I am reasonably sure that both chart.js and RGraph.js could both be used to create a Generico filter bundle, or a PoodLL3 widget, that would let you create a chart anywhere you can open a Moodle editor.

Using the data from your example, which for Lewis seems to be missing two items for which I substituted 0, here is the code for a bar chart and it's resulting output.

The php code:

And the result:

With just one to three additional lines of code, it would be easy to change the results to horizontal bars, stacked bars, lines, smooth lines, pie, or doughnut charts.

Average of ratings: Useful (1)
In reply to Rodney Wolford

Re: Use Chart.js in a Tab Page

by AL Rachels -
Picture of Core developers Picture of Particularly helpful Moodlers Picture of Plugin developers Picture of Testers

Well, I should have looked sooner. Justin Hunt actually includes a simple linechart bundle with the Generico filter that uses //cdnjs.cloudflare.com/ajax/libs/Chart.js/1.0.2/Chart.min.js. He also includes a piechart bundle.

Due to my personal vision problems, I don't care for the colors but using Rod's data, here is it's output:

I am reasonably sure that it would be possible to easily change the colors as well as add some other settings. Right now a user can only set the width, height, datalabel, labels, and data.

Average of ratings: Useful (1)
In reply to AL Rachels

Re: Use Chart.js in a Tab Page

by Rodney Wolford -

AL,

Wow! You have taken my understanding of this to a new level. I appreciate you taking the time to show and explain. I will have to dip back into this with what you have shown me. Once again, thanks very much for taking the time to explain.

BTW, I agree with you on color selection problems. They occur all too often. I always try to check choices against U.S. 508 compliance criteria to avoid hard to read color and type combinations. "If you can't perceive it, you can't learn it."

Rod Wolford

In reply to Rodney Wolford

Re: Use Chart.js in a Tab Page

by Rodolfo Gallegos -

For the js changes that you need to make for practical tests use the Developer mode (see documentation https://docs.moodle.org/dev/Javascript_Modules). They should be done in the file moodle/lib/amd/src/chartjs-lazy.js (not without first including in the config.php the line $CFG-> cachejs = false; to avoid the cache of js). It worked excellently for me, the changes are immediately visible when saving. 

Regards