Permalink
Browse files

hacking on icicle visualization

  • Loading branch information...
1 parent beb9563 commit 12462e13c897d06f97d1892f8bde186b16b28126 @davepacheco davepacheco committed Apr 2, 2012
Showing with 2,295 additions and 343 deletions.
  1. +6 −2 Makefile
  2. +32 −0 cmd/stackvis
  3. +44 −0 lib/output-icicle.js
  4. +1 −1 lib/stackvis.js
  5. +52 −54 lib/www/icicle.js
  6. +2,026 −285 lib/www/sample.json
  7. +1 −1 package.json
  8. +133 −0 tools/jsl.web.conf
View
@@ -17,13 +17,17 @@ CATEST = tools/catest
#
# Files
#
-JS_FILES := $(shell find cmd lib test -name '*.js')
+JS_FILES := $(shell find cmd lib test -name '*.js' \
+ -not -path 'lib/www/*')
JSL_CONF_NODE = tools/jsl.node.conf
+JSL_CONF_WEB = tools/jsl.web.conf
JSL_FILES_NODE = $(JS_FILES)
+JSL_FILES_WEB := $(shell find lib/www -name '*.js' \
+ -not -name 'd3.*.js')
JSSTYLE_FLAGS = -oleading-right-paren-ok=1
-JSSTYLE_FILES = $(JS_FILES)
+JSSTYLE_FILES = $(JSL_FILES_NODE) $(JSL_FILES_WEB)
JSTEST_FILES := $(shell find test -name 'tst.*.js')
View
@@ -0,0 +1,32 @@
+#!/usr/bin/env node
+
+/*
+ * cmd/stackvis: convert stacks between different representations
+ */
+
+var mod_bunyan = require('bunyan');
+
+var mod_stackvis = require('../lib/stackvis');
+
+var log = new mod_bunyan({
+ 'name': 'stackvis',
+ 'stream': process.stderr
+});
+
+if (process.argv.length != 4) {
+ console.error('usage: stackvis input-format output-format');
+ process.exit(2);
+}
+
+var reader, writer;
+
+try {
+ reader = new mod_stackvis.readerLookup(process.argv[2]);
+ writer = new mod_stackvis.writerLookup(process.argv[3]);
+} catch (ex) {
+ console.error(ex.message);
+}
+
+mod_stackvis.pipeStacks(log, process.stdin, reader, writer, process.stdout,
+ function () {});
+process.stdin.resume();
View
@@ -0,0 +1,44 @@
+/*
+ * lib/output-icicle.js: emits StackSets as JSON suitable for use in a D3 icicle
+ * layout. See lib/stackvis.js for interface details.
+ */
+
+var mod_assert = require('assert');
+
+exports.emit = function emitIcicleData(args, callback)
+{
+ mod_assert.ok(args.stacks && args.stacks.constructor &&
+ args.stacks.constructor.name == 'StackSet',
+ 'required "stacks" argument must be a StackSet');
+ mod_assert.ok(args.output && args.output.write &&
+ typeof (args.output.write) == 'function',
+ 'required "output" argument must be a function');
+ mod_assert.ok(args.log, 'required "log" argument must be a logger');
+
+ var stacks = args.stacks;
+ var output = args.output;
+ var tree = {};
+
+ stacks.eachStackByStack(function (frames, count) {
+ var subtree = tree;
+ var node, i;
+
+ for (i = 0; i < frames.length; i++) {
+ if (!subtree.hasOwnProperty(frames[i]))
+ subtree[frames[i]] = {
+ svUnique: 0,
+ svTotal: 0,
+ svChildren: {}
+ };
+
+ node = subtree[frames[i]];
+ node.svTotal += count;
+ subtree = node.svChildren;
+ }
+
+ node.svUnique += count;
+ });
+
+ output.write(JSON.stringify(tree, null, '\t'));
+ callback();
+};
View
@@ -19,7 +19,7 @@ exports.pipeStacks = pipeStacks;
* BunyanLog). The object itself should then emit "stack" and "end" events.
* The "stack" event includes an array of frames and a count for the number of
* times that stack was seen in the input:
- *
+ *
* reader.on('stack', function (frames, count) {
* console.log(count + ' ' + frames.join(', '));
* });
View
@@ -4,8 +4,8 @@
window.onload = svInit;
-var svWidth = 800;
-var svHeight = 500;
+var svWidth = 1000;
+var svHeight = 900;
var xScale, yScale, colorScale;
var svData, svRects, svText;
var svInfo;
@@ -17,68 +17,66 @@ function svInit()
colorScale = d3.scale.category20c();
svInfo = d3.select('#info')[0][0].firstChild;
- console.log(svInfo.nodeValue);
-
- var vis = d3.select("#chart").append("svg:svg").
- attr("width", svWidth).
- attr("height", svHeight);
-
+
+ var vis = d3.select('#chart').append('svg:svg').
+ attr('width', svWidth).
+ attr('height', svHeight);
+
var partition = d3.layout.partition().children(function (d) {
- return (isNaN(d.value) ? d3.entries(d.value) : null);
- }).value(function (d) { return (d.value); });
-
- d3.json("sample.json", function (json) {
+ var rv = d3.entries(d.value.svChildren);
+ return (rv);
+ }).value(function (d) { return (d.value.svTotal); });
+
+ d3.json('sample.json', function (json) {
svData = partition(d3.entries(json)[0]);
- svRects = vis.selectAll("rect").data(svData)
- .enter().append("svg:rect")
- .attr("x", function (d) { return (xScale(d.x)); })
- .attr("y", function (d) { return (yScale(d.y)); })
- .attr("rx", 5)
- .attr("ry", 5)
- .attr("width", function (d) { return (xScale(d.dx)); })
- .attr("height", function (d) { return (yScale(d.dy)); })
- .attr("fill", function (d) {
- return (colorScale((d.children ? d : d.parent).data.key));
- })
- .on("click", svClick)
- .on("mouseover", svStatus);
- svText = vis.selectAll("text").data(svData)
- .enter().append("text")
- .attr("x", function (d) { return (xScale(d.x)); })
- .attr("y", function (d) { return (yScale(d.y)); })
- .attr("dx", 5)
- .attr("dy", "1.2em")
- .attr("text-anchor", "start")
- .text(function (d) { return (d.data.key); })
+ svRects = vis.selectAll('rect').data(svData)
+ .enter().append('svg:rect')
+ .attr('x', function (d) { return (xScale(d.x)); })
+ .attr('y', function (d) { return (yScale(d.y)); })
+ .attr('rx', 5)
+ .attr('ry', 5)
+ .attr('width', function (d) { return (xScale(d.dx)); })
+ .attr('height', function (d) { return (yScale(d.dy)); })
+ .attr('fill', function (d) { return (colorScale(d.data.key)); })
+ .on('click', svClick)
+ .on('mouseover', svStatus);
+ svText = vis.selectAll('text').data(svData)
+ .enter().append('text')
+ .attr('x', function (d) { return (xScale(d.x)); })
+ .attr('y', function (d) { return (yScale(d.y)); })
+ .attr('dx', 5)
+ .attr('dy', '1.2em')
+ .attr('text-anchor', 'start')
+ .text(function (d) { return (d.data.key); });
});
}
-function svClick(d)
+function svClick(cd)
{
- xScale.domain([d.x, d.x + d.dx]);
- yScale.domain([d.y, 1]).range([d.y ? 20 : 0, svHeight]);
+ xScale.domain([cd.x, cd.x + cd.dx]);
+ yScale.domain([cd.y, 1]).range([cd.y ? 20 : 0, svHeight]);
svRects.transition()
- .duration(400)
- .attr("x", function (d) { return (xScale(d.x)); })
- .attr("y", function (d) { return (yScale(d.y)); })
- .attr("width", function (d) {
- return (xScale(d.x + d.dx) - xScale(d.x));
- })
- .attr("height", function (d) {
- return (yScale(d.y + d.dy) - yScale(d.y));
- });
+ .duration(400)
+ .attr('x', function (d) { return (xScale(d.x)); })
+ .attr('y', function (d) { return (yScale(d.y)); })
+ .attr('width', function (d) {
+ return (xScale(d.x + d.dx) - xScale(d.x));
+ })
+ .attr('height', function (d) {
+ return (yScale(d.y + d.dy) - yScale(d.y));
+ });
svText.transition()
- .duration(400)
- .attr("x", function (d) { return (xScale(d.x)); })
- .attr("y", function (d) { return (yScale(d.y)); })
- .attr("width", function (d) {
- return (xScale(d.x + d.dx) - xScale(d.x));
- })
- .attr("height", function (d) {
- return (yScale(d.y + d.dy) - yScale(d.y));
- });
+ .duration(400)
+ .attr('x', function (d) { return (xScale(d.x)); })
+ .attr('y', function (d) { return (yScale(d.y)); })
+ .attr('width', function (d) {
+ return (xScale(d.x + d.dx) - xScale(d.x));
+ })
+ .attr('height', function (d) {
+ return (yScale(d.y + d.dy) - yScale(d.y));
+ });
}
function svStatus(d)
Oops, something went wrong.

0 comments on commit 12462e1

Please sign in to comment.