/Grapher.js

A wrapper around D3.js

Primary LanguageJavaScript

Grapher - plotting library

Grapher is a minimal wrapper around D3.js to do line plots, bar plots and sparklines.

Table of Contents

Installation

<script src="./d3.js"></script>
<script src="./grapher.js"></script>

Example

<body>

        <h2>My Graph</h2>
        <button onclick="switchBarLine()">Switch bar / lines</button>
        <div id="myPlot"></div>
        
        <script src="https://cdnjs.cloudflare.com/ajax/libs/d3/5.15.0/d3.min.js" integrity="sha256-m0QmIsBXcOMiETRmpT3qg2IQ/i0qazJA2miCHzOmS1Y=" crossorigin="anonymous"></script>
        <script src="./grapher.js"></script>
        <script>
         data = [{"value":3,"Country/Region":"France","date":"2020-01-21T23:00:00.000Z"},
                 {"value":1,"Country/Region":"France","date":"2020-01-22T23:00:00.000Z"},
                 {"value":4,"Country/Region":"France","date":"2020-01-23T23:00:00.000Z"},
                 {"value":7,"Country/Region":"France","date":"2020-01-24T23:00:00.000Z"},
                 {"value":-3,"Country/Region":"Italy","date":"2020-01-21T23:00:00.000Z"},
                 {"value":3,"Country/Region":"Italy","date":"2020-01-22T23:00:00.000Z"},
                 {"value":4,"Country/Region":"Italy","date":"2020-01-23T23:00:00.000Z"},
                 {"value":10,"Country/Region":"Italy","date":"2020-01-24T23:00:00.000Z"}]

         let options = {
             "data": data,
             "x": {
                 "name":"date",
                 "scale": "scaleTime",
                 "tickFormat": d3.timeFormat("%d/%m/%y"),
                 "parse": (d) => new Date(d)
             },
             "y": {
                 "name": "value",
                 "scale": "scaleLinear",
                 "tickFormat": d3.format('.3s')
             },
             "category": "Country/Region",
             "type": "lines",
             "style": {
                 "grid": false
             }
         }
         let myGraph = new Grapher("myPlot", options);
         myGraph.draw();

         function switchBarLine() {
             if (myGraph.options.type == "bar") {
                 myGraph.draw({"type":"lines"});
             } else {
                 myGraph.draw({"type":"bar"})
             }
         }
        </script>
    </body>

Development

Build the package

npm run build

Create documentation

npm run doc

Documentation

Table of Contents

findTimeFormat

Return the timeformat in d3.timeParse function

Parameters

  • str string string containing d3.timeParse(xxx)

Returns string time format argument of d3.timeParse function

unique

Return unique values of an array (including if there are dates)

Parameters

  • array Array array
  • sorting boolean whether to sort the array (optional, default true)
  • _sort function sorting function (optional, default undefined)

Examples

let uniqueArray = unique([1, 1, 2, 3 ])
uniqueArray 
> [1, 2, 3]

Returns Array of unique values of 'arr'

getOptimalPrecision

Get optimal decimal precision for number formatting

Parameters

  • maxN number maximum number in the data

Returns string optimal format for d3.format

updateDict

Update a nested dictionary (stored as an Object)

Parameters

  • dict Object Object to update with values in newDict
  • newDict Object Object containing key:values to update dict with

getDimensionText

Retrieve the width and height of some text based on its font

Parameters

  • text string text to be measured
  • fontSize string fontSize of the text

Returns Object Object with width and height of the text as if it was on the DOM

to_csv

Transform a JSON object into a csv

Parameters

  • j Array<Object> Array of objects, each object should has the same number of keys (and each key is going to be a column). Each element of the array is going to be a line.
  • header Boolean If true, first line of the csv fine will be a header composed of the first object keys (optional, default true)

Returns String return a csv file as a string

splitString

Split a string in substrings of length of approx. n characters and splitting on space only. The function will split the string in substring of minimum length 'n' on spaces inside the string.

Parameters

  • s string string to be split
  • n number length of bits to split string 's'
  • sep string separator to be used to for splitting the string. The character should not be inside the string. (optional, default "|")

Returns Array array of substrings

wideToLong

Transform a 'wide' array of Dict to 'long' array, pivoting on some 'pivot' columns (keys). The long format is a {id, key, value}, where id is one or multiple 'pivot' columns, 'key' are the non pivot columns of the original array and the value are the value of the corresponding keys. A category value can also be passed as a new 'column'. The long format becomes {id, key, value, category}. A mapping function can also be passed to be applied to each long element (for instance to parse a date)

Parameters

  • wideData Array data to pivot
  • pivotColumns Array list of keys on which to pivot from wide to long
  • keyName string name of the key for variable name in the long format. (optional, default "field_id")
  • valueName string name of the key for value in the long format (optional, default "field_value")
  • category string? optional category key to be added in the long data (optional, default "undefined")
  • mapLongElement function (Dict) optional function to be applied on each long element (optional, default undefined)

Examples

wideArray = [{'date':'2020-07-19','temperature':32,'pressure':1016},
             {'date':'2020-07-20','temperature':25,'pressure':1020}];
longArray = wideToLong(wideArray, ['date']);
longArray = [{'date':'2020-07-19', 'field_id':'temperature','field_value':32},
             {'date':'2020-07-19', 'field_id':'pressure','field_value':1016},
             {'date':'2020-07-20', 'field_id':'temperature','field_value':25},
             {'date':'2020-07-20', 'field_id':'pressure','field_value':1020}]

longToWide

Transform a 'long' array of Dict to 'wide' array, pivoting on some 'index' columns (keys).

Parameters

  • longData Array data to pivot
  • index Array column(s) to pivot on
  • column (optional, default 'field_id')
  • value (optional, default 'field_value')
  • keyName string name of the key for variable name in the long format. (optional, default "field_id")
  • valueName string name of the key for value in the long format (optional, default "field_value")
  • mapLongElement function (Dict) optional function to be applied on each long element

Examples

longArray = [{'date':'2020-07-19', 'field_id':'temperature','field_value':32},
             {'date':'2020-07-19', 'field_id':'pressure','field_value':1016},
             {'date':'2020-07-20', 'field_id':'temperature','field_value':25},
             {'date':'2020-07-20', 'field_id':'pressure','field_value':1020}] 
longToWide(longArray, 'date', 'field_id', 'field_value');
wideArray = [{'date':'2020-07-19','temperature':32,'pressure':1016},
             {'date':'2020-07-20','temperature':25,'pressure':1020}];

barycenterColor

Compute the barycenter between two colors. Returned color will be startColor _ weight + endColor _ (1 - weight)

Parameters

  • startColor string starting color in rgb / hsl format
  • endColor string ending color in rgb / hsl format
  • weight number weight of the first color

Returns string the barycenter color

getBackgroundColor

Return the background color of an element, if transparent returns the background color of the parent element. If no parent, then the defaultColor is returned.

Parameters

  • el string DOM element to retrieve bacground color from
  • defaultColor string color to be returned if no background color is found. (optional, default "rgb(255, 255, 255)")

groupBy

This function mimics Python pandas function group by.

Parameters

  • array Array the array to group by
  • key string key to group by with
  • colSum Array array of columns to agg by sum (optional, default [])
  • colCount Array array of columns to agg by count (optional, default [])
  • colFirst Array array of columns to keep first (optional, default [])

GrapherBase

Base class for Grapher linking the chart to the DOM element and creating the svg

Parameters

  • id string id of the DOM element
  • type string Chart type
  • width number width of the DOM element (if not already setup in HTML or CSS) (optional, default null)
  • height number height of the DOM element (if not already setup in HTML or CSS) (optional, default null)

wipe

Wipe the graph elements created by draw without removing the core elements so that the graph can be drawn again with .draw()

downloadData

Download the data associated with the Grapher element

Chart

The Chart object represents the graph.

You create a Chart by specifying a container (a DOM element) that will contain the graph, and other options.

Parameters

  • id string of the DOM element
  • options Object Set of options for the graph.
    • options.data Array<Object> Array of JSON containing the data (optional, default [])
    • options.x Object Set of options for the x axis
      • options.x.name string Name of the x-axis variable in options.data (optional, default x)
      • options.x.scale string d3-scale, see d3-scale on Github (optional, default "scaleLinear")
      • options.x.parse (function | null) Function to parse the data (useful if x-axis is a date) (optional, default null)
      • options.x.tickFormat (function | null) Function to format the variable when displayed as tick or in tooltip (optional, default null)
      • options.x.label (string | null) Label for x-axis (optional, default null)
      • options.x.domain (Array<number> | null) Hardcode the x-axis bound. Default is to use min and max of x values in options.data (optional, default null)
      • options.x.nice Boolean Extends the domain so that it starts and ends on nice round values (applying d3.nice()), for further reference see d3-scale on Github (optional, default true)
      • options.x.padding (number | null)? Padding to be used between bars when x.scale is scaleBand.
      • options.x.values (Array<string> | null)? List of values of x axis. Derived from the data if not provided.
    • options.y Object Set of options for the y axis
      • options.y.name string name of the y-axis variable in options.data (optional, default x)
      • options.y.scale string d3-scale, see d3-scale on Github (optional, default "scaleLinear")
      • options.y.parse (function | null) function to parse the data (useful if y-axis is a date) (optional, default null)
      • options.y.tickFormat (function | null) function to format the variable when displayed as tick or in tooltip (optional, default null)
      • options.y.label (string | null) label for y-axis (optional, default null)
      • options.y.domain (Array<number> | null) Hardcode the y-axis bound. Default is to use min and max of y values in options.data (optional, default null)
      • options.y.nice Boolean Extends the domain so that it starts and ends on nice round values (applying d3.nice()), for further reference see d3-scale on Github (optional, default true)
    • options.category Object set of options for category
      • options.category.name (string | null) name of the category variable in options.data (optional, default null)
      • options.category.parse function function to parse (or format) the category variable when displayed in tooltip (optional, default (d=>d))
    • options.categories (Array<string> | Boolean) Hardcode the list of elements of the 'category' variable to select only data's elements belonging to this list. When no list is specified, the list of elements is derived from the data and all 'category' values found in the data are considered. (optional, default false)
    • options.type string type of the graph. Possible types are "line", "bar", "stacked-bar", "stacked-area", "dotted-line", "dot", "sparkline" (optional, default "line")
    • options.style Object list of options for styling the elements of the graph
      • options.style.colors Array<string> List of colors for the lines, bars, dots (not applicable for sparkline). Default is ["#1abb9b","#3497da","#9a59b5","#f0c30f","#e57e22","#e64c3c","#7f8b8c","#CC6666", "#9999CC", "#66CC99"]
      • options.style.barWidth number Share of the x axis width that should be filled with bars. Setting to 0.8, lets 20% in space between bars. (optional, default 0.8)
      • options.style.strokeWidth number stroke-width of the line. Default is 3px (optional, default 3)
      • options.style.dotSize number dot-size of the dots. Default is 4px (optional, default 4)
      • options.style.tooltipColor string Text color in the tooltip (optional, default "#181818")
      • options.style.tooltipBackgroundColor string Background color of the tooltip (optional, default "#ffffff")
      • options.style.tooltipOpacity string Opacity of the tooltip. Default is 0.8 (80%) (optional, default "0.8")
      • options.style.tooltipLineColor string Color of the vertical line color (optional, default "#000000")
      • options.style.beautifyClosestLine (string | function) Beautify the closest line to current mouse cursor (only works for line or dotted-lines). Possible options are either "widen" (increase the stroke-width by 1), "color" (color the closest line, grayed the others) or you can pass a function that will be applied on every lines and takes four parameters: the element itself, whether the line is the closest, the path and the category. (optional, default "widen")
    • options.grid Object Options for the grid
      • options.grid.x Object Options for grid on the x-axis
        • options.grid.x.show Boolean if true, grid will be added (same frequency as ticks) (optional, default false)
        • options.grid.x.lines Array<{x: string, label: string, position: string, y: string, textAnchor: string, class: string}> Array for vertical lines. For each line, you should at least specify the position on the x-axis (same format as x axis). You can add a label for which you can specify its position by choosing 'position' value among 'start', 'middle', 'end'. The label can also be more precisely positionned by specifying a 'y' and textAnchor value among 'start', 'middle', 'end'. You can also add a class with 'class'. (optional, default [])
      • options.grid.y Object Options for grid on the y-axis
        • options.grid.y.show Boolean if true, grid will be added (same frequency as ticks) (optional, default true)
        • options.grid.y.lines Array<{y: string, label: string, position: string, x: string, textAnchor: string, class: string}> Array for horizontal lines. For each line, you should at least specify the position on the y-axis (same format as y axis). You can add a label for which you can specify its position by choosing 'position' value among 'start', 'middle', 'end'. The label can also be more precisely positionned by specifying a 'x' and textAnchor value among 'start', 'middle', 'end'. You can also add a class with 'class'. (optional, default [])
    • options.legend Object Options for the legend
      • options.legend.show Boolean show legend. If false, legend will not be displayed. (optional, default true)
      • options.legend.x number legend's x position in the svg (optional, default 15)
      • options.legend.y number legend's y position in the svg. Default value equals the margin-top of the g element inside the svg.
      • options.legend.interstice number space in px between the legend items (optional, default 25)
      • options.legend.backgroundColor string legend's background color (optional, default "#ffffff")
      • options.legend.opacity string opacity of the legend (optional, default "0.9")
    • options.download Object options for downloading data associated with the graph
    • options.filename string filename for the csv linked to the data (optional, default "data_<elementId>_<date>.csv")
    • options.sparkline Object options for the sparkline object
      • options.sparkline.range (Array<number> | null) range for the background's band displayed in the sparkline. If null, not the band is not displayed. (optional, default null)
      • options.sparkline.textLastPoint Boolean display the last point's value as adjacent text. (optional, default true)
      • options.sparkline.strokeWidth number stroke's width of the sparkline (optional, default 1)
      • options.sparkline.lineColor string line's color of the sparkline (optional, default "#000000")
      • options.sparkline.circleColor string circle's color for the last point of the sparkline (optional, default "#f00")
      • options.sparkline.textColor string text's color of the last point value displayed next to the sparkline (optional, default "#f00")
      • options.sparkline.textFontSize string text's font size (optional, default "85%")
      • options.sparkline.textFontWeight string text's font weight (optional, default "600")
      • options.sparkline.rangeFillColor string range's band fill color (optional, default "#ccc")
      • options.sparkline.rangeFillColor string range's band fill color (optional, default "#ccc")
    • options.advanced Object Advanced options
      • options.advanced.additionalColumnsInData Array<string> Grapher will only keep x, y and category when parsing the data. Passing columns names here will preserve them in the data. (optional, default [])
  • width number width of the DOM element (if not already setup in HTML or CSS) (optional, default null)
  • height number height of the DOM element (if not already setup in HTML or CSS) (optional, default null)

Examples

let myGraphExample1 = new Grapher('myGraphExample1',
                                {"data": data,
                                 "x": {
                                     "name": "date",
                                      "scale": "scaleTime",
                                      "parse": (d) => d3.timeParse('%Y-%m-%d')(d),
                                      "tickFormat": d3.timeFormat("%d/%m/%y"),
                                      "label": "Date"
                                  },
                                  "y": {
                                      "name": "value",
                                      "tickFormat": d3.format('.3s'),
                                      "label": "Glucose"
                                  },
                                  "type": "dotted-line",
                                  });

draw

Draw the Grapher object

Parameters
  • options (Object | null) you can pass an options Object to update the element's option. @link Grapher

margin

Get and sets the values of the inner margins

Parameters

  • margin Object
    • margin.top string margin top (optional, default 10)
    • margin.right (string | function) margin right depends of the width of the graph (optional, default (x)=>x<400?20:30)
    • margin.bottom string margin bottom
    • margin.left (string | function) margin left depends of the width of the graph (optional, default (x)=>x<400?40:60)

Returns Object

margin

Get and sets the values of the inner margins

Parameters

  • margin Object
    • margin.top string margin top (optional, default 10)
    • margin.right (string | function) margin right depends of the width of the graph (optional, default (x)=>x<400?20:30)
    • margin.bottom string margin bottom
    • margin.left (string | function) margin left depends of the width of the graph (optional, default (x)=>x<400?40:60)

Returns Object

options

Gets and sets the option for Grapher object. Note that setter is called only by typing myGraph.options = {something}; Typing myGraph.options.data = something; do work but setter is not called and data is not parsed again, etc.

Parameters

  • options Object @link Grapher

draw

Draw the Grapher object

Parameters

  • options (Object | null) you can pass an options Object to update the element's option. @link Grapher

Donut

The Donut class is a children class of the Grapher class. This is still a work in progress. Currently the Donut is mainly a Gauge.

Parameters

  • id string id of the DOM element
  • options Object Set options for the Gauge
    • options.value number Value to display (optional, default 50)
    • options.foregroundColor function Function to plot a foreground color (function of the value). Default is d => #1abb9b. It's a function rather than a string so that it allows you to change the color depending on the value.
    • options.backgroundColor string Background color of the donut. Default is the "weighted average" between the background color and foreground color with a 60% weight on the background color.
    • options.innerRadius number inner radius of the donut. Default is 40% of the size. (optional, default 0.4*size)
    • options.outerRadius number outer radius of the donut. Default is 50% of the size. (optional, default 0.5*size)
    • options.startAngle number starting angle. Default is -180 (other values allows you to plot less than a "circle"). (optional, default -180)
    • options.endAngle number ending angle. Default is 180 (optional, default 180)
    • options.minValue number mininum value when the angle is -180, default is 0. (optional, default 0)
    • options.maxValue number maximum value when the angle is 180, default is 100. (optional, default 100)
    • options.displayValue boolean? display value inside the donut.
    • options.fontSize string fontSize of the displayed value inside the donut. Default is the font size of the DOM element.
    • options.cornerRadius number corner radius of the arc (see cornerRadius of d3.arc for more details) (optional, default 0)
    • options.maxHeight number maximum height of the DOM element. Default is DOM element size. (optional, default size)
    • options.padAngle number pad angle of the arc (see padAngle of d3.arc for more details) (optional, default 0.03)
  • displayText function text to be displayed inside the donut. It's a function of the value. Default d => d (e.g. dispkay the value).
  • size (number | null) size of the gauge (for a gauge, width and height are the same).
  • type string type of the graph. (optional, default "donut")

Examples

let myArc = new g.Donut("myArc",
                        {"value": 30},
                        size=100);
myArc.draw();

_draw

Return a d3 scale for colors

Gauge

The Gauge is a child of Donut class with convenient defaults for plotting a gauge.

Parameters

  • id string id of the DOM element
  • options Object Set options for the Gauge
  • size (number | null) size of the gauge (for a gauge, width and height are the same).

Examples

let myGauge = new g.Donut("myGauge",
                         {"value": 20},
                         size=100);
myGauge.draw();

See also

There are many libraries to do plots out-there, starting by D3.js. You can also have a look to more high-level libraries like C3.js, plot.ly, Chart.js, Vega.

Credits

Copyright: Louis de Charsonville, louisdecharson@posteo.net