<!DOCTYPE html>
<meta charset="utf-8">
<html>

  <head>
    <script charset="utf-8" src="//cdnjs.cloudflare.com/ajax/libs/d3/3.3.11/d3.min.js"></script>
    <link rel="stylesheet" href="style.css" />
  </head>

  <body>
    <h1>D3 Heatmap</h1>
    <div id="master-slave"></div>
    <div id="drqs"></div>
    <script src="script.js"></script>
    <script>
      heatMap('centralized.csv', '#master-slave');
      heatMap('drqs.csv', '#drqs');
    </script>
  </body>

</html>
function heatMap(csvFile, elementID) {
  // Constants
  var margin = {
    top: 80,
    right: 0,
    bottom: 10,
    left: 80
  };
  width = 520;
  height = 520;


  // Create and attach top level svg
  var svg = d3.select(elementID)
    .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 + ")");

  svg.append("text")
    .attr("class", "chartTitle")
    .attr("text-anchor", "middle")
    .attr("transform", "translate(" + width / 2 + "," + -margin.top / 2 + ")")
    .text("Receiving Rank");

  svg.append("text")
    .attr("class", "chartTitle")
    .attr("text-anchor", "middle")
    .attr("transform", "translate(" + -margin.left / 2 + "," + height / 2 + ")rotate(-90)")
    .text("Sending Rank");

  var legendHeight = 20;
  var legendWidth = width + margin.left + margin.right;
  var legendId = 'legendGradient';

  var legend = d3.select(elementID).append("div").append("svg:svg")
    .attr("width", legendWidth)
    .attr("height", legendHeight);


  var gradientID = elementID + "-gradient";
  if (gradientID.substring(0, 1) == '#') {
    gradientID = gradientID.substr(1, gradientID.length);
  }
  console.log(gradientID);
  var gradient = svg.append("svg:defs")
    .append("svg:linearGradient")
    .attr("id", gradientID)
    .attr("x1", "0%")
    .attr("y1", "0%")
    .attr("x2", "100%")
    .attr("y2", "0%")
    .attr("spreadMethod", "pad");

  gradient.append("svg:stop")
    .attr("offset", "0%")
    .attr("stop-color", "#5ff4ff")
    .attr("stop-opacity", 1);

  gradient.append("svg:stop")
    .attr("offset", "100%")
    .attr("stop-color", "#c42bd4")
    .attr("stop-opacity", 1);


  legend.append("svg:rect")
    .attr("width", legendWidth)
    .attr("height", legendHeight)
    .style("fill", "url(#" + gradientID + ")")
    .attr("transform", "translate(" + margin.left + ",0)");

  var cellValue = d3.select('body').append("div")
    .style("position", "absolute")
    .style("opacity", 1e-6)
    .attr("class", "tooltip");

  // Map the ranks to a bands
  var x = d3.scale.ordinal().rangeBands([0, width]);

  var z = d3.scale.linear().range([0, 1]).clamp(true);

  var c = d3.scale.linear().range(["#5ff4ff", "#c42bd4"]);

  function formatBytes(bytes) {
    var sizes = ['Bytes', 'KB', 'MB', 'GB', 'TB'];
    if (bytes == 0) return '0 Bytes';
    var i = parseInt(Math.floor(Math.log(bytes) / Math.log(1024)));
    return Math.round(bytes / Math.pow(1024, i), 2) + ' ' + sizes[i];
  }

  // Build a space delimited parser and parse the CSV
  var parser = d3.dsv(" ", "text/plain")
  var points = parser(csvFile)
    .row(function(d) {
      return {
        Sender: +d.Sender,
        Receiver: +d.Receiver,
        Bytes: +d.Bytes
      };
    })
    .get(function(error, rows) {
      var rankCount = Math.sqrt(rows.length);

      var xScale = d3.scale.linear()
        .domain([0, rankCount])
        .range([0, width]);

      var yScale = d3.scale.linear()
        .domain([0, rankCount])
        .range([height, 0]);

      var matrix = [];
      var row_idx = 0;
      for (var i = 0; i < rankCount; i++) {
        matrix[i] = [];
        for (var j = 0; j < rankCount; j++) {
          matrix[i][j] = [];
        }
      }
      rows.forEach(function(row, i) {
        matrix[row.Sender][row.Receiver] = {
          "sender": row.Sender,
          "receiver": row.Receiver,
          "bytes": row.Bytes
        };
      });

      // Apply color gradient domain
      var extent = d3.extent(rows, function(d) {
        return d.Bytes;
      });
      var min = extent[0];
      var max = extent[1];
      c.domain([min, (min + max) / 2, max]);

      legend.append("text")
        .attr("class", "legendText")
        .attr("text-anchor", "end")
        .attr("y", legendHeight - 5)
        .attr("x", legendWidth - margin.right - 10)
        .text(formatBytes(max));

      legend.append("text")
        .attr("class", "legendText")
        .attr("y", legendHeight - 5)
        .attr("x", margin.left + 10)
        .text(formatBytes(min));


      // Apply the rankCount as the domain for x
      x.domain(d3.range(rankCount));

      svg.append("rect")
        .attr("class", "background")
        .attr("width", width)
        .attr("height", height)
        .style("fill", "#eee");

      var row = svg.selectAll(".row")
        .data(matrix)
        .enter().append("g")
        .attr("class", "row")
        .attr("transform", function(d, i) {
          return "translate(0," + x(i) + ")";
        })
        .each(rowFunc);

      function rowFunc(rowObject) {
        var cell = d3.select(this).selectAll(".cell")
          .data(rowObject)
          .enter().append("rect")
          .attr("class", "cell")
          .attr("x", function(d, i) {
            return x(i);
          })
          .attr("width", x.rangeBand())
          .attr("height", x.rangeBand())
          .style("fill-opacity", function(d) {
            return z(d.bytes);
          })
          .style("fill", function(d) {
            return c(d.bytes);
          })
          .on("mousemove", mouseMove)
          .on("mouseover", mouseOver)
          .on("mouseout", mouseOut);
      }

      function mouseOver(evt) {
        cellValue.transition()
          .duration(300)
          .style('opacity', 1);
      }

      function mouseOut(evt) {
        cellValue.transition()
          .duration(300)
          .style('opacity', 1e-6);
        d3.selectAll(".row text").classed("active", false);
        d3.selectAll(".column text").classed("active", false);
      }

      function mouseMove(evt) {
        cellValue.text("Rank " + evt.sender + " to " + evt.receiver + ": " + formatBytes(evt.bytes));
        cellValue.style("left", (d3.event.pageX) + "px");
        cellValue.style("top", (d3.event.pageY) + "px");
        d3.selectAll(".row text").classed("active", function(d, i) {
          return evt.sender == i;
        });
        d3.selectAll(".column text").classed("active", function(d, i) {
          return evt.receiver == i;
        })
      }

      row.append("line")
        .attr("x2", width)
        .attr("stroke", "#fff");

      row.append("text")
        .attr("x", -6)
        .attr("y", x.rangeBand() / 2)
        .attr("dy", ".32em")
        .attr("text-anchor", "end")
        .text(function(d, i) {
          return i;
        });

      var column = svg.selectAll(".column")
        .data(matrix)
        .enter().append("g")
        .attr("class", "column")
        .attr("transform", function(d, i) {
          return "translate(" + x(i) + ")rotate(-90)";
        });

      column.append("line")
        .attr("x1", -width)
        .attr("stroke", "#fff");

      column.append("text")
        .attr("x", 6)
        .attr("y", x.rangeBand() / 2)
        .attr("dy", ".32em")
        .attr("text-anchor", "start")
        .text(function(d, i) {
          return i;
        });
    });

}
/* Styles go here */

.active {
  fill: red;
}

.tooltip {
          position: absolute;
          text-align: center;
          width: 100px;
          color:white;
          padding: 8px;
          font: 10px sans-serif;
          background: black;
          border: solid 1px #aaa;
          pointer-events: none;
}
Sender Receiver Bytes
0 0 0
0 1 1416764092
0 2 4098253320
0 3 2106916386
0 4 1262617412
0 5 1059002706
0 6 891019678
0 7 719843912
0 8 794784178
0 9 705375450
0 10 633794346
0 11 545948094
0 12 557540490
0 13 540263648
0 14 498643870
0 15 511809624
0 16 554348884
0 17 550255516
0 18 523935306
0 19 484032112
0 20 507731712
0 21 523864308
0 22 514341244
0 23 475911560
0 24 495823644
0 25 486259456
0 26 471343942
0 27 446707372
0 28 536274564
0 29 569101028
0 30 500390494
0 31 534429930
1 0 23106442962
1 1 0
1 2 0
1 3 0
1 4 0
1 5 0
1 6 0
1 7 0
1 8 0
1 9 0
1 10 0
1 11 0
1 12 0
1 13 0
1 14 0
1 15 0
1 16 0
1 17 0
1 18 0
1 19 0
1 20 0
1 21 0
1 22 0
1 23 0
1 24 0
1 25 0
1 26 0
1 27 0
1 28 0
1 29 0
1 30 0
1 31 0
2 0 610495002
2 1 0
2 2 0
2 3 0
2 4 0
2 5 0
2 6 0
2 7 0
2 8 0
2 9 0
2 10 0
2 11 0
2 12 0
2 13 0
2 14 0
2 15 0
2 16 0
2 17 0
2 18 0
2 19 0
2 20 0
2 21 0
2 22 0
2 23 0
2 24 0
2 25 0
2 26 0
2 27 0
2 28 0
2 29 0
2 30 0
2 31 0
3 0 160505722
3 1 0
3 2 0
3 3 0
3 4 0
3 5 0
3 6 0
3 7 0
3 8 0
3 9 0
3 10 0
3 11 0
3 12 0
3 13 0
3 14 0
3 15 0
3 16 0
3 17 0
3 18 0
3 19 0
3 20 0
3 21 0
3 22 0
3 23 0
3 24 0
3 25 0
3 26 0
3 27 0
3 28 0
3 29 0
3 30 0
3 31 0
4 0 70361538
4 1 0
4 2 0
4 3 0
4 4 0
4 5 0
4 6 0
4 7 0
4 8 0
4 9 0
4 10 0
4 11 0
4 12 0
4 13 0
4 14 0
4 15 0
4 16 0
4 17 0
4 18 0
4 19 0
4 20 0
4 21 0
4 22 0
4 23 0
4 24 0
4 25 0
4 26 0
4 27 0
4 28 0
4 29 0
4 30 0
4 31 0
5 0 56677892
5 1 0
5 2 0
5 3 0
5 4 0
5 5 0
5 6 0
5 7 0
5 8 0
5 9 0
5 10 0
5 11 0
5 12 0
5 13 0
5 14 0
5 15 0
5 16 0
5 17 0
5 18 0
5 19 0
5 20 0
5 21 0
5 22 0
5 23 0
5 24 0
5 25 0
5 26 0
5 27 0
5 28 0
5 29 0
5 30 0
5 31 0
6 0 63926386
6 1 0
6 2 0
6 3 0
6 4 0
6 5 0
6 6 0
6 7 0
6 8 0
6 9 0
6 10 0
6 11 0
6 12 0
6 13 0
6 14 0
6 15 0
6 16 0
6 17 0
6 18 0
6 19 0
6 20 0
6 21 0
6 22 0
6 23 0
6 24 0
6 25 0
6 26 0
6 27 0
6 28 0
6 29 0
6 30 0
6 31 0
7 0 31849816
7 1 0
7 2 0
7 3 0
7 4 0
7 5 0
7 6 0
7 7 0
7 8 0
7 9 0
7 10 0
7 11 0
7 12 0
7 13 0
7 14 0
7 15 0
7 16 0
7 17 0
7 18 0
7 19 0
7 20 0
7 21 0
7 22 0
7 23 0
7 24 0
7 25 0
7 26 0
7 27 0
7 28 0
7 29 0
7 30 0
7 31 0
8 0 32826998
8 1 0
8 2 0
8 3 0
8 4 0
8 5 0
8 6 0
8 7 0
8 8 0
8 9 0
8 10 0
8 11 0
8 12 0
8 13 0
8 14 0
8 15 0
8 16 0
8 17 0
8 18 0
8 19 0
8 20 0
8 21 0
8 22 0
8 23 0
8 24 0
8 25 0
8 26 0
8 27 0
8 28 0
8 29 0
8 30 0
8 31 0
9 0 30718716
9 1 0
9 2 0
9 3 0
9 4 0
9 5 0
9 6 0
9 7 0
9 8 0
9 9 0
9 10 0
9 11 0
9 12 0
9 13 0
9 14 0
9 15 0
9 16 0
9 17 0
9 18 0
9 19 0
9 20 0
9 21 0
9 22 0
9 23 0
9 24 0
9 25 0
9 26 0
9 27 0
9 28 0
9 29 0
9 30 0
9 31 0
10 0 19137146
10 1 0
10 2 0
10 3 0
10 4 0
10 5 0
10 6 0
10 7 0
10 8 0
10 9 0
10 10 0
10 11 0
10 12 0
10 13 0
10 14 0
10 15 0
10 16 0
10 17 0
10 18 0
10 19 0
10 20 0
10 21 0
10 22 0
10 23 0
10 24 0
10 25 0
10 26 0
10 27 0
10 28 0
10 29 0
10 30 0
10 31 0
11 0 15596010
11 1 0
11 2 0
11 3 0
11 4 0
11 5 0
11 6 0
11 7 0
11 8 0
11 9 0
11 10 0
11 11 0
11 12 0
11 13 0
11 14 0
11 15 0
11 16 0
11 17 0
11 18 0
11 19 0
11 20 0
11 21 0
11 22 0
11 23 0
11 24 0
11 25 0
11 26 0
11 27 0
11 28 0
11 29 0
11 30 0
11 31 0
12 0 20192340
12 1 0
12 2 0
12 3 0
12 4 0
12 5 0
12 6 0
12 7 0
12 8 0
12 9 0
12 10 0
12 11 0
12 12 0
12 13 0
12 14 0
12 15 0
12 16 0
12 17 0
12 18 0
12 19 0
12 20 0
12 21 0
12 22 0
12 23 0
12 24 0
12 25 0
12 26 0
12 27 0
12 28 0
12 29 0
12 30 0
12 31 0
13 0 10711718
13 1 0
13 2 0
13 3 0
13 4 0
13 5 0
13 6 0
13 7 0
13 8 0
13 9 0
13 10 0
13 11 0
13 12 0
13 13 0
13 14 0
13 15 0
13 16 0
13 17 0
13 18 0
13 19 0
13 20 0
13 21 0
13 22 0
13 23 0
13 24 0
13 25 0
13 26 0
13 27 0
13 28 0
13 29 0
13 30 0
13 31 0
14 0 13247168
14 1 0
14 2 0
14 3 0
14 4 0
14 5 0
14 6 0
14 7 0
14 8 0
14 9 0
14 10 0
14 11 0
14 12 0
14 13 0
14 14 0
14 15 0
14 16 0
14 17 0
14 18 0
14 19 0
14 20 0
14 21 0
14 22 0
14 23 0
14 24 0
14 25 0
14 26 0
14 27 0
14 28 0
14 29 0
14 30 0
14 31 0
15 0 18247100
15 1 0
15 2 0
15 3 0
15 4 0
15 5 0
15 6 0
15 7 0
15 8 0
15 9 0
15 10 0
15 11 0
15 12 0
15 13 0
15 14 0
15 15 0
15 16 0
15 17 0
15 18 0
15 19 0
15 20 0
15 21 0
15 22 0
15 23 0
15 24 0
15 25 0
15 26 0
15 27 0
15 28 0
15 29 0
15 30 0
15 31 0
16 0 18990280
16 1 0
16 2 0
16 3 0
16 4 0
16 5 0
16 6 0
16 7 0
16 8 0
16 9 0
16 10 0
16 11 0
16 12 0
16 13 0
16 14 0
16 15 0
16 16 0
16 17 0
16 18 0
16 19 0
16 20 0
16 21 0
16 22 0
16 23 0
16 24 0
16 25 0
16 26 0
16 27 0
16 28 0
16 29 0
16 30 0
16 31 0
17 0 12903490
17 1 0
17 2 0
17 3 0
17 4 0
17 5 0
17 6 0
17 7 0
17 8 0
17 9 0
17 10 0
17 11 0
17 12 0
17 13 0
17 14 0
17 15 0
17 16 0
17 17 0
17 18 0
17 19 0
17 20 0
17 21 0
17 22 0
17 23 0
17 24 0
17 25 0
17 26 0
17 27 0
17 28 0
17 29 0
17 30 0
17 31 0
18 0 17275910
18 1 0
18 2 0
18 3 0
18 4 0
18 5 0
18 6 0
18 7 0
18 8 0
18 9 0
18 10 0
18 11 0
18 12 0
18 13 0
18 14 0
18 15 0
18 16 0
18 17 0
18 18 0
18 19 0
18 20 0
18 21 0
18 22 0
18 23 0
18 24 0
18 25 0
18 26 0
18 27 0
18 28 0
18 29 0
18 30 0
18 31 0
19 0 9624686
19 1 0
19 2 0
19 3 0
19 4 0
19 5 0
19 6 0
19 7 0
19 8 0
19 9 0
19 10 0
19 11 0
19 12 0
19 13 0
19 14 0
19 15 0
19 16 0
19 17 0
19 18 0
19 19 0
19 20 0
19 21 0
19 22 0
19 23 0
19 24 0
19 25 0
19 26 0
19 27 0
19 28 0
19 29 0
19 30 0
19 31 0
20 0 19176028
20 1 0
20 2 0
20 3 0
20 4 0
20 5 0
20 6 0
20 7 0
20 8 0
20 9 0
20 10 0
20 11 0
20 12 0
20 13 0
20 14 0
20 15 0
20 16 0
20 17 0
20 18 0
20 19 0
20 20 0
20 21 0
20 22 0
20 23 0
20 24 0
20 25 0
20 26 0
20 27 0
20 28 0
20 29 0
20 30 0
20 31 0
21 0 14517602
21 1 0
21 2 0
21 3 0
21 4 0
21 5 0
21 6 0
21 7 0
21 8 0
21 9 0
21 10 0
21 11 0
21 12 0
21 13 0
21 14 0
21 15 0
21 16 0
21 17 0
21 18 0
21 19 0
21 20 0
21 21 0
21 22 0
21 23 0
21 24 0
21 25 0
21 26 0
21 27 0
21 28 0
21 29 0
21 30 0
21 31 0
22 0 25347724
22 1 0
22 2 0
22 3 0
22 4 0
22 5 0
22 6 0
22 7 0
22 8 0
22 9 0
22 10 0
22 11 0
22 12 0
22 13 0
22 14 0
22 15 0
22 16 0
22 17 0
22 18 0
22 19 0
22 20 0
22 21 0
22 22 0
22 23 0
22 24 0
22 25 0
22 26 0
22 27 0
22 28 0
22 29 0
22 30 0
22 31 0
23 0 11748116
23 1 0
23 2 0
23 3 0
23 4 0
23 5 0
23 6 0
23 7 0
23 8 0
23 9 0
23 10 0
23 11 0
23 12 0
23 13 0
23 14 0
23 15 0
23 16 0
23 17 0
23 18 0
23 19 0
23 20 0
23 21 0
23 22 0
23 23 0
23 24 0
23 25 0
23 26 0
23 27 0
23 28 0
23 29 0
23 30 0
23 31 0
24 0 16868502
24 1 0
24 2 0
24 3 0
24 4 0
24 5 0
24 6 0
24 7 0
24 8 0
24 9 0
24 10 0
24 11 0
24 12 0
24 13 0
24 14 0
24 15 0
24 16 0
24 17 0
24 18 0
24 19 0
24 20 0
24 21 0
24 22 0
24 23 0
24 24 0
24 25 0
24 26 0
24 27 0
24 28 0
24 29 0
24 30 0
24 31 0
25 0 13369354
25 1 0
25 2 0
25 3 0
25 4 0
25 5 0
25 6 0
25 7 0
25 8 0
25 9 0
25 10 0
25 11 0
25 12 0
25 13 0
25 14 0
25 15 0
25 16 0
25 17 0
25 18 0
25 19 0
25 20 0
25 21 0
25 22 0
25 23 0
25 24 0
25 25 0
25 26 0
25 27 0
25 28 0
25 29 0
25 30 0
25 31 0
26 0 13200128
26 1 0
26 2 0
26 3 0
26 4 0
26 5 0
26 6 0
26 7 0
26 8 0
26 9 0
26 10 0
26 11 0
26 12 0
26 13 0
26 14 0
26 15 0
26 16 0
26 17 0
26 18 0
26 19 0
26 20 0
26 21 0
26 22 0
26 23 0
26 24 0
26 25 0
26 26 0
26 27 0
26 28 0
26 29 0
26 30 0
26 31 0
27 0 9923536
27 1 0
27 2 0
27 3 0
27 4 0
27 5 0
27 6 0
27 7 0
27 8 0
27 9 0
27 10 0
27 11 0
27 12 0
27 13 0
27 14 0
27 15 0
27 16 0
27 17 0
27 18 0
27 19 0
27 20 0
27 21 0
27 22 0
27 23 0
27 24 0
27 25 0
27 26 0
27 27 0
27 28 0
27 29 0
27 30 0
27 31 0
28 0 29637524
28 1 0
28 2 0
28 3 0
28 4 0
28 5 0
28 6 0
28 7 0
28 8 0
28 9 0
28 10 0
28 11 0
28 12 0
28 13 0
28 14 0
28 15 0
28 16 0
28 17 0
28 18 0
28 19 0
28 20 0
28 21 0
28 22 0
28 23 0
28 24 0
28 25 0
28 26 0
28 27 0
28 28 0
28 29 0
28 30 0
28 31 0
29 0 16314678
29 1 0
29 2 0
29 3 0
29 4 0
29 5 0
29 6 0
29 7 0
29 8 0
29 9 0
29 10 0
29 11 0
29 12 0
29 13 0
29 14 0
29 15 0
29 16 0
29 17 0
29 18 0
29 19 0
29 20 0
29 21 0
29 22 0
29 23 0
29 24 0
29 25 0
29 26 0
29 27 0
29 28 0
29 29 0
29 30 0
29 31 0
30 0 15893186
30 1 0
30 2 0
30 3 0
30 4 0
30 5 0
30 6 0
30 7 0
30 8 0
30 9 0
30 10 0
30 11 0
30 12 0
30 13 0
30 14 0
30 15 0
30 16 0
30 17 0
30 18 0
30 19 0
30 20 0
30 21 0
30 22 0
30 23 0
30 24 0
30 25 0
30 26 0
30 27 0
30 28 0
30 29 0
30 30 0
30 31 0
31 0 18624438
31 1 0
31 2 0
31 3 0
31 4 0
31 5 0
31 6 0
31 7 0
31 8 0
31 9 0
31 10 0
31 11 0
31 12 0
31 13 0
31 14 0
31 15 0
31 16 0
31 17 0
31 18 0
31 19 0
31 20 0
31 21 0
31 22 0
31 23 0
31 24 0
31 25 0
31 26 0
31 27 0
31 28 0
31 29 0
31 30 0
31 31 0
Sender Receiver Bytes
0 0 0
0 1 1337735
0 2 1498089
0 3 1927158
0 4 954470
0 5 1059291
0 6 337230
0 7 1196630
1 0 920993
1 1 0
1 2 68509952
1 3 24007175
1 4 294988
1 5 33621593
1 6 746257
1 7 3212629
2 0 3064254
2 1 36162185
2 2 0
2 3 2552097
2 4 140083
2 5 503400
2 6 3624428
2 7 984222
3 0 12371778
3 1 71141164
3 2 39918684
3 3 0
3 4 165707
3 5 1998975
3 6 523288
3 7 254694
4 0 5878690
4 1 3743080
4 2 1084812
4 3 89613280
4 4 0
4 5 2189278
4 6 43995619
4 7 823902
5 0 52302944
5 1 11820707
5 2 23220812
5 3 8316031
5 4 38104169
5 5 0
5 6 1027855
5 7 1455038
6 0 4636646
6 1 12330615
6 2 3741502
6 3 6500068
6 4 219557981
6 5 3391134
6 6 0
6 7 104803858
7 0 12262082
7 1 2535301
7 2 2735266
7 3 22877396
7 4 3142736
7 5 3213889
7 6 341987
7 7 0