1)차트작성
1-1) 프로젝트 생성
1-2)기본
1-3) bar와 line
1-4)파이그래프 , 도넛그래프
2)DB연동
2-1) 게시물(board)에서 게시글 작성자별 건수;
2-2) 날짜별로 게시물 갯수
3) model2에 그래프 적용시켜보기
3-1) 작성자별 게시물수 (pie)
3-2) 날짜별 게시물수(bar)
1) 차트작성
Chart.js
Simple yet flexible JavaScript charting library for the modern web
www.chartjs.org
(차트에관한정보들이있음)
해당사이트에 접속해 getStarted 클릭
밑줄친부분의 script부분을 잘 가지고있자!!!!!
<script src="https://cdn.jsdelivr.net/npm/chart.js"></script>
1-1) 프로젝트생성
다음이름과같이 DynamicWebProject를 만들어줘!!
1-2) 기본
(아까 복사해놓은 스크립트 활용)
/chartStudy/src/main/webapp/bar1.html
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>간단한막대그래프작성</title>
</head>
<body>
<script src="https://cdn.jsdelivr.net/npm/chart.js"></script>
<div><canvas id=myChart></canvas></div>
<script type="text/javascript">
const ctx = document.querySelector("#myChart"); //canvas객체
new Chart(ctx,{
type:"bar",//막대그래프
data:{
labels:["Red","blue","Yellow","Green","Purple","Orange"],
datasets:[{
label : "# of votes1",
data:[12,19,3,5,2,3], //막대그래프의 y축값(높이)라고 봐주면댐
borderWidth : 1,
backgroundColor :["Red","blue","Yellow","Green","Purple","Orange"]
},
{
label : "# of votes2",
data:[5,9,1,10,15,3],
borderWidth : 1,
backgroundColor :["Red","blue","Yellow","Green","Purple","Orange"]
}]
},
options:{
scales:{y:{beginAtZero : true}},
plugins: {
legend: {
position: "right" // 범례 위치를 오른쪽으로 설정
}
}
},
})
</script>
</body>
</html>
1-3) bar 와 line
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>막대,선 그래프 함께표현</title>
<script src="https://cdn.jsdelivr.net/npm/chart.js"></script>
</head>
<body>
<div style="width:75%">
<canvas id="canvas"></canvas>
</div>
<script type="text/javascript">
let months=
["1월","2월","3월","4월","5월","6월","7월","8월","9월","10월","11월","12월"];
let chartData={
labels : months,
datasets:[
{
type:'line',
label:'영업부',
borderColor : '#FF0000',//선의색상
borderWidth : 3,//두꼐
fill : true,
data:[10,15,25,55,0,-25,-40,56,78,12,50,25]
},
{
type:'bar',//막대그래프
label:'총무부',
backgroundColor : '#A565FF',
borderColor : 'black', //테두리색상
borderWidth : 2,
data:[10,15,25,55,0,-25,-40,56,78,12,50,25]
},
{
type:'bar',//막대그래프
label:'총무부',
backgroundColor : '#00FF00',
borderColor : 'red', //테두리색상
borderWidth : 2,
data:[10,15,25,55,0,-25,-40,56,78,12,50,25]
}
]}
window.onload = function(){
let ctx = document.getElementById("canvas");
new Chart(ctx,{
type:'bar',
data : chartData,
options : {
responsive : true,
title:{display:true, text:'막대그래프와 선그래프'}
},
legend : {display : true},
})
}
</script>
</body>
</html>
1-4)파이그래프 , 도넛그래프
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>파이(도넛)그래프</title>
</head>
<body>
<script src="https://cdn.jsdelivr.net/npm/chart.js"></script>
<div style="width:75%">
<canvas id="canvas"></canvas>
</div>
<script type="text/javascript">
let months=
["1월","2월","3월","4월","5월","6월","7월","8월","9월","10월","11월","12월"];
let getData = function(){
return Math.round(Math.random()*100)
}
let config={
type : "pie", //doughnut
data :{
datasets:[
{
data:[
getData(),getData(),getData(),getData(),
getData(),getData(),getData(),getData(),
getData(),getData(),getData(),getData(),
],
backgroundColor:['red','orange','yellow','green','blue',
'#FFEEFE','#123456','#12FFFF','#FFFF56',
'#FFFF00','#FF00FF','#EEEEEE'],
label:"파이(도넛)그래프"
}],
labels : months
},
options: {
responsive: true,
plugins: {
legend: {
position: 'right' // 범례 위치를 오른쪽으로 설정
},
title: {
display: true,
text: '파이(도넛)그래프연습'
}
},
animation: {
animateScale: true,
animateRotate: true
}
}
}
window.onload = function(){
let ctx = document.querySelector("#canvas");
new Chart(ctx,config);
}
</script>
</body>
</html>
type : pie
type : doughnut
2)DB연동
2-1) 게시물(board)에서 게시글 작성자별 건수;
/chartStudy/src/main/webapp/db/barline.jsp
<%@ page language="java" contentType="text/html; charset=UTF-8"
pageEncoding="UTF-8"%>
<%@ taglib prefix="c" uri="http://java.sun.com/jsp/jstl/core" %>
<%@ taglib prefix="sql" uri="http://java.sun.com/jsp/jstl/sql" %>
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>게시글 작성자별 건수 그래프</title>
</head>
<body>
<sql:setDataSource var="conn" driver="org.mariadb.jdbc.Driver"
url="jdbc:mariadb://localhost:3306/gdjdb"
user="gduser" password="1234"/>
<sql:query var="rs" dataSource="${conn}" >
select writer,count(*) cnt from board
group by writer
order by count(*) desc
</sql:query>
<div style="width:75%"><canvas id="canvas"></canvas></div>
<script src="https://cdn.jsdelivr.net/npm/chart.js"></script>
<script type="text/javascript">
let randomColorFactor = function(){
return Math.round(Math.random()*255)//0~255사이의 정수
}
let randomColor = function(opacity){
//rgba(100,100,50,1) : rgba(red,green,blue,투명도)
//투명도 : 0~1사이의값, 0:투명 1:불투명
return "rgba("+ randomColorFactor()+","
+ randomColorFactor() + ","+randomColorFactor()+","
+(opacity || ".3")+")";
}
let chartData = {
labels:
[<c:forEach items="${rs.rows}" var="m">"${m.writer}",</c:forEach>],
datasets :[
{
type:'line',
borderWidth : 2,
borderColor : [<c:forEach items="${rs.rows}" var="m">randomColor(1),</c:forEach>],
label :'건수',
fill : false,
data:
[<c:forEach items="${rs.rows}" var="m">"${m.cnt}",</c:forEach>],
},
{
type:'bar',
borderWidth : 2,
backgroundColor : [<c:forEach items="${rs.rows}" var="m">randomColor(1),</c:forEach>],
label :'건수',
data:
[<c:forEach items="${rs.rows}" var="m">"${m.cnt}",</c:forEach>],
}]
}
window.onload = function(){
let ctx = document.querySelector("#canvas");
new Chart(ctx,{
type:'bar',
data : chartData,
options:{
responsive : true,
plugins:{
legend:{
display:false,
},
title:{
display:true,
text:"작성자별 게시판 등록건수"
},
},
scales:{
x:{
display:true,
title:{
display:true,
text:"게시물작성자"
},
},
y:{
display:true,
beginAtZero:true,
title:{
display:true,
text:"게시물작성 건수"
},
}
}
}//option
})//chart
}
</script>
</body>
</html>
옛날방식
<script type="text/javascript"
src="https://cdnjs.cloudflare.com/ajax/libs/Chart.js/2.9.4/Chart.min.js"></script>
으로 작성하는 방법 ↓ ↓ ↓ ↓
window.onload = function() {
let ctx = document.querySelector("#canvas");
new Chart(ctx,{
type : 'bar',
data : charData,
options : {
responsive : true,
title : {display : true, text :"작성자별 게시판 등록 건수"},
legend : {display : false},
scales : {
y : {beginAtZero :true},
xAxes : [
{display : true,
scaleLabel : {
display : true,
labelString : "게시물작성자"}
}],
yAxes : [{
display : true,
scaleLabel : {
display : true,
labelString : "게시물 작성 건수"
}
}]
}
}
})
}
PIE타입으로 바꿔서
<%@ page language="java" contentType="text/html; charset=UTF-8"
pageEncoding="UTF-8"%>
<%@ taglib prefix="c" uri="http://java.sun.com/jsp/jstl/core" %>
<%@ taglib prefix="sql" uri="http://java.sun.com/jsp/jstl/sql" %>
<%--pie그래프로 게시글 작성자별 건수 출력하기 --%>
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>PIE</title>
</head>
<body>
<sql:setDataSource var="conn" driver="org.mariadb.jdbc.Driver"
url="jdbc:mariadb://localhost:3306/gdjdb"
user="gduser" password="1234"/>
<sql:query var="rs" dataSource="${conn}">
select writer,count(*) cnt from board
group by writer
order by count(*) desc
</sql:query>
<div style="width:75%"><canvas id="canvas"></canvas></div>
<script src="https://cdn.jsdelivr.net/npm/chart.js"></script>
<script type="text/javascript">
let randomColorFactor = function(){
return Math.round(Math.random()*255)//0~255사이의 정수
}
let randomColor = function(opacity){
return "rgba("+ randomColorFactor()+","
+ randomColorFactor() + ","+randomColorFactor()+","
+(opacity || ".3")+")";
}
let chartData = {
labels:
[<c:forEach items="${rs.rows}" var="m">"${m.writer}",</c:forEach>],
datasets :[
{
type:'pie',
borderWidth : 2,
backgroundColor : [<c:forEach items="${rs.rows}" var="m">randomColor(1),</c:forEach>],
label :'건수',
fill : false,
data:
[<c:forEach items="${rs.rows}" var="m">"${m.cnt}",</c:forEach>],
}]
}
window.onload = function(){
let ctx = document.querySelector("#canvas");
new Chart(ctx,{
type:'pie',
data : chartData,
options:{
responsive : true,
plugins:{
legend:{
display:true,
position:'right'
},
title:{
display:true,
text:"작성자별 게시판 등록건수",
position:'bottom',
color:'purple',
font:{
size:30
}
},
},
}//option
})//chart
}
</script>
</body>
</html>
2-2) 날짜별로 게시물 갯수
<%@ page language="java" contentType="text/html; charset=UTF-8"
pageEncoding="UTF-8"%>
<%@ taglib prefix="c" uri="http://java.sun.com/jsp/jstl/core" %>
<%@ taglib prefix="sql" uri="http://java.sun.com/jsp/jstl/sql" %>
<%--
날짜별로 등록된 게시물건수를 막대 , 선그래프로출력하기
--%>
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>날짜별 게시물건수</title>
</head>
<body>
<sql:setDataSource var="conn" driver="org.mariadb.jdbc.Driver"
url="jdbc:mariadb://localhost:3306/gdjdb"
user="gduser" password="1234"/>
<sql:query var="rs" dataSource="${conn}" >
select SUBSTR(regdate,1,10) 'date' ,count(*) cnt from board
group by SUBSTR(regdate,1,10)
order by SUBSTR(regdate,1,10) asc;
</sql:query>
<div style="width:75%"><canvas id="canvas"></canvas></div>
<script src="https://cdn.jsdelivr.net/npm/chart.js"></script>
<script type="text/javascript">
let randomColorFactor = function(){
return Math.round(Math.random()*255)//0~255사이의 정수
}
let randomColor = function(opacity){
//rgba(100,100,50,1) : rgba(red,green,blue,투명도)
//투명도 : 0~1사이의값, 0:투명 1:불투명
return "rgba("+ randomColorFactor()+","
+ randomColorFactor() + ","+randomColorFactor()+","
+(opacity || ".3")+")";
}
let chartData = {
labels:
[<c:forEach items="${rs.rows}" var="m">"${m.date}",</c:forEach>],
datasets :[
{
type:'line',
borderWidth : 2,
borderColor : [<c:forEach items="${rs.rows}" var="m">randomColor(1),</c:forEach>],
label :'건수',
fill : false,
data:
[<c:forEach items="${rs.rows}" var="m">"${m.cnt}",</c:forEach>],
},
{
type:'bar',
borderWidth : 2,
backgroundColor : [<c:forEach items="${rs.rows}" var="m">randomColor(1),</c:forEach>],
label :'건수',
data:
[<c:forEach items="${rs.rows}" var="m">"${m.cnt}",</c:forEach>],
}]
}
window.onload = function(){
let ctx = document.querySelector("#canvas");
new Chart(ctx,{
type:'bar',
data : chartData,
options:{
responsive : true,
plugins:{
legend:{
display:false,
},
title:{
display:true,
text:"날짜별 게시판 등록건수"
},
},//plugin
scales:{
x:{
display:true,
title:{
display:true,
text:"날짜"
},
},
y:{
display:true,
beginAtZero:true,
title:{
display:true,
text:"게시물작성 건수"
},
}
}
}//options
})//chart
}
</script>
</body>
</html>
3) model2에 그래프 적용시켜보기
3-1) 작성자별 게시물수 (pie)
변경한 layout.jsp
(크기의문제가있어서)
<script type="text/javascript"
src="https://cdnjs.cloudflare.com/ajax/libs/Chart.js/2.9.4/Chart.min.js"></script>
다음과 같이 CDN의 스크립트 버전을 낮췄다
코딩방법도 조금은달라짐 ( plugin을 사용하지않음)
<%@ page language="java" contentType="text/html; charset=UTF-8"
pageEncoding="UTF-8"%>
<%@taglib uri="http://java.sun.com/jsp/jstl/core" prefix="c"%>
<%@taglib uri="http://java.sun.com/jsp/jstl/fmt" prefix="fmt"%>
<%@taglib uri="http://java.sun.com/jsp/jstl/functions" prefix="fn"%>
<c:set var="path" value="${pageContext.request.contextPath }"></c:set>
<!DOCTYPE html>
<html>
<head>
<title><sitemesh:write property="title" /></title>
<meta charset="utf-8">
<meta name="viewport" content="width=device-width, initial-scale=1">
<link rel="stylesheet"
href="https://cdn.jsdelivr.net/npm/bootstrap@4.6.2/dist/css/bootstrap.min.css">
<script
src="https://cdn.jsdelivr.net/npm/jquery@3.7.1/dist/jquery.slim.min.js"></script>
<script
src="https://cdn.jsdelivr.net/npm/popper.js@1.16.1/dist/umd/popper.min.js"></script>
<script
src="https://cdn.jsdelivr.net/npm/bootstrap@4.6.2/dist/js/bootstrap.bundle.min.js"></script>
<!-- include summernote css/js -->
<link
href="https://cdn.jsdelivr.net/npm/summernote@0.8.18/dist/summernote.min.css"
rel="stylesheet">
<script
src="https://cdn.jsdelivr.net/npm/summernote@0.8.18/dist/summernote.min.js"></script>
<script type="text/javascript"
src="https://cdnjs.cloudflare.com/ajax/libs/Chart.js/2.9.4/Chart.min.js"></script>
<style>
.fakeimg {
height: 200px;
background: #aaa;
}
.footer {
display: flex;
flex-direction: column;
}
.footer_link {
height: 15%;
display: flex;
align-items: center;
}
.footer_link a {
text-decoration: none;
color: black;
font-weight: bold;
margin: 15px;
}
.footer_company {
height: 70%;
}
.footer_company>ul {
list-style: "- ";
padding-left: 15px;
}
.footer_copyright {
height: 15%;
text-align: center
}
.footer>div {
border-top: 1px solid gray
}
</style>
<sitemesh:write property="head" />
<script
src="https://ajax.googleapis.com/ajax/libs/jquery/3.7.1/jquery.min.js"></script>
</head>
<body>
<div class="jumbotron text-center" style="margin-bottom: 0">
<h1>dongPage</h1>
<p>남자의 페이지</p>
</div>
<nav class="navbar navbar-expand-sm bg-dark navbar-dark">
<a class="navbar-brand" href="#">목록</a>
<button class="navbar-toggler" type="button" data-toggle="collapse"
data-target="#collapsibleNavbar">
<span class="navbar-toggler-icon"></span>
</button>
<div class="collapse navbar-collapse" id="collapsibleNavbar">
<ul class="navbar-nav">
<li class="nav-item"><a class="nav-link"
href="${path}/member/main">회원관리</a></li>
<li class="nav-item"><a class="nav-link"
href="${path}/board/list?boardid=1">공지사항</a></li>
<li class="nav-item"><a class="nav-link"
href="${path}/board/list?boardid=2">자유게시판</a></li>
<c:if test="${sessionScope.login != null}">
<li class="nav-item"><a class="nav-link" href="#">${sessionScope.login}님
하이</a></li>
<li class="nav-item"><a class="nav-link"
href="${path}/member/logout">로그아웃</a></li>
</c:if>
<li class="nav-item"><a class="nav-link"
href="javascript:history.go(-1)">뒤로가기</a></li>
</ul>
</div>
</nav>
<div class="container" style="margin-top: 30px">
<div class="row">
<div class="col-6" style="border: 1px solid #EEEEEE;">
<%-- 작성자별 게시물 등록 건수 pie그래프 : 가장많이작성한작성자 5명만 --%>
<canvas id="canvas1"></canvas>
</div>
<div class="col-6" style="border: 1px solid #EEEEEE;">
<%-- 최근작성일자 기준 게시물 등록 건수 pie그래프 : 가장많이작성한작성자 5명만--%>
<canvas id="canvas2" ></canvas>
</div>
</div>
<sitemesh:write property="body" />
</div>
<footer class="footer">
<div>
<span id="si"> <select name="si" onchange="getText('si')">
<option value="">시,도를 선택하세요</option>
</select>
</span> <span id="gu"> <select name="gu" onchange="getText('gu')">
<option value="">구군 선택하세요</option>
</select>
</span> <span id="dong"> <select name="dong">
<option value="">동리를 선택하세요</option>
</select>
</span>
</div>
<div class="footer_link">
<a href="">이용약관</a> | <a href="">개인정보취급방침</a> | <a href="">인재채용</a> |
<a href="">고객센터</a>
</div>
<div class="footer_company">
<ul>
<li>상호명 : DongCompany</li>
<li>대표자 : 유동곤</li>
<li>전화 : 010-86948525</li>
<li>개인정보책임자 : 유동곤 /ddkk8525@gmail.com</li>
</ul>
</div>
<div class="footer_copyright">Copyright ⓒ dong Company.
Allrights reserved.</div>
</footer>
<script type="text/javascript">
$(function(){
piegraph();
bargraph();
$.ajax({
url : "${path}/ajax/select",
success: function(data){
//data : ["서울특별시","경기도",.....]
let arr = JSON.parse(data)
$.each(arr,function(i,item){
//item : 서울특별시
$("select[name=si]").append(function(){
return "<option>"+item+"</option>"
})
})
},
error:function(e){
alert("서버오류 : "+e.status)
}
})
}) //여기까지의부분은 모든 시(name='si')를 AJAX를 통해 가져올거임
function getText(type) { // 시 or 도를 선택하면 발생하는 함수
const si = $("select[name=si]").val(); //클릭한 시의 vlaue
const gu = $("select[name=gu]").val();//클릭한 구의 vlaue
let url = "";
let targetSelect;
if (type === "si") {
if (!si) return;
url = "${path}/ajax/select?si="+si; //입력받은si의값을 파라미터로갖는 주소
targetSelect = $("select[name=gu]"); //target을 gu에해당하는 select태그로설정
// 시를 선택하면 기존 구, 동 초기화
$("select[name=gu]").html('<option value="">구군 선택하세요</option>');
$("select[name=dong]").html('<option value="">동리를 선택하세요</option>');
} else if (type === "gu") {
if (!si || !gu) return;
url = "${path}/ajax/select?si="+si+"&gu="+gu;
targetSelect = $("select[name=dong]");
// 구를 선택하면 기존 동 초기화
$("select[name=dong]").html('<option value="">동리를 선택하세요</option>');
} else {
return;
}
$.ajax({ //ajax에 요청을 보낼거임
url: url, //위 type에의한 url 설정
success: function(data) {
const arr = JSON.parse(data); //성공시 JSON방식(배열)으로 데이터를가져옴
$.each(arr, function(i, item) {
//해당배열을 순회해서 나온값들을 모두 taget태그하위에 option으로넣는다
targetSelect.append("<option>"+item+"</option>" );
});
},
error: function(e) {
alert("서버 오류 : " + e.status);
}
});
}
function piegraph(){
$.ajax("${path}/ajax/graph1",{
success: function(data){
//data : [{"cnt":24,"writer":유동곤"},{"cnt":2,"writer":fff"},{"cnt":2,"writer":admin"},{"cnt":1,"writer":김창민"},{"cnt":1,"writer":김민지"}]
pieGraphPrint(data);
},
error : function(e){
alert("서버오류 : "+e.status)
}
})
}
function bargraph(){
$.ajax("${path}/ajax/graph2",{
success: function(data){
bargraphPrint(data);
},
error : function(e){
alert("서버오류 : "+e.status)
}
})
}
let randomColorFactor = function(){
return Math.round(Math.random()*255)//0~255사이의 정수
}
let randomColor = function(opacity){
//rgba(100,100,50,1) : rgba(red,green,blue,투명도)
//투명도 : 0~1사이의값, 0:투명 1:불투명
return "rgba("+ randomColorFactor()+","
+ randomColorFactor() + ","+randomColorFactor()+","
+(opacity || ".3")+")";
}
function pieGraphPrint(data){
let rows = JSON.parse(data); //json형식으로데이터를받아
let writers = [] //작성자목록
let datas=[] //게시물 갯수
let color=[] // 랜덤한Color를 넣어둘곳
$.each(rows,function(i,item){//모든데이터를 순회
//item : {"cnt":3,"writer":"홍길동"}
writers[i] = item.writer; // "홍길동"
datas[i] = item.cnt; //3
color[i] = randomColor(1);
})
let config = {
type:'pie',
data : {
datasets:[{
data : datas,//cnt가있는배열
backgroundColor : color
}],
labels : writers,
},
options : {
responsive: true,//반응형차트생성
legend : {position:"right"},//label을 우측에위치
title : {
display : true,
text : '게시물 작성자별 등록건수(최대 5명)',
position:'bottom'
}
}
}
let ctx = document.querySelector("#canvas1");
new Chart(ctx,config)
}
function bargraphPrint(data){
let rows = JSON.parse(data);
let dates =[] //날짜
let cnts=[] //게시물 갯수
let color=[] // 랜덤한Color를 넣어둘곳
console.log("rows : ",rows)
$.each(rows,function(i,item){//모든데이터를 순회
cnts[i] = item.cnt; //게시물개수
dates[i] = item.date; //날짜(년월일)
color[i] = randomColor(1);
})
let config = {
type:'bar',
data : {
datasets:[{
data : cnts,
backgroundColor : color
}],
labels : dates,
},
options : {
responsive: true,
legend : { display: true,position:"right"},
title : {
display : true,
text : '날짜별 등록건수(최대5일)',
position:'bottom'
},
scales:{
yAxes:[{
ticks:{
display : true,
beginAtZero:true
},
}]
}
}
}
let ctx = document.querySelector("#canvas2");
new Chart(ctx,config)
}
</script>
</body>
</html>
AjaxController에 graph1 매핑 추가 (구식방법과 jackson사용한방법 두개다있음)
/*@RequestMapping("graph1") 구식방법
public String graph1(HttpServletRequest request ,
HttpServletResponse response) {
BoardDao dao = new BoardDao();
List<Map<String,Object>> list = dao.boardgraph1();
StringBuilder sb = new StringBuilder("[");
int i=0;
for(Map<String,Object> m : list) {
for(Map.Entry<String, Object> me : m.entrySet()) {
if(me.getKey().equals("cnt")) {
sb.append("{\"cnt\":"+me.getValue()+",");
}
if(me.getKey().equals("writer")) {
sb.append("\"writer\":\""+me.getValue()+"\"}");
}
//하나의 map을 처리
}//2번for문종료
i++;
if(i<list.size()) {
sb.append(",");
} //각 map사이에 , 를 찍어줌
}//1번for문 종료
sb.append("]");//[{"cnt":xx,"writer":xx},{"cnt":x2,"writer":x2}]의형태
request.setAttribute("json", sb.toString().trim());
return "ajax/graph";
}*/
@RequestMapping("graph1")
public String graph1(HttpServletRequest request ,
HttpServletResponse response) {
BoardDao dao = new BoardDao();
List<Map<String,Object>> list = dao.boardgraph1();
ObjectMapper objectMapper = new ObjectMapper();
try {
String json = objectMapper.writeValueAsString(list);
request.setAttribute("json", json);
}
catch(Exception e) {
e.printStackTrace();
}
return "ajax/graph";
}
해당라이브러리 꼭 추가!!
BoardDao에
boardgraph1 메서드추가
public List<Map<String, Object>> boardgraph1() {
SqlSession session = MyBatisConnection.getConnection();
List<Map<String, Object>> list = null;
try {
list = session.getMapper(cls).boardgraph1();
return list;
} catch (Exception e) {
e.printStackTrace();
}
finally {
MyBatisConnection.close(session);
}
return null;
}
BoardMapper에 sql문 넣기
@Select("select writer , count(*) cnt from board"
+ " group by writer order by cnt desc"
+ " limit 0,5") //limit 0,5 : 0번째행부터 5개
List<Map<String, Object>> boardgraph1();
//Map<컬럼명,컬럼값> 형태를 List에 순서대로넣음
// ex : {"writer":"길동" , "cnt":4}
// {"writer":"길순" , "cnt":2}
앞의번호가 set의 인덱스라고생각하면 되고
속성명: key
값 : value 로 생각
/webapp/view/ajax/graph.jsp
<%@ page language="java" contentType="text/html; charset=UTF-8"
pageEncoding="UTF-8"%>
${json}
3-2) 날짜별 게시물수(bar)
layout.jsp (주요한 함수들만 남겨놈)
<%@ page language="java" contentType="text/html; charset=UTF-8"
pageEncoding="UTF-8"%>
<%@taglib uri="http://java.sun.com/jsp/jstl/core" prefix="c"%>
<%@taglib uri="http://java.sun.com/jsp/jstl/fmt" prefix="fmt"%>
<%@taglib uri="http://java.sun.com/jsp/jstl/functions" prefix="fn"%>
<c:set var="path" value="${pageContext.request.contextPath }"></c:set>
.......
<script type="text/javascript"
src="https://cdnjs.cloudflare.com/ajax/libs/Chart.js/2.9.4/Chart.min.js"></script>
...
<div class="container" style="margin-top: 30px">
<div class="row">
<div class="col-6" style="border: 1px solid #EEEEEE;">
<%-- 작성자별 게시물 등록 건수 pie그래프 : 가장많이작성한작성자 5명만 --%>
<canvas id="canvas1"></canvas>
</div>
<div class="col-6" style="border: 1px solid #EEEEEE;">
<%-- 최근작성일자 기준 게시물 등록 건수 pie그래프 : 가장많이작성한작성자 5명만--%>
<canvas id="canvas2"></canvas>
</div>
</div>
<sitemesh:write property="body" />
</div>
....
<script type="text/javascript">
$(function(){
piegraph();
bargraph();
$.ajax({
url : "${path}/ajax/select",
success: function(data){
//data : ["서울특별시","경기도",.....]
let arr = JSON.parse(data)
$.each(arr,function(i,item){
//item : 서울특별시
$("select[name=si]").append(function(){
return "<option>"+item+"</option>"
})
})
},
error:function(e){
alert("서버오류 : "+e.status)
}
})
}) //여기까지의부분은 모든 시(name='si')를 AJAX를 통해 가져올거임
function bargraph(){
$.ajax("${path}/ajax/graph2",{
success: function(data){
bargraphPrint(data);
},
error : function(e){
alert("서버오류 : "+e.status)
}
})
}
let randomColorFactor = function(){
return Math.round(Math.random()*255)//0~255사이의 정수
}
let randomColor = function(opacity){
//rgba(100,100,50,1) : rgba(red,green,blue,투명도)
//투명도 : 0~1사이의값, 0:투명 1:불투명
return "rgba("+ randomColorFactor()+","
+ randomColorFactor() + ","+randomColorFactor()+","
+(opacity || ".3")+")";
}
function bargraphPrint(data){
let rows = JSON.parse(data);
let dates = [] //작성자목록
let cnts=[] //게시물 갯수
let color=[] // 랜덤한Color를 넣어둘곳
$.each(rows,function(i,item){//모든데이터를 순회
dates[i] = item.date; //날짜(년월일)
cnts[i] = item.cnt; //게시물개수
color[i] = randomColor(1);
})
let config = {
type:'bar',
data : {
labels : dates,
datasets:[{
data : cnts,
backgroundColor : color
}],
},
options : {
responsive: true,
legend : {position:"top"},
title : {
display : true,
text : '날짜별 등록건수(최대5일)',
position:'bottom'
},
scales:{
yAxes:[{
ticks:{
beginAtZero:true
},
}]
}
}
}
let ctx = document.querySelector("#canvas2");
new Chart(ctx,config)
}
</script>
</body>
</html>
AjaxController의 graph2 매핑부분
/*@RequestMapping("graph2") //구식의방법
public String graph2(HttpServletRequest request ,
HttpServletResponse response) {
BoardDao dao = new BoardDao();
List<Map<String,Object>> list = dao.boardgraph2();
StringBuilder sb = new StringBuilder("[");
int i=0;
for(Map<String,Object> m : list) {
for(Map.Entry<String, Object> me : m.entrySet()) {
if(me.getKey().equals("date")) {
sb.append("{\"date\":\""+me.getValue()+"\",");
}
if(me.getKey().equals("cnt")) {
sb.append("\"cnt\":"+me.getValue()+"}");
}
//하나의 map을 처리
}//2번for문종료
i++;
if(i<list.size()) {
sb.append(",");
} //각 map사이에 , 를 찍어줌
}//1번for문 종료
sb.append("]");//[{"cnt":xx,"writer":xx},{"cnt":x2,"writer":x2}]의형태
request.setAttribute("json", sb.toString().trim());
return "ajax/graph";
}*/
@RequestMapping("graph2")
public String graph3(HttpServletRequest request, HttpServletResponse response) {
BoardDao dao = new BoardDao();
List<Map<String, Object>> list = dao.boardgraph2();
ObjectMapper objectMapper = new ObjectMapper();
try {
/* 날짜 포맷 설정
SimpleDateFormat dateFormat = new SimpleDateFormat("yyyy-MM-dd");
objectMapper.setDateFormat(dateFormat);*/
// List<Map<String, Object>>를 JSON 문자열로 변환
String jsonStr = objectMapper.writeValueAsString(list);
// 변환된 JSON 문자열 출력
System.out.println(jsonStr);
request.setAttribute("json", jsonStr);
} catch (IOException e) {
e.printStackTrace();
}
return"ajax/graph";
}
해당 jar파일(라이브러리)가 존재해야 가능함
BoardDao의 boardgraph2 메서드
public List<Map<String, Object>> boardgraph2() {
SqlSession session = MyBatisConnection.getConnection();
List<Map<String, Object>> list = null;
try {
list = session.getMapper(cls).boardgraph2();
return list;
} catch (Exception e) {
e.printStackTrace();
}
finally {
MyBatisConnection.close(session);
}
return null;
}
graph.jsp (요청을받으면 json 파라미터를 받아 layout.jsp쪽으로 응답할거임)
<%@ page language="java" contentType="text/html; charset=UTF-8"
pageEncoding="UTF-8"%>
${json}
BoardMapper의 boardgraph2 (방법1)
@Select("select SUBSTR(regdate,1,10) as 'date' , count(*) as cnt "
+ " from board"
+ " group by SUBSTR(regdate,1,10)"
+ " order by SUBSTR(regdate,1,10) asc"
+ " limit 0,5"
)
List<Map<String, Object>> boardgraph2();
(substr로바꿔준다면 dateType--> StringType으로바뀌면서 1번째문자부터 10개만꺼냄)
BoardMapper의 boardgraph2 (방법2)
@Select("SELECT date_format(regdate,'%Y-%m-%d') as 'date' ,count(*) cnt FROM board "
+ " group by date_format(regdate,'%Y-%m-%d') "
+ " order by 1 desc"
+ " limit 0,7")
List<Map<String, Object>> graph2();
date의형식을 아예바꾸지않고 format을 통해 바꿔줌
'JSP' 카테고리의 다른 글
부트캠프59일차(크롤링, model2적용) (0) | 2025.04.25 |
---|---|
부트캠프58일차( writeForm에서의 이미지사용 , {jsoupStudy}웹크롤링) (0) | 2025.04.24 |
부트캠프56일차(jqeury이용한DB연결 , XML분석 , model2의 시,구,동 설정) (0) | 2025.04.22 |
부트캠프56일차(ajax설명,fetch , jquery , json 설명) (0) | 2025.04.22 |
54일차의 내용추가(book 관련) (1) | 2025.04.19 |