Color svg paths based on position along gradient in D3

时间:2016-08-31 18:27:05

标签: javascript d3.js svg

I'm working with a bunch of svg paths, and I'd like to color them based on their positions along a gradient. The image below is a sketch of my situation. Not the actual chart.

enter image description here

I've been digging around and it seems a mask might be a solution, but I can't seem to get it working.

Here is a snippet of my code:

var overlaySvg = svg.append('g')
    .attr('class', 'overlay-svg');

var defs = svg.append('defs');

var gradient = defs.append("linearGradient")
    .attr("id", "gradient")
    .attr('gradientUnits', 'userSpaceOnUse')
    .attr("x1", "0")
    .attr("y1", "0")
    .attr("x2", "100%")
    .attr("y2", "0%");

gradient.append("stop")
    .attr("offset", "10%")
    .attr("stop-color", "#0081c5");

gradient.append("stop")
    .attr("offset", "50%")
    .attr("stop-color", "#aaa");

gradient.append("stop")
    .attr("offset", "80%")
    .attr("stop-color", "#ed1c24");

var rect = mask.append('rect')
    .attr("width", width)
    .attr("height", height)

svg.selectAll('g.chart-container path')
  .attr('d', line)
  .classed('line', true)
  .attr('stroke', 'url(#gradient)')
  .attr("mask", "url(#gradient-mask)");

What am I doing wrong? Are there other alternatives? Would a filter be suitable for this situation? Thanks for any help!

UPDATE: Here is what my actual chart looks like: enter image description here

1 个答案:

答案 0 :(得分:2)

您不需要遮罩,只需使用渐变填充,其中渐变已使用gradientUnits =“userSpaceOnUse”定义。这样,渐变在用户空间中定义,并且通过适当的停止,您将获得正确的颜色以在每个x值处填充形状。

<svg width="800px" height="600px">
  <defs>
        <linearGradient id="grad1" x1="10" y1="0" x2="600" y2="0" gradientUnits="userSpaceOnUse">
      <stop offset="0" style="stop-color:rgb(0,0,255)" />
       <stop offset="50%" style="stop-color:rgb(255,255,255);stop-opacity:1" />         
      <stop offset="100%" style="stop-color:rgb(255,0,0);stop-opacity:1" />
    </linearGradient>
  </defs>
  

  <path d="M 0 0 q 200 200 0 400" stroke="url(#grad1)" fill="none" stroke-width="5px"/>
    <path d="M 100 0 q 200 200 0 400" stroke="url(#grad1)" fill="none" stroke-width="5px"/>
    <path d="M 200 0 q 200 200 0 400" stroke="url(#grad1)" fill="none" stroke-width="5px"/>
    <path d="M 300 0 q 200 200 0 400" stroke="url(#grad1)" fill="none" stroke-width="5px"/>
      <path d="M 400 0 q 200 200 0 400" stroke="url(#grad1)" fill="none" stroke-width="5px"/>
      <path d="M 500 0 q 200 200 0 400" stroke="url(#grad1)" fill="none" stroke-width="5px"/>
  
</svg>