I am trying to add a black border to a line element of the d3js library. How can I do that ? I tried it with following Code:
Plunker:https://plnkr.co/edit/brSPxoRczQcULz3IxXQk?p=preview
CSS:
<style>
line.linecap {
border-style:dashed;
border-width:2px;
border-color: black;
}
</style>
JavaScript
<script>
var line = d3.select("body")
.append("svg")
.attr("width", 449)
.attr("height", 249);
line.append("line")
.style("stroke", "rgb(220, 220, 220)")
.attr("stroke-width", 94)
.classed('linecap', true)
.attr("x1", 139)
.attr("y1", 487)
.attr("x2", 139)
.attr("y2", 92);
</script>
SVG elements don't have border. Please check this list: https://www.w3.org/TR/SVG/propidx.html
That being said, the simple alternative is making another line, with the colour you want, a little bit thicker:
var line = d3.select("body")
.append("svg")
.attr("width", 500)
.attr("height", 300);
line.append("line")
.style("stroke", "red")
.attr("stroke-width", 96)
.classed('linecap', true)
.attr("x1", 139)
.attr("y1", 291)
.attr("x2", 139)
.attr("y2", 9);
line.append("line")
.style("stroke", "rgb(220, 220, 220)")
.attr("stroke-width", 94)
.classed('linecap', true)
.attr("x1", 139)
.attr("y1", 290)
.attr("x2", 139)
.attr("y2", 10);
<script src="https://cdnjs.cloudflare.com/ajax/libs/d3/3.4.11/d3.min.js"></script>
You can draw a rectangle (SVG rect) instead of a line, then border is available using stroke.
line.append("rect")
.style("stroke-width", "3")
.style("fill", "none")
.style("stroke", "rgb(220, 220, 220)")
.attr("x", 139)
.attr("y", 92)
.attr("width", 94)
.attr("height", 487 - 92 );
Updated plnkr
P.S. the line drawn gets outside of the svg boundaries, I didn't fix this problem (to do so, just adjust the coordinates as wanted).
Related
I want to have the d3 js chart with a different background rectangle based on some timestamps.
var orangeBack = svg
.append("rect")
.attr("x", margin.left + 0)
.attr("y", margin.top)
.attr("height", containerHeight - 120)
.attr("width", 200)
.style("stroke", bordercolor)
.attr("fill", "orange")
.attr("opacity", 0.2)
.style("stroke-width", border);
I have a d3 js chart created per below:
My code sandbox - https://codesandbox.io/s/quizzical-bhabha-4ullr?file=/src/TimelineChart.js
Right now I have given 200 in width but this will be my timestamp in x scale.
.attr("width", 200)
How I can use x scale for horizontally positioning the rectangle by timestamp ?
.attr("width", xScale()) // or XDomain something..
I tried to use scale e.g. but it's not working.
var orangeBack = svg.selectAll("rect")
.data(data)
.enter()
.append("rect")
//.attr("x", margin.left + 0)
.attr("x", function(d){return xScale(d.startTime)})
.attr("y", margin.top)
.attr("height", containerHeight - 120)
// .attr("width", 200)
.attr("width", function(d){return (xScale(d.startTime) - xScale("1568283720049"));})
.style("stroke", bordercolor)
.attr("fill", "orange")
.attr("opacity", 0.05)
.style("stroke-width", border);
Any reference will be helpful. Thanks..
I am trying to follow something like this.. How to add background shading to D3 line chart
This is how I am trying to achieve this. Let me know if anything better we can do.
var orangeBack = svg
.selectAll("rect")
.data(data)
.enter()
.append("rect")
.attr("x", margin.left)
// .attr("x", function (d) {
// return xScale(1568283720049);
// })
.attr("y", margin.top)
.attr("height", containerHeight - 120)
// .attr("width", 200)
.attr("width", function (d) {
return xScale(1568283720049) - xScale(1567851720049) + 10;
})
.style("stroke", bordercolor)
.attr("fill", "orange")
.attr("opacity", 0.05)
.style("stroke-width", border);
currently I have given the timestamp directly e.g. xScale(1568283720049) this can be done dynamically.
code sandbox - https://codesandbox.io/s/quizzical-bhabha-4ullr?file=/src/TimelineChart.js
Can someone explain to me how to use clipping mask on the circle arc.
To explain what I'm doing. I have a circle and on this circle I add an arc that can be moved around. Now I would like to add like a linear gradient to this circle from left to right. But the gradient should only be seen on the arc, not the circle itself. Also I found one solution here https://www.freshconsulting.com/d3-js-gradients-the-easy-way/ but it's not what I want to do as my gradient should always be the same, but only the arc should display it. For example like this:
This is how you would draw a masked circle with a gradient fill with d3.
const svg = d3.select("body")
.append("svg")
.attr("width", 500)
.attr("height", 500)
const defs = svg.append("defs")
const gradient = defs.append("linearGradient")
.attr("id", "exampleGradient")
gradient.append("stop")
.attr("offset", "10%")
.attr("stop-color", "white")
gradient.append("stop")
.attr("offset", "100%")
.attr("stop-color", "red")
const mask = defs.append("mask")
.attr("id", "donutMask")
mask.append("circle")
.attr("cx", 250)
.attr("cy", 250)
.attr("r", 150)
.attr("fill", "white")
mask.append("circle")
.attr("cx", 250)
.attr("cy", 250)
.attr("r", 120)
const circle = svg.append("circle")
.attr("r", 149)
.attr("cx", 250)
.attr("cy", 250)
.attr("stroke", "black")
.attr("mask", "url(#donutMask)")
.attr("fill", "url(#exampleGradient)")
<script src="https://cdnjs.cloudflare.com/ajax/libs/d3/3.4.11/d3.min.js"></script>
I am interested in learning how to create a transparent mask with d3.js.
http://jsfiddle.net/59bunh8u/35/
This is where I am up to - how would I create a subtraction mask on the red rectangle - also how could you style the red rectangle to take on more of a multiply style property?
$(document).ready(function() {
var el = $(".mask"); //selector
// Set the main elements for the series chart
var svg = d3.select(el[0]).append("svg")
.attr("class", "series")
.attr("width", "800px")
.attr("height", "500px")
.append("g")
.attr("transform", "translate(0,0)")
var rect = svg
.append("rect")
.attr("x", 0)
.attr("y", 0)
.attr("width", 500)
.attr("height", 500)
.style("fill", "red")
.style('opacity', 0.75)
var rect = svg
.append("circle").attr("cx", 250).attr("cy", 250).attr("r", 125).style("fill", "white");
});
You need an SVG mask. Feel free to play with it to tweak the parameters:
var mask = svgroot
.append("defs")
.append("mask")
.attr("id", "myMask");
mask.append("rect")
.attr("x", 0)
.attr("y", 0)
.attr("width", 500)
.attr("height", 500)
.style("fill", "white")
.style("opacity", 0.7);
mask.append("circle")
.attr("cx", 300)
.attr("cy", 300)
.attr("r", 100);
Modified example: http://jsfiddle.net/59bunh8u/40/
See also SVG clipPath to clip the *outer* content out
I am successful in getting crosshair in D3.js chart but issue is I am only getting vertical line, how do I add code for horizontal line as well?
Image of chart
JSFiddle code chart is not plotting in JSFiddle
Basically code to add vertical line crosshair is as below:-
var vertical = d3.select("body")
.append("div")
.attr("class", "remove")
.style("position", "absolute")
.style("z-index", "19")
.style("width", "1px")
.style("height", "450px")
.style("top", "47px")
.style("bottom", "1px")
.style("left", "8px")
.style("background", "#000");
Can I add horizontal crosshair as well same way?
P.S. also wanted a way to keep this vertical line only in chart area, but is coming in whole body, i.e. empty area next to chart in right and left.
Your approach is too complicated. This is simpler:
First, create a transparent rectangle to get the mouse movements:
var transpRect = svg.append("rect")
.attr("x", 0)
.attr("y", 0)
.attr("width", width)
.attr("height", height)
.attr("fill", "white")
.attr("opacity", 0);
Then, create the lines:
var verticalLine = svg.append("line")
.attr("opacity", 0)
.attr("y1", 0)
.attr("y2", height)
.attr("stroke", "black")
.attr("stroke-width", 1)
.attr("pointer-events", "none");
var horizontalLine = svg.append("line")
.attr("opacity", 0)
.attr("x1", 0)
.attr("x2", width)
.attr("stroke", "black")
.attr("stroke-width", 1)
.attr("pointer-events", "none");
Finally, position the lines on mousemove:
transpRect.on("mousemove", function(){
mouse = d3.mouse(this);
mousex = mouse[0];
mousey = mouse[1];
verticalLine.attr("x1", mousex).attr("x2", mousex).attr("opacity", 1);
horizontalLine.attr("y1", mousey).attr("y2", mousey).attr("opacity", 1)
}).on("mouseout", function(){
verticalLine.attr("opacity", 0);
horizontalLine.attr("opacity", 0);
});
Here is your fiddle: https://jsfiddle.net/xrf1ro1a/
PS: to avoid killing your tooltips, I put the mousemove both on the rectangle and on the svg as well, which has the undesirable effect of making the lines going outside the chart area. To avoid this, set pointer-events = none to the elements outside the chart area.
var w = 725;
var h = 500;
var padding = 20;
var svgcanvas = divElem.append("svg:svg")
.attr("width", w)
.attr("height", h);
The path that I wish to restrict the region to, but the element has disappeared
svgcanvas.append("svg:clipPath")
.attr("id", "clipper")
.attr("d","M -200,0 A200,200 0 0,0 500,0 L -200,0")
.attr("transform", "translate(220,400) scale(1, -1)")
.style("stroke-width", 2)
.style("stroke", "steelblue")
.style("fill", "yellow");
Do not wish the line to go beyond this path but the element has disappeared
var myLine = svgcanvas.append("svg:line")
.attr("x1", 40)
.attr("y1", 50)
.attr("x2", 450)
.attr("y2", 150)
.attr("clip-path", "url(#clipper)")
.style("stroke", "rgb(6,120,155)");
Do not wish the Circles to go beyond this path, but element has disappeared
var circle = svgcanvas.selectAll("circle").data(jsoncirclehigh);
circle.enter().append('circle')
.attr('opacity',0)
.attr("cursor","pointer")
.on("mouseover", function(){d3.select(this).style("fill", "red");})
.on("mouseout", function() {d3.select(this).style("fill", "orange");})
.attr("clip-path", "url(#clipper)")
.attr("cx", function(d) {return d.cx;})
.attr("cy", function(d) {return d.cy;});
Look at this example, I apply a ClipPath and a line with a setInterval:
demo