Forked from: https://gist.github.com/gtb104/3667340
Here's a d3 plugin that allows you to create a polygon selection. You instantiate it just like d3.svg.brush.
var brush = d3.svg.polybrush();
It has an extra public method that 'brush' does not, and that's 'isWithinExtent(x, y)'. You can use this method to test if a given point falls within the drawn extent.
if (brush.isWithinExtent(x, y)) {
console.log("I'm inside!");
}
Usage:
Click to add an anchor point, double click to close the selection.
Drag the selection to reposition it.
Double click outside the selection to clear it.
Areas For Improvement:
xxxxxxxxxx
<html>
<head>
<script type="text/javascript" src="https://d3js.org/d3.v2.min.js"></script>
<script type="text/javascript" src="polybrush.js"></script>
<style type="text/css">
.brush .extent {
stroke: #000;
stroke-width: 1.5px;
fill: #000;
fill-opacity: 0.3;
}
.voronoi {
fill: steelblue;
fill-opacity: 0.4;
stroke: steelblue;
stroke-opacity: 0.5;
}
.voronoi.selected {
fill: red;
fill-opacity: 0.4;
stroke: darkred;
stroke-opacity: 0.5;
}
.point.selected {
fill: red;
stroke: darkred;
stroke-width: 1;
}
</style>
</head>
<body>
<div id="chart"></div>
<script type="text/javascript">
var w = 960,
h = 500;
var brush = d3.svg.polybrush()
.x(d3.scale.linear().range([0, w]))
.y(d3.scale.linear().range([0, h]))
.on("brushstart", function() {
svg.selectAll(".selected").classed("selected", false);
})
.on("brush", function() {
// set the 'selected' class for the circle
svg.selectAll(".point").classed("selected", function(d) {
//get the associated circle
var id = d3.select(this).attr("id");
var i = id.substr(id.indexOf("-")+1, id.length);
var vornoi = d3.select("#path-"+i);
// set the 'selected' class for the path
if (brush.isWithinExtent(d[0], d[1])) {
vornoi.classed("selected", true);
return true;
} else {
vornoi.classed("selected", false);
return false;
}
});
});
var vertices = d3.range(200).map(function(d) {
return [Math.random() * w, Math.random() * h];
});
var svg = d3.select("#chart")
.append("svg:svg")
.attr("width", w)
.attr("height", h);
var paths, points, clips;
clips = svg.append("svg:g").attr("id", "point-clips");
points = svg.append("svg:g").attr("id", "points");
paths = svg.append("svg:g").attr("id", "point-paths");
clips.selectAll("clipPath")
.data(vertices)
.enter().append("svg:clipPath")
.attr("id", function(d, i) { return "clip-"+i;})
.append("svg:circle")
.attr('cx', function(d) { return d[0]; })
.attr('cy', function(d) { return d[1]; })
.attr('r', 20);
paths.selectAll("path")
.data(d3.geom.voronoi(vertices))
.enter().append("svg:path")
.attr("d", function(d) { return "M" + d.join(",") + "Z"; })
.attr("id", function(d,i) { return "path-"+i; })
.attr("clip-path", function(d,i) { return "url(#clip-"+i+")"; })
.attr("class", "voronoi");
points.selectAll("circle")
.data(vertices)
.enter().append("svg:circle")
.attr("class", "point")
.attr("id", function(d, i) { return "point-"+i; })
.attr("transform", function(d) { return "translate(" + d + ")"; })
.attr("r", 2)
.attr('stroke', 'none');
svg.append("svg:g")
.attr("class", "brush")
.call(brush);
</script>
</body>
</html>
Modified http://d3js.org/d3.v2.min.js to a secure url
https://d3js.org/d3.v2.min.js