I basically copied the example https://bl.ocks.org/skokenes/a85800be6d89c76c1ca98493ae777572
Then I got the code to work with my data. So, I can now get the lasso to work.
But when I try to add back my old code for the circles to display a text-type tool tip, the lasso breaks. The code then puts the class variables such as not_possible or selected on the "text" elements rather than on the "circle" elements where they need to be.
I found that is the issue by using Chrome developer tools.
When the tool tips code is commented out, the lasso code works and the DOM looks like this:
<circle cx="854" cy="37" fill="red" r="7" class="selected"></circle>
When the tool tips code is live, the tool tips work but the lasso code doesn't work and the DOM looks like this:
<circle cx="854" cy="37" fill="red" r="4.9">
<title r="3.5" class> ==$0
"curr = 89.7, prev = 89.5, geo = Alaska, measure = Percent Citizen, Born in the US"
</title>
</circle>
I've tried changing the styles for the classes, for example, from ".possible" to "circle.possible" but that doesn't help. I've googled for suggestions but haven't found anything that I could make work. I've tried passing the circle selection thru lasso.items(circles) but that doesn't work.
This is the lasso code that does work: the troublesome ".append title" and "text" lines are commented out.
var margin = {top: 20, right: 15, bottom: 60, left: 60}
, width = 960 - margin.left - margin.right
, height = 960 - margin.top - margin.bottom;
var xScale = d3.scaleLinear()
.domain([0, d3.max(data, function(d) { return d[1]; })])
.range([0, width]);
var yScale = d3.scaleLinear()
.domain([0, d3.max(data, function(d) { return d[0]; })])
.range([height, 0]);
var svgArea = d3.select('.content')
.append('svg')
.attr('width', width + margin.right + margin.left)
.attr('height', height + margin.top + margin.bottom)
.attr('class', 'chart');
var main = svgArea.append('g')
.attr('transform', 'translate(' + margin.left + ',' + margin.top + ')')
.attr('width', width)
.attr('height', height)
.attr('class', 'main');
main.append('g')
.attr('transform', 'translate(0,' + height + ')')
.attr('class', 'main axis date')
.call(d3.axisBottom(xScale));
main.append('g')
.append("text")
.attr("x", width / 2)
.attr("y", height + margin.bottom - 10)
.style("text-anchor", "middle")
.style("font", "14px times")
.text("Current X");
main.append('g')
.attr('transform', 'translate(0,0)')
.attr('class', 'main axis date')
.call(d3.axisLeft(yScale));
main.append('g')
.append("text")
.attr("transform", "rotate(-90)")
.attr("x", 0 - (height / 2))
.attr("y", 0 - margin.left / 2)
.style("text-anchor", "middle")
.style("font", "14px times")
.text("Previous Y");
var rScale = d3.scaleLinear()
.domain([0, d3.max(data, function(d) { return d[1]; })])
.range([ 4, 5 ]);
var lasso_start = function() {
lasso.items()
.attr("r",7)
.classed("not_possible",true)
.classed("selected",false)
;
};
var lasso_draw = function() {
lasso.possibleItems()
.classed("not_possible",false)
.classed("possible",true)
;
lasso.notPossibleItems()
.classed("not_possible",true)
.classed("possible",false)
;
};
var lasso_end = function() {
lasso.items()
.classed("not_possible",false)
.classed("possible",false)
;
lasso.selectedItems()
.classed("selected",true)
.attr("r", 7)
;
lasso.notSelectedItems()
.attr("r", 3.5)
;
};
var circles = main.selectAll("circle")
.data(data)
.enter().append("circle")
.attr("cx", function (d,i) { return xScale(d[1]); } )
.attr("cy", function (d) { return yScale(d[0]); } )
.attr("fill", function (d) { if (d[1] > 75) { return "red"; } else { return "black"; } })
.attr("r", function (d) { return rScale(d[1]); })
//.append("title")
//.text(function(d) {
// return "curr = " + d[1] +
// ", prev = " + d[0] +
// ", geo = " + d[2] +
// ", measure = " + d[3];
// })
;
var lasso = d3.lasso()
.items(circles)
.closePathDistance(75) // max distance for the lasso loop to be closed
.closePathSelect(true) // can items be selected by closing the path?
.targetArea(svgArea) // area where the lasso can be started
.on("start",lasso_start) // lasso start function
.on("draw",lasso_draw) // lasso draw function
.on("end",lasso_end); // lasso end function
svgArea.call(lasso);
Why does including ".title" and ".text" cause a problem? And how do I solve it?
I don't think the problem is with the CSS, but here it is:
<style>
// styling for D3 chart
.chart {
background: #fdfefe;
}
.main text {
font: 10px sans-serif;
}
// styling for D3-lasso
.axis path,
.axis line {
fill: none;
stroke: #000;
shape-rendering: crispEdges;
}
circle {
fill-opacity: 0.4;
}
.dot {
stroke: #000;
}
.lasso path {
stroke: rgb(80,80,80);
stroke-width: 2px;
}
.lasso .drawn {
fill-opacity: 0.05 ;
}
.lasso .loop_close {
fill: none;
stroke-dasharray: 4,4;
}
.lasso .origin {
fill: #3399FF;
fill-opacity: 0.5;
}
.not_possible {
fill: rgb(200,200,200);
}
.possible {
fill: #EC888C;
}
.selected {
fill: steelblue;
}
</style>