프로필사진
owgno6
CODELIB
Recent Posts
Recent Comments
«   2024/11   »
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
Archives
Today
Total

티스토리 뷰

라인차트의 예제로 그림과 같이 툴팁 기능과

정확한 데이터값을 보여주기 위해 꺾은선 그래프를 구현한다.


구현할 툴팁 기능은 

바 차트에서는 도형(rect)에 마우스를 올리면 

해당하는 값을 보이게 했다.

라인 차트는 하나의 선이기 때문에 이렇게 구현할 수 없다.

대체 방법은 X축의 값이 있는 부분에

적당한 도형(rect, circle등)을 생성하고(append)

이 도형에 마우스를 올리면 툴팁이 보이도록 작성한다.

반지름(r)이 3 px인 원을 생성하였다.

보이고 숨기는 방식은 바 차트와 동일하다.


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
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
<!DOCTYPE html>
<meta charset="utf-8">
<style>
.grid line {
    stroke: lightgrey;
    stroke-opacity: 0.7;
}
.lineChart {
    fill: none;
    stroke: steelblue;
    stroke-width: 1.5px;
}
.lineChart:hover {
    stroke: black;
    stroke-width: 3px;
}
.toolTip {
    position: absolute;
    border: 1px solid;
    border-radius: 4px 4px 4px 4px;
    background: rgba(0, 0, 0, 0.8);
    color : white;
    padding: 5px;
    text-align: center;
    font-size: 12px;
    min-width: 30px;
}
</style>
<svg width="700" height="320"></svg>
<script src="https://d3js.org/d3.v4.min.js"></script>
<script>
 
    var series = ["2017""2018"];
 
    var dataset = [ 
{'1':17'2':27'3':37'4':27'5':17'6':7,  '7':9'8':19'9':29'10':19'11':9'12':0},
{'1'9'2':19'3':29'4':39'5':29'6':19'7':9'8':7'9':17'10':27'11':17'12':7}];
 
    var keys = d3.keys(dataset[0]);
    var data = [];
 
    dataset.forEach(function(d, i) {
    data[i] = keys.map(function(key) { return {x: key, y: d[key]}; })
    });
 
    var margin = {left: 20, top: 10, right: 10, bottom: 20};
    var svg = d3.select("svg");
    var width  = parseInt(svg.style("width"), 10- margin.left - margin.right;
    var height = parseInt(svg.style("height"), 10)- margin.top  - margin.bottom;
    var svgG = svg.append("g")
        .attr("transform""translate(" + margin.left + "," + margin.top + ")");
    var xScale = d3.scalePoint()//scaleBand() scaleOrdinal
        .domain(keys)
        .rangeRound([0, width]);
    var yScale = d3.scaleLinear()
        .domain([0, d3.max(dataset, function(d) { return d3.max(keys, function(key) { return d[key];});})])
.nice()
        .range([height, 0]);
    var colors = d3.scaleOrdinal(d3.schemeCategory10);
 
    svgG.append("g")
        .attr("class""grid")
        .attr("transform""translate(0," + height + ")")
        .call(d3.axisBottom(xScale)
            .tickSize(-height)
        );
 
    svgG.append("g")
        .attr("class""grid")
        .call(d3.axisLeft(yScale)
            .ticks(5)
            .tickSize(-width)
           );
 
    var line = d3.line()
        //.curve(d3.curveBasis)
        .x(function(d) { return xScale(d.x); })
        .y(function(d) { return yScale(d.y); });
    var lineG = svgG.append("g")
        .selectAll("g")
        .data(data)
           .enter().append("g");
 
    lineG.append("path")
        .attr("class""lineChart")
        .style("stroke"function(d, i) { return colors( series[i]); })
        .attr("d"function(d, i) {return line(d); });
 
    lineG.selectAll("dot")
        .data(function(d) {return d })
        .enter().append("circle")
            .attr("r"3)
            .attr("cx"function(d) { return xScale(d.x) })
            .attr("cy"function(d) { return yScale(d.y);})
            .on("mouseover"function() { tooltip.style("display"null); })
            .on("mouseout",  function() { tooltip.style("display""none"); })
            .on("mousemove"function(d) {
                tooltip.style("left", (d3.event.pageX+10)+"px");
                tooltip.style("top",  (d3.event.pageY-10)+"px");
                tooltip.html("month. " + d.x + "<br/>" + "data value : " + d.y);
            });

    var tooltip = d3.select("body")
        .append("div")
        .attr("class""toolTip")
        .style("display""none");
 
    var legend = svgG.append("g")
        .attr("text-anchor""end")
        .selectAll("g")
        .data(series)
        .enter().append("g")
        .attr("transform"function(d, i) { return "translate(0," + i * 20 + ")"; });
 
    legend.append("rect")
          .attr("x", width - 20)
          .attr("width"19)
          .attr("height"19)
          .attr("fill", colors);
 
      legend.append("text")
          .attr("x", width - 30)
          .attr("y"9.5)
          .attr("dy""0.32em")
          .text(function(d) { return d; });

</script>



[line 76]

다만, 앞서 제작한 예제는

값에 따라 휘어지는 라인이 부드럽다 (curveBasis).

이렇게 부드러운 상태에서

정확한 값에 도형(dot)을 출력하면 

선과 도형의 위치가 맞지 않게 된다.

따라서 선도 그림과 같이 딱 맞추어서 출력되게 하기 위해

부드러운 선이 아닌 꺾은선으로 구현해야 한다.

즉, 유연성은 없지만 꺾은선의 데이터 표기는 정확하다.

.curve(d3.curveBasis)를 지우면

기본 설정이 적용되어

그림과 같이 꺾인 선으로 출력된다.


[line 17 ~ 27]

tooltip의 설정과 CSS 구현부분이다.

이제 더 이상 설명은 필요없을 것 같다.


[line 59]

이번에는 라인의 색상을 다르게 구현해봤다.

d3.schemeCategory10

(전 예제 참조, 05 라인 차트 만들기)


[line 89 ~ 106]

tooltip생성에 따른 반지름 생성과

마우스 오버 아웃 효과를 정의하고

변수 생성(append)과

받아오는 attr, CSS와

style 설정을 하고 마친다.













'D3.js' 카테고리의 다른 글

09 TSV(외부파일)로 차트(Bar Chart) 구현  (1) 2018.06.21
07 원형 차트(Pie & Doughnut Chart)  (1) 2018.06.15
05 라인 차트(Line Chart)  (0) 2018.06.05
04 툴팁(Tooltip)  (2) 2018.06.04
03 그리드(Grid)  (0) 2018.06.01
댓글