user1899082
user1899082

Reputation:

Scatterplot is not updating the number of circles

So here is all the code, in a gist, you can just save it as a HTML file and try it:

https://gist.github.com/babakinks/5407967

so look at the very beginning I am assuming some default number for scatter plot circles, and I fully draw the scatter plot

var numDataPoints = 50;

Then at the bottom, I have this listener that redraws the scatter plot with random new values, and it works..BUT I wanted to improve it such that I can type how many circles to draw in the text box and it should draw that many circles, not always the same 50 that it began with. BUT it doesn't listen to me! Yes it does redraw the circles with new random values BUT it is still drawing the same number of circles that it had at first . I don't know how to fix this part, I am pretty new to D3.js . The way I am expecting it to work is wrong?

    //On click, update with new data            
    d3.select("#drawbtn")
        .on("click", function() {

Upvotes: 1

Views: 2078

Answers (1)

Jonah
Jonah

Reputation: 16202

You just need to add enter() and remove() selections:

<!DOCTYPE html>
<html lang="en">
  <head>
        <meta charset="utf-8">
        <title>yguyghggjkgh</title>
        <script src="http://d3js.org/d3.v3.min.js"></script>
        <style type="text/css">

            .axis path,
            .axis line {
                fill: none;
                stroke: black;
                shape-rendering: crispEdges;
            }

            .axis text {
                font-family: sans-serif;
                font-size: 11px;
            }

        </style>
    </head>
    <body>

        <div>
          <input type="text" id="count" name="howmany">
          <input type="button" id="drawbtn" value="draw">
        </div>


        <script type="text/javascript">

            //Width and height
            var w = 500;
            var h = 300;
            var padding = 30;

            //Dynamic, random dataset
            var dataset = [];                                           //Initialize empty array
            var numDataPoints = 50;
            console.log("so we are here.")                                      
            var maxRange = Math.random() * 1000;                        //Max range of new values
            for (var i = 0; i < numDataPoints; i++) {                   //Loop numDataPoints times
                var newNumber1 = Math.floor(Math.random() * maxRange);  //New random integer
                var newNumber2 = Math.floor(Math.random() * maxRange);  //New random integer
                dataset.push([newNumber1, newNumber2]);                 //Add new number to array
            }

            //Create scale functions
            var xScale = d3.scale.linear()
                                 .domain([0, d3.max(dataset, function(d) { return d[0]; })])
                                 .range([padding, w - padding * 2]);

            var yScale = d3.scale.linear()
                                 .domain([0, d3.max(dataset, function(d) { return d[1]; })])
                                 .range([h - padding, padding]);

            //Define X axis
            var xAxis = d3.svg.axis()
                              .scale(xScale)
                              .orient("bottom")
                              .ticks(5);

            //Define Y axis
            var yAxis = d3.svg.axis()
                              .scale(yScale)
                              .orient("left")
                              .ticks(5);

            //Create SVG element
            var svg = d3.select("body")
                        .append("svg")
                        .attr("width", w)
                        .attr("height", h);

            //Create circles
            svg.selectAll("circle")
               .data(dataset)
               .enter()
               .append("circle")
               .attr("cx", function(d) {
                    return xScale(d[0]);
               })
               .attr("cy", function(d) {
                    return yScale(d[1]);
               })
               .attr("r", 2);

            //Create X axis
            svg.append("g")
                .attr("class", "axis")
                .attr("transform", "translate(0," + (h - padding) + ")")
                .call(xAxis);

            //Create Y axis
            svg.append("g")
                .attr("class", "axis")
                .attr("transform", "translate(" + padding + ",0)")
                .call(yAxis);


            //On click, update with new data            
            d3.select("#drawbtn")
                .on("click", function() {
                    //New values for dataset
                    var numValues = parseInt(document.getElementById('count').value, 10);
                    console.log(numValues);
                    var maxRange = Math.random() * 1000;                        
                    dataset = [];                                               //Initialize empty array
                    for (var i = 0; i < numValues; i++) {                       //Loop numValues times
                        var newNumber1 = Math.floor(Math.random() * maxRange);  //New random integer
                        var newNumber2 = Math.floor(Math.random() * maxRange);  //New random integer
                        dataset.push([newNumber1, newNumber2]);                 //Add new number to array
                    }

                    //Update scale domains
                    xScale.domain([0, d3.max(dataset, function(d) { return d[0]; })]);
                    yScale.domain([0, d3.max(dataset, function(d) { return d[1]; })]);

                    //Update all circles
                    svg.selectAll("circle")
                       .data(dataset)
                       .transition()
                       .duration(1000)
                       .attr("cx", function(d) {
                            return xScale(d[0]);
                       })
                       .attr("cy", function(d) {
                            return yScale(d[1]);
                       });

                    //Enter new circles
                    svg.selectAll("circle")
                       .data(dataset)
             .enter()
             .append("circle")
                       .attr("cx", function(d) {
                            return xScale(d[0]);
                       })
                       .attr("cy", function(d) {
                            return yScale(d[1]);
                       })
             .attr("r", 2);

                    // Remove old
                    svg.selectAll("circle")
                       .data(dataset)
             .exit()
             .remove()

                });


        </script>
    </body>
</html>

Upvotes: 3

Related Questions