d3.js - 硬刷新后存储选择数据

时间:2014-10-22 10:50:34

标签: d3.js coffeescript icicle-diagram

我很好奇为什么我的d3画布会保存数据,即使在我对浏览器进行硬刷新之后也是如此。现在,如果我'缩放'在g元素上,dy,dx,w和h的变化。因此,如果我使用过滤器并重新渲染冰柱,则g元素具有与之前相同的位置,但高度和宽度就像是新装载的一样。这留下了很多空白。通过一些实验,我发现d3以某种方式保存了绑定到g元素的所有数据。我将它构建为Ruby on Rails项目的前端。我试图用canvas.selectAll(" svg> *")来清除选择,但它似乎不起作用。我按如下方式构建布局:

w = 1200
h = 800
x = d3.scale.linear().range([0,w])
y = d3.scale.linear().range([0,h])

renderIcicle = ()->
  canvas = getCanvas('#canvas')
  url = "/icicle/data.json"
  renderOnData(url, canvas)

getCanvas = (id)->
  d3.select(id).select("svg").remove()
  canvas = d3.select(id).append("svg").attr("width", w).attr("height", h)
  return canvas

calculateLayout = (root)->
  partition = d3.layout.partition()
  data = partition.nodes(root)
  return data

d3.json url, (root)->
  data = calculateLayout(root)
  drawCanvas(canvas, data, root)

  $('#filter-button').click ->
    rerender()

  rerender = ()->
    clearCanvas(canvas)
    data = calculateLayout(root)
    drawCanvas(canvas, data, root)

  drawCanvas = (canvas, data, root)->
    g = canvas.selectAll("g").data(data)

    g.enter().append("g").attr("transform", (d) ->
      "translate(" + x(d.y) + "," + y(d.x) + ")"
    ).on("click", (d)->
      click(d)
    ).append("rect").attr("width", root.dy * kx).attr("height", (d)->
      d.dx * ky
    )

    g.exit().remove()

    click = (d)->
      kx = (if d.y then w - 40 else w) / (1 - d.y)
      ky = h / d.dx
      x.domain([d.y, 1]).range [(if d.y then 40 else 0), w ]
      y.domain [d.x, d.x + d.dx]

      t = g.transition().duration(750).attr("transform", (d)->
        "translate(" + x(d.y) + "," + y(d.x) + ")"
      )

      t.select("rect").attr("width", (d)->
        d.dy * kx
      ).attr "height", (d)->
        d.dx * ky

      t.select("text").attr("transform", (d)->
        "translate(" + (d.x + d.dx / 2) + "," + (d.y + d.dy / 2) + ")"
      ).style "opacity", (d)->
        (if d.dx * ky > 12 then 1 else 0)

      d3.event.stopPropagation()

      return

clearCanvas = (canvas)->
  canvas.selectAll("svg").remove()
  canvas.selectAll("g").remove()
  canvas.selectAll("rect").remove()
  canvas.selectAll("text").remove()

-------------------- UPDATE --------------------
我通过设置宽度和高度等于画布的宽度和高度来解决我最初的d3问题,即保存组的宽度和高度。

.append("rect").attr("width", w).attr("height", h)

这是一种非常黑客的方式,但在重新渲染画布后不再有空白。然而,现在出现的问题是一些矩形开始与其他矩形重叠,导致并非所有数据都被显示。这是因为它按层次呈现项目而不是基于x,y位置。所以我的问题仍然存在:

D3是否在元素上缓存数据(如宽度)?

0 个答案:

没有答案