【问题标题】:D3.js color the node circles with a function using spectrum.jsD3.js 使用 spec.js 使用函数为节点圆圈着色
【发布时间】:2016-11-15 11:40:59
【问题描述】:

对于每个节点,我都有一个圆圈,我在函数 ColorType(d) 的帮助下着色:

 node.append("circle")
     .attr("r", 20)
     .attr("y", -25)
     .style("fill", function(d) { return ColorType(d); })
     .style("stroke-width",0.5)
     .style("stroke",'black')
     .attr("opacity", "1");

我的ColorType函数是

function ColorType(d){
    for (var i = 0; i < TypesTab.length; i++) {
        if (d.type == TypesTab[i].type) { return ColorAction;}
    }   
}

在上面的函数中,d.type 是我节点的类型(见下面的 json 文件结构)。而TypesTab[i].type是我的每个类型分别存储在types中,检查节点类型是否与types中类型的值之一相同,如果是则应用为节点圈着色的ColorAction

这里是ColorAction 代码,它嵌入在每个颜色选择器容器中,该容器附加到类型中的每种类型,该列表插入到#filterColor html dom。所以每种类型都有一个颜色选择器容器,它应该只为自己的类型着色。

$(document).ready(function () {
    $.getJSON("databeta.json", function (obj) {
        $('#filterColor').data('types', obj.types.map(function (o) {
            // console.log(o.type);
            return o.type;
        })).append(obj.types.map(function (o) {
            return '<li>' + o.type + '<input class="color-picker" type="text"/></li>';
        }).join(''));

        var data = $('#filterColor').data('types'); //stores all types

        mynodes = obj.nodes;
        console.log("mynodes : ", mynodes); //array of all my nodes
        console.log("mynodes : ", mynodes[3].type); //reading the type of the fourth object in the nodes array

        $("#filterColor .color-picker").each(function(){
            $(this).spectrum({
                color: (function (m, s, c) {
                    return (c ? arguments.callee(m, s, c - 1) : '#') +
                        s[m.floor(m.random() * s.length)]
                })(Math, '0123456789ABCDEF', 5), //generate random initial color for each container
                preferredFormat: "rgb",
                showInput: true,
                showPalette: true,
                showAlpha: true,
                palette: [["red", "rgba(0, 255, 0, .5)", "rgb(0, 0, 255)"]],
                change: function(color) {
                    MyNode = d3.select("#node").selectAll(".entreprise").select("circle");
                    MyNode.style("fill", function(d) {
                        return d3.rgb(color.toHexString())
                    });
                    Coloration = d3.rgb(color.toHexString());
                }
            });
        });

    });
});

问题是当我在ColorType(d) 函数中硬编码类型时,

if (d.type == "school") { return ColorAction;}

它只成功地为 school 类型的节点着色。但是,如果我想让它动态化,以便使用颜色选择器分配给的类型为节点着色,它会失败,因为我无法与o.typeeach 建立连接。所以问题是将o.typeeach 传递给ColorAction 和/或ColorType(d),以便每个容器只为其自己类型的节点着色。

这是一次不成功的尝试,因为它没有考虑o.type,而是从包含所有@987654343 的全局变量(TypesTab) 中读取types 中的type 类型中的@s:

function ColorType(d){
    for (var i = 0; i < TypesTab.length; i++) {
        if (d.type == TypesTab[i].type) { return ColorAction;}
    }

}

下面是json结构:

{
    "nodes": [
        {
        "type": "school",
        "country": "US",
        "name": "saint peter's",
        "id": 1006
        },
        {
        "type": "univeristy",
        "country": "Brazil",
        "name": "saint joseph's",
        "id": 1007
        }        
        ...
    ],
    "links": [
            {
            "source": 1006,
            "target": 1007,
            "value": 20            
        },
       ...

    ],
    "types": [
                {
                    "type": "school",
                    "image": "image01"
                },
                {
                    "type": "univeristy",
                    "image": "image02"
                },
                {
                    "type": "company",
                    "image": "image03"
                },
                ...
            ]   
}

【问题讨论】:

  • 它可能不是答案,但通常你应该在比较中使用 === 而不是 ==。如果 == 还没有伤害到你,那它肯定会。为什么 - 因为 === 测试相等的值和相等的类型。有关解释,请参阅此 SO 帖子。 stackoverflow.com/questions/359494/…
  • 您发布了很多有用的信息,但在这种情况下,它掩盖了问题。你能把这个问题分解成一个简洁的例子吗?
  • 好的,所以你的 JSON 格式不正确,在 ` { "type": "company", "image ": "image03" },` JSON 标准不允许尾随逗号
  • 第 15 行的 JSON ... ',' 或 ']' 预期,得到 '.'
  • 另外你为什么使用 $.getJSON 为什么不使用 d3 的内置函数 d3.json() 来导入数据?事实上,您使用了很多 jQuery,而您最好只使用 d3.js 函数?

标签: javascript jquery json d3.js spectrumjs


【解决方案1】:

这就是我读取/导入 JSON 的方式。 for in 内部是基本的,因此您需要更改该部分以满足您的需要。

d3.json("data.json", function (error, data) { console.log(d3.values(data)); // do this as a check for (var d in data) { d.nodes = +d.nodes; d.links = +d.links; d.types = +d.types; } // svg can go here })

【讨论】:

  • 我收到TypeError: data.forEach is not a function
  • @jacky 好的,所以我的错误尝试使用 for in 而不是 forEach 循环。这也是一个很棒的free d3.js charts book
  • 又报错了,反正这不是直接解决问题的答案。你能提供这个问题的有效答案吗
猜你喜欢
  • 2013-01-23
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2022-12-06
  • 2012-08-01
  • 2012-11-13
  • 2021-12-26
  • 1970-01-01
相关资源
最近更新 更多