D3条形图。如何基于JSON数据设置自定义x和y轴?

时间:2018-08-13 14:52:03

标签: javascript html d3.js

例如,我有一个如下所示的JSON数据:

[
{
    "Letter": "A",
    "Freq": 20,
    "Font" : 123
},
{
    "Letter" : "B",
    "Freq": 12,
    "Font" : 123
},
{
    "Letter" : "C",
    "Freq": 47,
    "Font" : 123
},
{
    "Letter" : "D",
    "Freq": 34,
    "Font" : 123
}]

然后我有两种输入类型来设置轴。

enter image description here

如何绘制条形图以反映所选属性?

这是我到目前为止所拥有的。

    var xname = document.getElementById("xvalue").value;
    var yname = document.getElementById("yvalue").value;
    var jsObjects = document.getElementById("jstextarea").value;
    jsObjectsArray = eval(jsObjects);


    x.domain(jsObjectsArray.map(function (jsObjectsArray) {
        return Object.values(jsObjectsArray)[0];
    }));
    y.domain([0, d3.max(jsObjectsArray, function (jsObjectsArray) {
        return Object.values(jsObjectsArray)[1];
    })]);
    chart.select('.x.axis').transition().duration(300).call(xAxis);
    chart.select(".y.axis").transition().duration(300).call(yAxis);
    chart.data(jsObjectsArray);
    chart.select("#xAxistext").text(function (jsObjectsArray) {
        return xname || Object.keys(jsObjectsArray)[0];
    });

    chart.select("#yAxistext").text(function (jsObjectsArray) {
        return yname || Object.keys(jsObjectsArray)[1];
    });

    chart.selectAll("#sampledata").remove();
    chart.selectAll(".label").remove();
    var bars = chart.selectAll(".bar").data(jsObjectsArray);

    bars.enter().append("rect")
        .attr("x", function (jsObjectsArray) {
            return x(Object.values(jsObjectsArray)[0]);
        })
        .attr("y", function (jsObjectsArray) {
            return y(Object.values(jsObjectsArray)[1]);
        })
        .attr("height", function (jsObjectsArray) {
            return height - y(Object.values(jsObjectsArray)[1]);
        })
        .attr("width", x.rangeBand())
        .attr("class", "bar")
        .style("fill", function (jsObjectsArray, i) {
            return color(i);
        })
        .style("color", function () {
            return '#FFFFFF';
        })
        .on("mousemove", function (jsObjectsArray) {
            tooltip
                .style("left", d3.event.pageX - 50 + "px")
                .style("top", d3.event.pageY - 70 + "px")
                .style("display", "inline-block")
                .html((Object.values(jsObjectsArray)[0]) + "<br>" + (Object.values(jsObjectsArray)[1]));
        })
        .on("mouseout", function (jsObjectsArray) {
            tooltip.style("display", "none");
        })
        .attr("data-legend", function (jsObjectsArray) {
            return Object.values(jsObjectsArray)[0]
        });


    var texts = chart.selectAll(".label")
        .data(jsObjectsArray);

    texts.enter()
        .append("text")
        .attr("class", "label");

    texts.attr("x", (function (jsObjectsArray) {
        return x(Object.values(jsObjectsArray)[0]) + 76;
    }))
        .attr("y", (function (jsObjectsArray) {
            return y(Object.values(jsObjectsArray)[1]) - 20;
        }))
        .attr("dy", ".75em")
        .text(function (jsObjectsArray) {
            return Object.values(jsObjectsArray)[1];
        });

    chart.select("#dataLegend").call(d3.legend);

如您所见,我只是将其硬编码到JSON数组的第一和第二位置。如何选择要设置轴及其值的属性?

1 个答案:

答案 0 :(得分:1)

使用数据集之前,必须先对其进行转换

var xname = document.getElementById("xvalue").value;
var yname = document.getElementById("yvalue").value;
var jsObjects = document.getElementById("jstextarea").value;
jsObjectsArray = eval(jsObjects);
jsObjectsArray = jsObjectsArray.map( function (d) { return {key:d[xname], value:d[yname] }; });

之后,使用d作为函数参数,并使用d.keyd.value之类的。使用jsObjectsArray作为每个参数的名称会造成混淆。

bars.enter().append("rect")
    .attr("x", function (d) { return x(d.key); })
    .attr("y", function (d) { return y(d.value); })
    .attr("height", function (d) { return height - y(d.value); })