javascript - 在动态创建的 div 上绘制多个 NVD3.js 图表的问题

标签 javascript css d3.js nvd3.js

我应该根据具有以下结构的 JSON 文档生成报告:

tables:
[
  {
    <some descriptors of the dataset>, 
    series: 
    [
      key: ...,
      values: 
        [
          { label: ..., value: ... },
          ...
        ]
    ]
  },
  ...
]

JSON 数组中可以有任意数量的表,具有任意系列。当然,每个系列都包含具有不同值的同一组值。对于每个表,我必须用给定的数据和多条形图绘制一个表。我选择 NVD3.js 作为我的图表库。

由于我对 JavaScript 不是很有经验,所以我决定谨慎行事,严格按照 NVD3.js 示例,以尽可能最古老和愚蠢的方式生成我需要的 div 和对象。一旦我对 JS 感到更自在,我就会实现模板等。这是我的 JavaScript 代码的简化版本。我知道这很可怕,所以请不要评判我。

var report_data = <stupid way of getting data, will use AJAX later>;

var my_div = document.getElementById('show-report');

report_data.tables.forEach(
    function(table)
    {
        var newDiv = document.createElement('div');
        newDiv.id = 'report_' + table.name;

        var newHeader = document.createElement('h1');
        newHeader.textContent = table.name;
        newDiv.appendChild(newHeader);

                    // Generate style element for chart
        var newStyle = document.createElement('style');
        newStyle.textContent = '#' + table.name + '_chart svg {height: 500px;}';
        newDiv.appendChild(newStyle);

                    // Generate <div><svg /></div> where chart will be placed
        var chartDiv = document.createElement('div');
        chartDiv.id = table.name + '_chart';
        var svgEl = document.createElement('svg');
        chartDiv.appendChild(svgEl);
        newDiv.appendChild(chartDiv);

        // Here I write the table and append it to the main div. Omitted because of intense shame.

        my_div.appendChild(newDiv);

        //Draw chart
        nv.addGraph(
        function() 
        {
            var chart = nv.models.multiBarHorizontalChart()
            .x(function(d) { return d.label })
            .y(function(d) { return d.value })
            .margin({top: 30, right: 20, bottom: 50, left: 175})
            .tooltips(true)
            .showControls(true);

            chart.yAxis
            .tickFormat(d3.format(',.2f'));

            d3.select('#'+ table.name +'_chart svg')
            .datum(table.series)
            .transition().duration(250)
            .call(chart);

            nv.utils.windowResize(chart.update);

            return chart;
        }
        );
    }
);

所以,代码很糟糕,但它可以工作……有点。事情是这样的:它尝试绘制每个图表并将其放入其 div 中,但每个图表仅以没有样式的纯文本显示。参见 this Imgur album .如果我用我的一个表的名称“硬编码”一个 div,它会在其中毫无障碍地绘制图表。在我看来,新创建的 div 似乎没有应用 NVD3.js CSS 文件。我什至不知道这是否可能,因为我对 CSS 的了解甚至比对 JavaScript 的了解还要少。

有没有人尝试过这样的事情或者有人知道是什么导致了这种行为?

最佳答案

我刚遇到这个问题,在 GitHub 上四处看看后我 found the problem .

you cant create SVG elements using document.createElement, you have to use document.createElementNS and specify the xml namespace for SVG, or just use d3´s append method: d3.select(...).append("svg")

我的问题特别涉及 jQuery,这导致我使用以下方法生成 SVG 元素:

var $svg = d3.select($jqElement[0]).append("svg")

对于非 jQuery 用户,可以将常规 DOM 元素传递到 d3.select 中。在示例中,调用了 $jqElement[0] 以获取 jQuery 对象的 DOM 版本。

关于javascript - 在动态创建的 div 上绘制多个 NVD3.js 图表的问题,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/22569367/

相关文章:

html - 意外的 <body> body 行为,因为它被 child 的 margin-top 向下推

javascript - IE8 对于最新的 jquery 没有圆 Angular

javascript - 一个 HTML 页面中不能有多个图表 - d3

d3.js:为什么 d3.geo.path() 给出 NaN?

javascript - 在 AngularJS 中使用单例模式是一种不好的做法吗?

javascript - 从除当前元素之外的所有相同元素中删除数据属性

javascript - 全局计数器变量

javascript - Wallabyjs - 不断收到 TypeError : 'undefined'

javascript - 具有显示/隐藏 div 功能的可点击图像映射

javascript - D3 : am I using scale. invert() 错误?