var MIN_RADIUS = 20; var MAX_RADIUS = 50; var DEFAULT_OPTIONS = { margin: {top: MAX_RADIUS, right: MAX_RADIUS, bottom: MAX_RADIUS, left: MAX_RADIUS} }; var xScale = d3.scale.linear(); var yScale = d3.scale.linear(); var radiusScale = d3.scale.linear() .range([MIN_RADIUS, MAX_RADIUS]); var colorScale = d3.scale.category20(); var data = d3.range(20).map(function(i) { return {size: i, x: Math.random(), y: Math.random()}; }); // create and configure the circle charlet var circles = CircleChartlet() .property('radius', function(d, i) {return radiusScale(d.size);}) .property('color', function(d, i) {return d.customColor || colorScale(i);}) .on('circleClicked', onClicked); // create chart var chart = new d3Kit.Skeleton('.chart', DEFAULT_OPTIONS) .autoResize('both') .on('resize', onResize) .on('data', onData); chart.resizeToFitContainer(); chart.data(data); // cope with data change function onData(data) { if (chart.hasData()) { radiusScale.domain(d3.extent(data, function(d) {return d.size;})); var nodes = chart.getRootG().selectAll('g.node') .data(data); nodes.enter() .append('g') .classed('node', true) .call(circles.enter); nodes.exit() .call(circles.exit); onResize(); } } // handle resize function onResize() { xScale.range([0, chart.getInnerWidth ()]); yScale.range([0, chart.getInnerHeight()]); chart.getRootG().selectAll('.node') .attr('transform', function(d) {return 'translate(' + [xScale(d.x), yScale(d.y)] + ')';}) .call(circles.update); } // toggle circles back when clicked function onClicked(d) { d.customColor = d.customColor ? null : 'black'; chart.getRootG().selectAll('.node').call(circles.update); } // circle chartlet constructor function CircleChartlet() { var events = ['circleClicked']; var chartlet = d3Kit.Chartlet(enter, update, exit, events); function enter(selection, done) { selection .append('circle') .attr('r', 0) .attr('fill', 'white') .on('click', chartlet.getDispatcher().circleClicked); done(selection); } function update(selection, done) { selection.select('circle') .transition() .attr('fill', chartlet.property('color')) .attr('r', chartlet.property('radius')) .each('end', done); } function exit(selection, done) { selection.select('circle') .transition() .attr('r', 0) .remove() .each('end', done); } return chartlet; };