|
|
|
@ -31,6 +31,7 @@ nv.models.scatter = function() {
|
|
|
|
|
, sizeRange = null
|
|
|
|
|
, singlePoint = false
|
|
|
|
|
, dispatch = d3.dispatch('elementClick', 'elementMouseover', 'elementMouseout')
|
|
|
|
|
, useVoronoi = true
|
|
|
|
|
;
|
|
|
|
|
|
|
|
|
|
//============================================================
|
|
|
|
@ -62,8 +63,6 @@ nv.models.scatter = function() {
|
|
|
|
|
return series;
|
|
|
|
|
});
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
//------------------------------------------------------------
|
|
|
|
|
// Setup Scales
|
|
|
|
|
|
|
|
|
@ -134,11 +133,11 @@ nv.models.scatter = function() {
|
|
|
|
|
g .attr('clip-path', clipEdge ? 'url(#nv-edge-clip-' + id + ')' : '');
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
function updateInteractiveLayer() {
|
|
|
|
|
|
|
|
|
|
if (!interactive) return false;
|
|
|
|
|
|
|
|
|
|
var eventElements;
|
|
|
|
|
|
|
|
|
|
var vertices = d3.merge(data.map(function(group, groupIndex) {
|
|
|
|
|
return group.values
|
|
|
|
@ -170,22 +169,44 @@ nv.models.scatter = function() {
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
//inject series and point index for reference into voronoi
|
|
|
|
|
var voronoi = d3.geom.voronoi(vertices).map(function(d, i) {
|
|
|
|
|
return {
|
|
|
|
|
'data': d,
|
|
|
|
|
'series': vertices[i][2],
|
|
|
|
|
'point': vertices[i][3]
|
|
|
|
|
}
|
|
|
|
|
});
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
var pointPaths = wrap.select('.nv-point-paths').selectAll('path')
|
|
|
|
|
.data(voronoi);
|
|
|
|
|
pointPaths.enter().append('path')
|
|
|
|
|
.attr('class', function(d,i) { return 'nv-path-'+i; });
|
|
|
|
|
pointPaths.exit().remove();
|
|
|
|
|
pointPaths
|
|
|
|
|
.attr('d', function(d) { return 'M' + d.data.join(',') + 'Z'; })
|
|
|
|
|
if (useVoronoi === true) {
|
|
|
|
|
var voronoi = d3.geom.voronoi(vertices).map(function(d, i) {
|
|
|
|
|
return {
|
|
|
|
|
'data': d,
|
|
|
|
|
'series': vertices[i][2],
|
|
|
|
|
'point': vertices[i][3]
|
|
|
|
|
}
|
|
|
|
|
});
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
var pointPaths = wrap.select('.nv-point-paths').selectAll('path')
|
|
|
|
|
.data(voronoi);
|
|
|
|
|
pointPaths.enter().append('path')
|
|
|
|
|
.attr('class', function(d,i) { return 'nv-path-'+i; });
|
|
|
|
|
pointPaths.exit().remove();
|
|
|
|
|
pointPaths
|
|
|
|
|
.attr('d', function(d) { return 'M' + d.data.join(',') + 'Z'; });
|
|
|
|
|
|
|
|
|
|
eventElements = pointPaths;
|
|
|
|
|
|
|
|
|
|
} else {
|
|
|
|
|
// bring data in form needed for click handlers
|
|
|
|
|
var dataWithPoints = vertices.map(function(d, i) {
|
|
|
|
|
return {
|
|
|
|
|
'data': d,
|
|
|
|
|
'series': vertices[i][2],
|
|
|
|
|
'point': vertices[i][3]
|
|
|
|
|
}
|
|
|
|
|
});
|
|
|
|
|
|
|
|
|
|
// add event handlers to points instead voronoi paths
|
|
|
|
|
eventElements = wrap.select('.nv-groups').selectAll('.nv-group')
|
|
|
|
|
.selectAll('path.nv-point')
|
|
|
|
|
.data(dataWithPoints)
|
|
|
|
|
.style('pointer-events', 'auto'); // recativate events, disabled by css
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
eventElements
|
|
|
|
|
.on('click', function(d) {
|
|
|
|
|
var series = data[d.series],
|
|
|
|
|
point = series.values[d.point];
|
|
|
|
@ -385,7 +406,7 @@ nv.models.scatter = function() {
|
|
|
|
|
sizeDomain = _;
|
|
|
|
|
return chart;
|
|
|
|
|
};
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
chart.sizeRange = function(_) {
|
|
|
|
|
if (!arguments.length) return sizeRange;
|
|
|
|
|
sizeRange = _;
|
|
|
|
@ -434,6 +455,15 @@ nv.models.scatter = function() {
|
|
|
|
|
return chart;
|
|
|
|
|
};
|
|
|
|
|
|
|
|
|
|
chart.useVoronoi= function(_) {
|
|
|
|
|
if (!arguments.length) return useVoronoi;
|
|
|
|
|
useVoronoi = _;
|
|
|
|
|
if (useVoronoi === false) {
|
|
|
|
|
clipVoronoi = false;
|
|
|
|
|
}
|
|
|
|
|
return chart;
|
|
|
|
|
};
|
|
|
|
|
|
|
|
|
|
chart.clipRadius = function(_) {
|
|
|
|
|
if (!arguments.length) return clipRadius;
|
|
|
|
|
clipRadius = _;
|
|
|
|
|