1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
|
# Static Pie Chart implementation (using d3).
class Epoch.Chart.Pie extends Epoch.Chart.SVG
defaults =
type: 'pie'
margin: 10
inner: 0
# Creates a new pie chart.
# @param [Object] options Options for the pie chart.
# @option options [Number] margin Margins to add around the pie chart (default: 10).
# @option options [Number] inner The inner radius for the chart (default: 0).
constructor: (@options={}) ->
super(@options = Epoch.Util.defaults(@options, defaults))
@pie = d3.layout.pie().sort(null)
.value (d) -> d.value
@arc = d3.svg.arc()
.outerRadius(=> (Math.max(@width, @height) / 2) - @options.margin)
.innerRadius(=> @options.inner)
@g = @svg.append('g')
.attr("transform", "translate(#{@width/2}, #{@height/2})")
@on 'option:margin', 'marginChanged'
@on 'option:inner', 'innerChanged'
@draw()
# Draws the pie chart
draw: ->
@g.selectAll('.arc').remove()
arcs = @g.selectAll(".arc")
.data(@pie(@getVisibleLayers()), (d) -> d.data.category)
arcs.enter().append('g')
.attr('class', (d) -> "arc pie " + d.data.className)
arcs.select('path')
.attr('d', @arc)
arcs.select('text')
.attr("transform", (d) => "translate(#{@arc.centroid(d)})")
.text((d) -> d.data.label or d.data.category)
path = arcs.append("path")
.attr("d", @arc)
.each((d) -> @._current = d)
text = arcs.append("text")
.attr("transform", (d) => "translate(#{@arc.centroid(d)})")
.attr("dy", ".35em")
.style("text-anchor", "middle")
.text((d) -> d.data.label or d.data.category)
super()
# Updates margins in response to an <code>option:margin</code> event.
marginChanged: -> @draw()
# Updates inner margin in response to an <code>option:inner</code> event.
innerChanged: -> @draw()
|