admin管理员组文章数量:1353308
a lot of what I've read regarding d3.js and tooltips makes reference to having individual points on a graph.
instead, my graph graph is using one long path to render. I was wondering how I would apply mouseover methods to such a path, where I would then tie a tooltip div accordingly
/
svg.append("path")
.attr("class", "area")
.attr("clip-path", "url(#clip)")
.style("fill", "url(#gradient)");
a lot of what I've read regarding d3.js and tooltips makes reference to having individual points on a graph.
instead, my graph graph is using one long path to render. I was wondering how I would apply mouseover methods to such a path, where I would then tie a tooltip div accordingly
http://jsfiddle/ericps/xJ3Ke/6/
svg.append("path")
.attr("class", "area")
.attr("clip-path", "url(#clip)")
.style("fill", "url(#gradient)");
Share
Improve this question
asked Mar 5, 2013 at 23:11
CQMCQM
44.3k77 gold badges230 silver badges370 bronze badges
2
- Consider adding another layer of (non-visible) point objects that you can add mouse interactions to? – Josh Commented Mar 6, 2013 at 2:41
- @Josh I had begun experimenting with adding svg circles with opacity 0, but my initial try did not work – CQM Commented Mar 6, 2013 at 15:15
2 Answers
Reset to default 7You can set a layer of invisible objects representing each point you'd like to have a tooltip for, and add mouse interactions to those objects.
I've updated your jsfiddle with the following -
svg.selectAll("circle")
.data(data)
.enter().append("circle")
.attr("r", 5)
.style("fill","none")
.style("stroke","none")
.style("pointer-events","all")
.append("title")
.text(function(d) { return "Date: " + formatDate2(d.date) + " Value: " + d.value; });
This adds a circle element to each data point, and a title element to each of those circles. Note that the "pointer-events","all"
allows the mouse interactions even though the elements are invisible
full jsfiddle here: http://jsfiddle/xJ3Ke/9/
Below is a simple Tooltip class I used.
/**
* Tooltip helper.
*
* Copyright © 2014 Maciej Nux Jaros.
* License: CC-BY or MIT.
*/
function Tooltip() {
var _tooltip = this;
var _container = null;
/**
* Tootltip class name (use if you want more then one tooltip).
* @type String
*/
this.className = 'tooltip';
/**
* Width of the rect.
* @type String
*/
this.width = "100";
/**
* Height of the rect.
* @type String
*/
this.height = "20";
/**
* Tootltip source attribute.
* @type String
*/
this.textSourceAttrName = 'data-title';
/**
* Style of background rectangle.
* @type String
*/
this.rectStyle = "opacity:0.9;fill:#ffffff;fill-opacity:1;stroke:#ffcc00;stroke-width:3;";
/**
* Init tooltip elements and append to container.
*
* @param {D3} container D3 container element - e.g. main group (chart container).
*/
this.init = function(container) {
_container = container;
container.append("g")
.attr("class", _tooltip.className)
.attr("style", "display:none")
.append("rect")
.attr("style", _tooltip.rectStyle)
.attr("width", _tooltip.width)
.attr("height", _tooltip.height)
.attr("rx", "10")
.attr("ry", "10")
;
container.selectAll("." + _tooltip.className)
.append("text")
.attr("x", 5)
.attr("y", 10)
.attr("dy", ".35em")
;
};
/**
* Show tooltip (title) for given point
*
* run e.g. onmouseover
*
* @param {Element} point Circle element.
*/
this.show = function(point) {
var text = point.getAttribute(_tooltip.textSourceAttrName);
var x = parseFloat(point.getAttribute('cx')) + 10;
var y = parseFloat(point.getAttribute('cy')) + 5;
_container
.selectAll("." + _tooltip.className)
.attr("style", "")
.attr("transform", function() { return "translate(" + x + "," + y + ")"; })
;
_container
.selectAll("." + _tooltip.className + " text")
.text(function() { return text; })
;
};
/**
* Hide tooltip.
*
* run e.g. onmouseout
*/
this.hide = function() {
_container
.selectAll("." + _tooltip.className)
.attr("style", "display:none")
;
};
}
Usage (assuming you have countries
data series with date
on X and share
on Y):
// points
for (var i=0; i<countries.length; i++) {
var points = svg.selectAll(".points" + i)
.data(countries[i].values)
.enter()
.append("g")
.attr("class", ".points" + i)
;
// visible points
points
.append("circle")
.attr("class", "point")
.attr("stroke", "none")
.attr("fill", "black")
.attr("cx", function(d, i) { return x(d.date) })
.attr("cy", function(d, i) { return y(d.share) })
.attr("r", function(d, i) { return 2 })
;
// bigger (almost) invisible points for tooltip
points
.append("circle")
.attr("class", "blank-point")
.attr("style", "opacity:0.05;fill-opacity:1;")
.style("fill", function(d) { return color(countries[i].name); })
.attr("cx", function(d, i) { return x(d.date) })
.attr("cy", function(d, i) { return y(d.share) })
.attr("r", function(d, i) { return 6 })
.attr("data-title", function(d, i) { return formatDate(d.date) +'; '+ d.share })
.attr("onmouseover", "tooltip.show(this)")
.attr("onmouseout", "tooltip.hide()")
;
}
// prepare tooltip
tooltip.init(svg);
Note make sure you prepare tooltip after other things on the chart or it will not be visible. Also make sure you have enough room on the right of the chart (e.g. set right margin of the chart to 100 or more).
本文标签: javascriptd3js tooltips on pathStack Overflow
版权声明:本文标题:javascript - d3.js tooltips on path - Stack Overflow 内容由网友自发贡献,该文观点仅代表作者本人, 转载请联系作者并注明出处:http://www.betaflare.com/web/1743874995a2554165.html, 本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌抄袭侵权/违法违规的内容,一经查实,本站将立刻删除。
发表评论