【问题标题】:D3JS: set colour gradient above a certain thresholdD3JS:将颜色渐变设置为高于某个阈值
【发布时间】:2021-04-20 11:22:38
【问题描述】:

我正在尝试这个D3 heatmap example。我想实现稍微复杂一点的着色逻辑 - 所有低于 30 的值都将简单地具有红色 fill,而高于 30 的值将遵循 Blues 颜色渐变。

Related question,但这会将恒定颜色应用于域的不同部分(例如红色表示值 0 到 50,蓝色表示 50 到 100...),而不是从恒定颜色翻转到颜色渐变。我可以按照这个答案,从原始 HTML 颜色代码手动实现一个红色域和一组足够大的蓝色,但我想要一个更优雅的解决方案,为我实现蓝色的比例,特别是因为我赢了不知道可能的范围输入的最大值是多少。

我尝试将attr("fill") 行修改为以下内容,但它不起作用 - 它正确应用红色,但非红色方块只是显示为黑色,这告诉我颜色渐变没有踢出于某种原因:

...
// Build color scale
var myColor = d3
    .scaleSequential()
    .interpolator(d3.interpolate)
    .domain([30, 100]); //Doesn't matter if I set the domain to [0.001, 100] or [30, 100]
...
.style("fill", function (d) { 
    if (d.value < 30) {
        return "red"
    } else {
        return myColor(d.value);
    };
})
...

【问题讨论】:

    标签: javascript d3.js


    【解决方案1】:

    您需要指定一个函数来在颜色之间进行插值。你已经指定了 d3.interpolate,但你没有给它任何值来进行插值,例如:

      d3.interpolate("steelblue","yellow")
    

    // Build color scale
    var myColor = d3
        .scaleSequential()
        .interpolator(d3.interpolate("steelblue","yellow"))
        .domain([30, 100]); 
    
    var data = d3.range(100)
    
    
    
    d3.select("body")
      .append("svg")
      .attr("height", 300)
      .selectAll("rect")
      .data(data)
      .enter()
      .append("rect")
      .attr("width", 20)
      .attr("height", 20)
      .attr("x", (d,i) => i%10 * 22)
      .attr("y", (d,i) => Math.floor(i/10) * 22)
      .style("fill", function (d) { 
        if (d < 30) {
            return "red"
        } else {
            return myColor(d);
        };
    })
    &lt;script src="https://cdnjs.cloudflare.com/ajax/libs/d3/5.7.0/d3.min.js"&gt;&lt;/script&gt;

    或者为不同的配色方案传递一个pre-built 插值器,例如:

     d3.interpolateBlues
    

    // Build color scale
    var myColor = d3
        .scaleSequential()
        .interpolator(d3.interpolateBlues)
        .domain([30, 100]); 
    
    var data = d3.range(100)
    
    
    
    d3.select("body")
      .append("svg")
      .attr("height", 300)
      .selectAll("rect")
      .data(data)
      .enter()
      .append("rect")
      .attr("width", 20)
      .attr("height", 20)
      .attr("x", (d,i) => i%10 * 22)
      .attr("y", (d,i) => Math.floor(i/10) * 22)
      .style("fill", function (d) { 
        if (d < 30) {
            return "red"
        } else {
            return myColor(d);
        };
    })
    &lt;script src="https://cdnjs.cloudflare.com/ajax/libs/d3/5.7.0/d3.min.js"&gt;&lt;/script&gt;

    您可以使用 d3.scaleSequential(interpoloator) 而不是使用 .interpoloator 方法指定插值器:

    // Build color scale
    var myColor = d3
        .scaleSequential(d3.interpolateBlues)
        .domain([30, 100]); 
    
    var data = d3.range(100)
    
    
    d3.select("body")
      .append("svg")
      .attr("height", 300)
      .selectAll("rect")
      .data(data)
      .enter()
      .append("rect")
      .attr("width", 20)
      .attr("height", 20)
      .attr("x", (d,i) => i%10 * 22)
      .attr("y", (d,i) => Math.floor(i/10) * 22)
      .style("fill", function (d) { 
        if (d < 30) {
            return "red"
        } else {
            return myColor(d);
        };
    })
    &lt;script src="https://cdnjs.cloudflare.com/ajax/libs/d3/5.7.0/d3.min.js"&gt;&lt;/script&gt;

    【讨论】:

      猜你喜欢
      • 2020-10-14
      • 2020-09-25
      • 2021-08-04
      • 1970-01-01
      • 2016-12-15
      • 2020-04-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多