Skip to content

Instantly share code, notes, and snippets.

@swilcox

swilcox/_mgraph.md

Last active Oct 6, 2017
Embed
What would you like to do?
Multi-graph example widget for Shopify's Dashing dashboard

Multi-graph widget for Dashing

Description

Multi-graph widget for Shopify's dashing to display a comparison style graph (or stacked with a minor modification). Obviously, this is an example that is built heavily on the existing graph widget that is provided with dashing. This widget provides a more clear framework for expanding the graph for multiple series (or nodes) of data. After seeing the example code, it should be fairly easy to expand to 3 or more overlaid graphs (although colors might get tricky). And really, this is just a slightly greater use of the cool rickshaw graphs.

To use this widget:

  • copy mgraph.coffee, mgraph.html and mgraph.scss into a new /widgets/mgraph folder
  • copy multitest.rb into your /jobs folder

Then include the widget in a dashboard, by adding the following snippet to your dashboard layout file:

  • For a nice 2 tile-wide widget:
    <li data-row="1" data-col="1" data-sizex="2" data-sizey="1">

      <div data-id="multitest" data-view="Mgraph" data-title="Multi Convergence" style="background-color:#ff9618"></div>
      
    </li>
class Dashing.Mgraph extends Dashing.Widget
@accessor 'current', ->
return @get('displayedValue') if @get('displayedValue')
points = @get('points')
if points
points[0][points[0].length - 1].y + ' / ' + points[1][points[1].length - 1].y
ready: ->
container = $(@node).parent()
# Gross hacks. Let's fix this.
width = (Dashing.widget_base_dimensions[0] * container.data("sizex")) + Dashing.widget_margins[0] * 2 * (container.data("sizex") - 1)
height = (Dashing.widget_base_dimensions[1] * container.data("sizey"))
@graph = new Rickshaw.Graph(
element: @node
width: width
height: height
renderer: 'area'
stroke: false
series: [
{
color: "#fff",
data: [{x:0, y:0}]
},
{
color: "#222",
data: [{x:0, y:0}]
}
]
)
@graph.series[0].data = @get('points') if @get('points')
x_axis = new Rickshaw.Graph.Axis.Time(graph: @graph)
y_axis = new Rickshaw.Graph.Axis.Y(graph: @graph, tickFormat: Rickshaw.Fixtures.Number.formatKMBT)
@graph.renderer.unstack = true
@graph.render()
onData: (data) ->
if @graph
@graph.series[0].data = data.points[0]
@graph.series[1].data = data.points[1]
@graph.render()
<h1 class="title" data-bind="title"></h1>
<h3 class="value" data-bind="current"></h2>
<p class="more-info" data-bind="moreinfo"></p>
// ----------------------------------------------------------------------------
// Sass declarations
// ----------------------------------------------------------------------------
$background-color: #dc5945;
$title-color: rgba(255, 255, 255, 0.7);
$moreinfo-color: rgba(255, 255, 255, 0.3);
$tick-color: rgba(0, 0, 0, 0.4);
// ----------------------------------------------------------------------------
// Widget-graph styles
// ----------------------------------------------------------------------------
.widget-mgraph {
background-color: $background-color;
position: relative;
svg {
position: absolute;
opacity: 0.4;
fill-opacity: 0.4;
left: 0px;
top: 0px;
}
.title, .value {
position: relative;
z-index: 99;
}
.title {
color: $title-color;
}
.more-info {
color: $moreinfo-color;
font-weight: 600;
font-size: 20px;
margin-top: 0;
}
.x_tick {
position: absolute;
bottom: 0;
.title {
font-size: 20px;
color: $tick-color;
opacity: 0.5;
padding-bottom: 3px;
}
}
.y_ticks {
font-size: 20px;
fill: $tick-color;
fill-opacity: 1;
}
.domain {
display: none;
}
}
# this is just the dummy sample using random data to illustrate
# replace the random data with your real data... wherever you get it from
# Populate the multi-graph with some initial points
points1 = []
points2 = []
(1..10).each do |i|
points1 << { x: i, y: rand(50) } # graph 1 initialization
points2 << { x: i, y: rand(50) } # graph 2 initialization
end
last_x = points1.last[:x]
SCHEDULER.every '2s' do
points1.shift
points2.shift
last_x += 1
points1 << { x: last_x, y: rand(50) } # this is where you'd add a data element for graph 1
points2 << { x: last_x, y: rand(50) } # this is where you'd add a data element for graph 2
send_event('multitest', points: [points1, points2])
end
@shushiej

This comment has been minimized.

Copy link

@shushiej shushiej commented Nov 19, 2013

When i try to load this graph, no data is showing up, not even the sample data that u have provided, any ideas y?

@alexminnaar

This comment has been minimized.

Copy link

@alexminnaar alexminnaar commented Dec 3, 2013

I am having some trouble getting a third data series to appear. Here is the mgraph.coffee code that I have modified to include a third series.


  @accessor 'current', ->
    return @get('displayedValue') if @get('displayedValue')
    points = @get('points')
    if points
      points[0][points[0].length - 1].y + ' / ' + points[1][points[1].length - 1].y ' / ' + points[2][points[2].length - 1].y

  ready: ->
    container = $(@node).parent()
    # Gross hacks. Let's fix this.
    width = (Dashing.widget_base_dimensions[0] \* container.data("sizex")) + Dashing.widget_margins[0] \* 2 \* (container.data("sizex") - 1)
    height = (Dashing.widget_base_dimensions[1] \* container.data("sizey"))
    @graph = new Rickshaw.Graph(
      element: @node
      width: width
      height: height
      renderer: 'area'
      stroke: false
      series: [
        {
        color: "#fff",
        data: [{x:0, y:0}]
        },
        {
            color: "#222",
            data: [{x:0, y:0}]
        },
        {
            color: "#333",
            data: [{x:0, y:0}]
        }
      ]
    )

@graph.series[0].data = @get('points') if @get('points')

x_axis = new Rickshaw.Graph.Axis.Time(graph: @graph)
y_axis = new Rickshaw.Graph.Axis.Y(graph: @graph, tickFormat: Rickshaw.Fixtures.Number.formatKMBT)
@graph.renderer.unstack = true
@graph.render()


  onData: (data) ->
    if @graph
      @graph.series[0].data = data.points[0]
      @graph.series[1].data = data.points[1]
      @graph.series[2].data = data.points[2]
      @graph.render()```

When I run this code in dashing, no dashboards actually render (just a blank page appears).  I checked that the three data series are actually making it to this file from the .rb job.  The error seems to occur when I add a third series to 'series: ' where the rickshaw graph is being defined.  I'm not sure what I am doing wrong. Can you spot any errors? Thanks
@pranavjain02

This comment has been minimized.

Copy link

@pranavjain02 pranavjain02 commented May 26, 2014

@shushiej
Hey I also faced the same problem, I just sent my JSON data instead of fetching from the job. Which solved my problem

curl -d '{ "auth_token": "XXXXX","points": [[{"x":1,"y":22},{"x":2,"y":22},{"x":3,"y":2}],[{"x":1,"y":6},{"x":2,"y":22},{"x":3,"y":30}]]}' http://localhost:3030/widgets/{YOUR_DIV_DATA_ID}

@pranavjain02

This comment has been minimized.

Copy link

@pranavjain02 pranavjain02 commented May 26, 2014

@alexminnaar

Hey I modified the file as
class Dashing.Mgraph extends Dashing.Widget

@Accessor 'current', ->
return @get('displayedValue') if @get('displayedValue')
points = @get('points')
if points
points[0][points[0].length - 1].y + ' / ' + points[1][points[1].length - 1].y + ' / ' + points[2][points[2].length - 1].y

ready: ->
container = $(@node).parent()
# Gross hacks. Let's fix this.
width = (Dashing.widget_base_dimensions[0] * container.data("sizex")) + Dashing.widget_margins[0] * 2 * (container.data("sizex") - 1)
height = (Dashing.widget_base_dimensions[1] * container.data("sizey"))
@graph = new Rickshaw.Graph(
element: @node
width: width
height: height
renderer: 'area'
stroke: true
series: [
{
color: "#fff",
data: [{x:0, y:0}]
},
{
color: "#222",
data: [{x:0, y:0}]
},
{
color: "#333",
data: [{x:0, y:0}]
}
]
)

@graph.series[0].data = @get('points') if @get('points')

x_axis = new Rickshaw.Graph.Axis.Time(graph: @graph)
y_axis = new Rickshaw.Graph.Axis.Y(graph: @graph, tickFormat: Rickshaw.Fixtures.Number.formatKMBT)
@graph.renderer.unstack = true
@graph.render()

onData: (data) ->
if @graph
@graph.series[0].data = data.points[0]
@graph.series[1].data = data.points[1]
@graph.series[2].data = data.points[2]

  @graph.render()

And its working fine.
PS: Try restarting the dashing service

@pranavjain02

This comment has been minimized.

Copy link

@pranavjain02 pranavjain02 commented May 26, 2014

When I refresh the page the graph information is getting lost only the final value is being displayed.
Where as for the original graph it is still there.

Any assistance will be highly appreciated.

@Chris-Lancaster

This comment has been minimized.

Copy link

@Chris-Lancaster Chris-Lancaster commented Aug 10, 2015

@pranavjain02
I too am having the issue of the data disappearing on page refresh.
did you find a solution?

@Henskie

This comment has been minimized.

Copy link

@Henskie Henskie commented Feb 2, 2016

Yea I have that issue with refreshing I am not sure if there is an exist fix. The issue I have in addition to the page refresh issue is I cannot get the colors of the data points (the actual data on the graph) to show any colors than varying shades of gray. I would also like to show what values correspond to what

@swilcox

This comment has been minimized.

Copy link
Owner Author

@swilcox swilcox commented Feb 6, 2016

Not sure how to resolve the issues mentioned. I'm no longer using dashing... but a much much more thorough version of enhancing the graph widget can be found here: https://gist.github.com/jwalton/6614023

@pcompassion

This comment has been minimized.

Copy link

@pcompassion pcompassion commented Feb 8, 2016

@swilcox I'm just starting to use dashing, can you share why you stopped using it? have you found a better alternative?

@GWWallen

This comment has been minimized.

Copy link

@GWWallen GWWallen commented Apr 22, 2016

Is there a way to turn off the fill on the charts?

@GWWallen

This comment has been minimized.

Copy link

@GWWallen GWWallen commented Apr 26, 2016

Figured out the fill option. Do anyone know how to have the "points" have dots, or indicators of where the data is? Also, possible to add lines in the back.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment