block by ramnathv 9392270377ba1fa1ce3f

Circular Grid Chart

Full Screen

index.html

<!DOCTYPE html>
<html>
<head>
  <meta http-equiv="content-type" content="text/html; charset=UTF-8">
  <title>Circular Grid Chart - jsFiddle demo by ramnathv</title>
  <script type="text/javascript" src="//coffeescript.org/extras/coffee-script.js"></script>
  <script type='text/javascript' src="//d3js.org/d3.v3.min.js"></script>
  <script type='text/javascript' src="//rawgit.com/gka/d3-jetpack/master/d3-jetpack.js"></script>
  <script type='text/javascript' src="//rawgit.com/kristw/75b61f9beeab9b530612/raw/389e984e4041117a9185cf6edad9f6b85a38097a/d3kit.min.js"></script>
  <script type='text/javascript' src="//rawgit.com/ramnathv/a5a3199538f86817ec1b/raw/f6627fc544e65d8e6186ba87556f743caa3f2730/visutils.js"></script>
  <link rel="stylesheet" type="text/css" href="//maxcdn.bootstrapcdn.com/bootstrap/3.3.5/css/bootstrap.min.css">
  <script type='text/javascript' src="//gka.github.io/chroma.js/vendor/chroma-js/chroma.min.js"></script>
  <script type='text/javascript' src="//rawgit.com/Caged/d3-tip/master/index.js"></script>
  <link rel="stylesheet" type="text/css" href="//rawgit.com/Caged/d3-tip/master/examples/example-styles.css">
  <style type='text/css'>
    #main{
     margin-top: 20px;
   }
  .x-axis-layer path,
  .x-axis-layer line{
    fill: none;
  }
  .y-axis-layer path,
  .y-axis-layer line{
    fill: none;
  }
  svg text{
    font-size: 10px;
  }
  </style>
</head>
<body>
  <div class="container-fluid" id="main">
    <div class="row">
        <div class="col-xs-12 col-md-4">
            <div id="chart"></div>
        </div>
        <div class="col-xs-12 col-md-4">
          <div class="col-xs-6 col-md-4">
          <div class="thumbnail">
            <img id='avatar1' src="https://randomuser.me/api/portraits/thumb/men/1.jpg" class="img-circle">
           </div>
              </div>
           <div class="col-xs-6 col-md-4">
           <div class="thumbnail">
             <img id='avatar2' src="https://randomuser.me/api/portraits/thumb/men/2.jpg" class="img-circle">
        </div>
               </div>
              </div>
       
    </div>
</div>
  <script type="text/coffeescript">





y = d3.range(20)
x = y

expand_grid = (x, y) ->
  d3.merge(x.map (x_) -> y.map (y_) -> {x: x_, y: y_})

data = expand_grid(x, y)
data.forEach (d) ->
  d.c = Math.random()
    
switch_avatar = (d) ->
  #d3.json "//randomuser.me/api/", (error, data) ->
  url = (x) ->
    "https://randomuser.me/api/portraits/thumb/men/#{x}.jpg"
  d3.select('#avatar1').attr('src', url(d.x))
  d3.select('#avatar2').attr('src', url(d.y))


circularGridConstructor = (skeleton) ->
  layers = skeleton.getLayerOrganizer()
  S =
    x: d3.scale.ordinal()
    y: d3.scale.ordinal()
    c: d3.scale.linear().range(["lightyellow", "orange"])
        .domain([0, 1])
        .interpolate(d3.interpolateHcl)
  A =
    x: (d) -> d.x
    y: (d) -> d.y
    c: (d) -> d.c
  layers.create(["hrect", "vrect", 'x-axis', 'y-axis', 'circles'])
  hrect = layers.get('hrect').append('rect.hrect')
  vrect = layers.get('vrect').append('rect.vrect')
  visualize = ->
    data = skeleton.data()
    opts = skeleton.options()
    H = skeleton.getInnerHeight()
    W = skeleton.getInnerWidth()
    W = d3.min([W, H])
    H = d3.min([W, H])
    S.x.rangeRoundBands([0, W]).domain(data.map(A.x), 0, 0.01)
    S.y.rangeRoundBands([0, H]).domain(data.map(A.y), 0, 0.01)
        
    circles = layers.get('circles').selectAll('circle').data(data)
    circles.enter().append('circle')
    circles.attr
      cx: (d) -> S.x(A.x(d)) - S.x.rangeBand()/2
      cy: (d) -> S.y(A.y(d)) - S.y.rangeBand()/2
      r: (d) -> S.x.rangeBand()/2
      fill: (d, i) -> S.c A.c(d)
        
    #circles.call attachTooltip, {html: (d) -> "(#{d.x}, #{d.y})"}
    highlight = (d) ->
      d3.select('.hrect').attr
        x: - S.x.rangeBand()/2
        y: S.y(A.y(d)) - S.y.rangeBand()
        height: S.y.rangeBand()
        width: S.x(A.x(d))
        fill: '#aaa'
        opacity: 0.9
      d3.select('.vrect').attr
        x: S.x(A.x(d)) - S.x.rangeBand()
        y: S.y(A.y(d)) - S.y.rangeBand()/2
        height: H - S.y(A.y(d)) - S.y.rangeBand()
        width: S.x.rangeBand()
        fill: '#ccc'
        opacity: 0.9
    
    tip = d3.tip().attr('class', 'd3-tip')
      .html (d) ->  "(#{d.x}, #{d.y})"
    #circles.call(tip)
    circles.on "mouseover", (d, i) ->
       #tip.show(d)
       switch_avatar(d)
       highlight(d)
       d3.select(@).attr
         stroke: "black"
         "stroke-width": 2
          
    circles.on "mouseout", (d, i) ->
      #tip.hide(d)
      circles.each -> d3.select(@).attr("stroke", "none")
      #d3.select('.hrect').attr('width', 0)
      #d3.select('.vrect').attr('width', 0)
    layers.get('circles').on "mouseout", ->
      d3.select('.hrect').attr('width', 0)
      d3.select('.vrect').attr('width', 0)
    
    xAxis = d3.svg.axis()
      .scale(S.x)
      .orient('bottom')
    H2 = H - S.y.rangeBand()
    layers.get('x-axis')
      .translate([-S.x.rangeBand(), H2])
      .call(xAxis)
    yAxis = d3.svg.axis()
      .scale(S.y)
      .orient('left')
    layers.get('y-axis')
      .translate([-S.x.rangeBand(), -S.y.rangeBand()])
      .call(yAxis)    
  skeleton
    .resizeToFitContainer()
    .on("data", visualize)
    .on("resize", visualize)
    .autoResize(true)
  

renderCircularGrid= (el, x, width, height) ->
  circleGridChart = d3Kit.factory.createChart(
    x.defaults, [], circularGridConstructor                                   
  )
  mychart = new circleGridChart('#' + el.id).data(x.data)
  
defaults = 
  margin: {left: 50, right: 10, top: 30, bottom: 30}
  initialHeight: 400
  initialWidth: "auto"
  fontSize: 10
    
el = document.getElementById('chart')
x = {defaults: defaults, data: data}
renderCircularGrid(el, x)
    


</script>
</body>

</html>