vbernal
vbernal

Reputation: 681

Error: <path> attribute d: Expected number, "MNaN" - D3.js

I am trying to make a graph with D3.js and keep giving this error.

I saw that in Stack Overflow already has questions with this same error.

But the suggestions they gave I couldn't adapt to my code, I apologize.

That's the error show in my console:

enter image description here

        var codes = ["VENDAS_ANO", "VENDAS_ANT"];
        $('span.values').html(codes.join(', '));

        modalitySelected = document.querySelector('input[name=modality-selector]:checked').value;

        var data = null;
        var filtered_data = null;

        var margin = { top: 30, right: 20, bottom: 50, left: 50 };
        var width = 600 - margin.left - margin.right;
        var height = 300 - margin.top - margin.bottom;

        var month = ['Jan', 'Feb', 'Mar', 'Apr', 'May', 'Jun', 'Jul', 'Aug', 'Sep', 'Oct', 'Nov', 'Dec'];

        var x = d3.scaleTime().range([0, width]).domain(month);
        var y = d3.scaleLinear().range([height, 0]).domain([0, 65000])

        var color = d3.scaleOrdinal(d3.schemeCategory10);

        var xAxis = d3.axisBottom(x)
        var yAxis = d3.axisLeft(y);

        var svg = d3.select("#line-chart-container")
            .append("svg")
            .attr("width", width + margin.left + margin.right)
            .attr("height", height + margin.top + margin.bottom)
            .append("g")
            .attr("transform", "translate(" + margin.left + "," + margin.top + ")");

        var g = null;

        var line = d3.line()
            .x(function (d) {
                return x(d.month);
            })
            .y(function (d) {
                return y(d.value);
            });

        // get data   
        d3.queue()
            .defer(d3.json, 'http://www.json-generator.com/api/json/get/cejyrzNPzC?indent=2')
            .await(makeLineChart);

        function makeLineChart(error, data) {

            if (error) {
                console.log(error);
            }

            color.domain(d3.keys(data[0])
                .filter(function (key) {
                    return key == "CODE";
                })
            );

            createAxis();
            updateChart(data);

            // radio button change
            d3.selectAll("input[name='modality-selector']")
                .on("change", function () {
                    modalitySelected = document.querySelector('input[name=modality-selector]:checked').value;
                    clearChart();
                    createAxis();
                    updateChart(data);
                });

        } // end makeLineChart function

        /**
         * Create (if is the firts time) or updates the line chart, 
         * based on radio button selection.
         */
        function updateChart(data) {
            // filter data
            filtered_data = data.filter(function (d) {
                return d.MODALITY == modalitySelected && codes.includes(d.CODE);
            });

            // first we need to corerce the data into the right formats
            filtered_data = filtered_data.map(function (d) {
                return {
                    code: d.CODE,
                    month: d.month,
                    modality: d.MODALITY,
                    value: +d.VALUE
                };
            });

            filtered_data = d3.nest()
                .key(function (d) {
                    return d.code;
                })
                .entries(filtered_data);

            var codesArray = svg.selectAll(".code")
                .data(filtered_data, function (d) {
                    return d.key;
                })
                .enter()
                .append("g")
                .attr("class", "code");

            codesArray.append("path")
                .attr("class", "line")
                .attr("d", function (d) {
                    return line(d.values);
                })
                .style("stroke", function (d) {
                    return color(d.key);
                })
                .on("mouseover", function (a) {
                    // console.log(a);
                    codesArray.append("text")
                        .attr("class", "title-text")
                        .style("fill", "#000000")
                        .text(
                            a.key
                        )
                        .attr("text-anchor", "middle")
                        .attr("x", 200)
                        .attr("y", 20);
                })
                .on("mouseout", function (a) {
                    codesArray.select(".title-text").remove();
                })
        }

        function createAxis() {
            g = svg.append("g")
                .attr("class", "chartGroup")

            g.append("g")
                .attr("class", "axis x")
                .attr("transform", "translate(0, " + height + ")")
                .call(xAxis);

            g.append("g")
                .attr("class", "axis y")
                .call(yAxis);
        }

        /**
         * Remove old chart (axis and lines).
         */
        function clearChart() {
            d3.select(".chartGroup").remove();
            d3.selectAll(".code").remove();
        }
<!DOCTYPE html>
<html lang="en">

<head>
    <meta charset="utf-8">
    <script src="https://d3js.org/d3.v4.min.js" charset="utf-8"></script>
    <script src='https://ajax.googleapis.com/ajax/libs/jquery/3.3.1/jquery.min.js'></script>
    <script src="https://d3js.org/topojson.v2.min.js"></script>
    <title>Index 6</title>
</head>

<style>
    .line {
        fill: none;
        stroke-width: 1.5px;
    }
</style>

<body>
    <span style="display:block;margin-top: 10px;">Selected codes: <span class="values"></span></span><br>

    <div id="modality-selector-container">
        <form id="modality-selector">
            <input type="radio" name="modality-selector" id="rb-charneca" value="charneca" checked />
            <label for="rb-charneca">CHARNECA</label>
            <input type="radio" name="modality-selector" id="rb-joaoluis" value="joaoluis" />
            <label for="rb-joaoluis">JOÃO LUIS</label>
        </form>
    </div>

    <div id="line-chart-container"></div>

I am trying to do this exercise based on this code: http://embed.plnkr.co/snXgBYr0PxSvNDt1MbYI/

Upvotes: 0

Views: 4950

Answers (1)

pink_daemon
pink_daemon

Reputation: 374

I had very similar case to yours. The problem was, weirdly enough, in the wrong defined axis.

I had

var x = d3.scaleTime()
  .domain(d3.extent(data, function(d) { return d.dateRep; }))
  .range([ 0, width ]);

the dateRep was the original dataset variable name and not the transformed one. This was the transformation:

function(k){
   return {date : d3.timeParse("%d/%m/%Y")(k.dateRep), 
           value : k.amount}
    }

So I just changed it to

var x = d3.scaleTime()
  .domain(d3.extent(data, function(d) { return d.date; }))

And then It worked :) GL

Upvotes: 1

Related Questions