일 | 월 | 화 | 수 | 목 | 금 | 토 |
---|---|---|---|---|---|---|
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 |
- 로그인과 장바구니 구현
- 일단_해보는거야
- jakarta.mail
- Spring MVC
- js
- 인증코드로 비밀번호 변경 구현
- jquery
- Level 1
- 고객센터 구현
- 다중 카테고리 구현
- MySQL
- Spring
- 세션
- ajax
- Sts
- json
- 이메일로 인증코드 전송 구현
- 대분류/중분류/소분류
- java
- 스프링
- jsp
- 자바
- 프로그래머스
- 교보문고 따라하기
- SESSION
- MVC
- 오라클
- Oracle
- jsp 프로젝트
- 코딩
감 잃지말고 개발하기
[JSP][MVC][MySQL] 도서 등록 페이지 카테고리 구현하기 #3. 클라 딴 구현(마지막) 본문
저번 포스팅에서는 카테고리 구현 부분 중 서버 딴 로직을 정리해 보았다.
이번 포스팅에서는 클라이언트 딴에서의 코드를 정리해 보도록 하겠다.
목표
♠ 3개의 카테고리로 세분화하여 <select> 박스를 구현할 수 있다.
♠ JSP 파일과 구분한 JS 파일에서 서버에서 보낸 데이터를 사용할 수 있다.
클라이언트 딴에서의 흐름
- 서버에서 request 객체의 속성으로 보낸 카테고리 데이터(JSON Object형식)를 받는다.
- 이 데이터를 대분류 / 중분류 / 소분류로 나눈다.
- 사용자가 대분류를 선택했을 때 대분류에 따른 중분류가 중분류 <select> 박스의 옵션에 나타나게 한다.
- 사용자가 중분류를 선택했을 때 대분류와 중분류에 따른 소분류가 소분류 <select> 박스의 옵션에 나타나게 한다.
도서 등록 페이지(regist.jsp)
아래 이미지는 도서 등록 페이지의 화면이다.
카테고리를 선택하는 빨간 박스 부분을 중점적으로 살펴보자.
1. 카테고리 HTML 부분
나중에 JS 코드에서 각 <select> 요소의 class명으로 접근할 것이다.
순수 HTML 코드의 각 <select> 요소에는 하나의 <option>만이 있다.
<label for="b_main_catgy">카테고리 대분류</label>
<select class="main_select" name="b_main_catgy">
<option value="">전체</option>
</select>
<label for="b_middle_catgy">카테고리 중분류</label>
<select class="middle_select" name="b_middle_catgy">
<option value="">--</option>
</select>
<label for="b_sub_catgy">카테고리 소분류</label>
<select class="sub_select" name="b_sub_catgy">
<option value="">--</option>
</select>
2. 도서 등록 페이지의 스크립트 부분
아래 스크립트를 도서 등록 페이지에서 <body>의 가장 하단에 붙인다.
☞ <script language=JavaScript src="/js/yj/select-catgy.js"></script>
카테고리 관련 JS 코드를 모아놓은 파일이다.
이 파일에서 카테고리 관련한 모든 설정이 이루어진다.
☞ const catgys = ${catgys};
서버에서 request 파라미터에 담아 보낸 속성 catgys을 EL 표현식으로 가져와 JSP 페이지의 내부 스크립트에 따로 저장한 부분이다.
기본적으로 나는 JS 파일을 해당 JSP 페이지와 분리해 작성할 것이기 때문에,
외부 파일에서 서버에서 건너온 데이터를 사용해 주기 위해 위와 같이 작성해 주었다.
<script src="/js/vendor/jquery-2.2.4.min.js"></script>
<script language=JavaScript src="/js/yj/select-catgy.js"></script>
<script type="text/javascript">
const catgys = ${catgys};
console.log(catgys);
</script>
▼ 콘솔 확인
DB에서 가져온 데이터가 모두 출력된 것을 볼 수 있다.
카테고리 하나의 객체가 중괄호로 감싸져 있고, 이것들은 배열[ ]로 감싸져 있다.
이 배열은 최종적으로 "catgys"의 이름의 값이 되어 하나의 Object가 되었다.
외부 JS 파일(select-catgy.js)
도서 등록 페이지(JSP 파일)와 완전히 분리된 해당 JS 파일은 js 폴더 하위의 yj 폴더 하위에 존재한다.
코드를 작성해 보자.
1. $(document).ready(function() { });
카테고리 관련 작업은 DOM 요소를 조작하는 것과 연관되어 있다.
때문에 $(document).ready() 함수를 사용해 HTML 문서(구조)가 완전히 로드된 이후에 JS 코드가 실행되도록 처리한다.
select-catgy.js 파일에 아래 코드를 적고 브라우저 콘솔 창을 보면, 도서 등록 페이지(jsp 파일)의 스크립트 부분에서 선언한 catgys 변수가 출력된 것을 확인할 수 있다.
$(document).ready(function() {
console.log(catgys);
});
▼ 콘솔 확인
데이터가 잘 불러와졌으니, 이제 카테고리를 분류해 보자.
2. 대분류 <select> 박스
☞ $.each(catgys["catgys"], function(index, value) { });
catgys에서 이름이 "catgys"인 데이터를 루프를 돌면서 대분류 데이터(하나의 객체)만 뽑아올 것이다.
파라미터 value에는 하나의 객체(카테고리 VO 클래스 형식)가 들어간다.
☞ if(value.code_ref_md == 0 && value.code_ref_mn == 0) { }
대분류 객체에는 code_ref_md와 code_ref_mn에 값이 저장되어 있지 않다(포스팅 #1. 기본 세팅 편 참고).
value가 NULL인 데이터가 JSON 형식으로 넘어올 땐 0으로 저장되므로 0과 비교해 대분류의 데이터만 가져오도록 한다.
☞ main_catgy_arr.push(main_catgy);
Array 타입의 변수 main_catgy_arr에 뽑아온 대분류 데이터를 저장한다.
☞ $.each(main_catgy_arr, function(index, value) { });
루프를 돌면서 대분류 <select> 박스 하위에 <option>으로 추가한다.
var main_catgy_arr = new Array();
var main_catgy = new Object();
// 대분류 select 박스에 넣을 데이터 준비
$.each(catgys["catgys"], function(index, value) {
if(value.code_ref_md == 0 && value.code_ref_mn == 0) {
// init
main_catgy = new Object();
main_catgy.code = value.code;
main_catgy.name = value.name;
main_catgy_arr.push(main_catgy);
}
});
// 대분류 select 박스에 데이터 삽입
var main_select = $(".main_select");
$.each(main_catgy_arr, function(index, value) {
main_select.append("<option value='" + value.code + "'>" + value.name + "</option>");
});
▼ 화면 확인
3. 중분류 <select> 박스
대분류 <select> 박스가 정상적으로 출력되는 것을 확인했으니, 이젠 대분류 옵션을 클릭했을 때의 중분류 <select> 박스를 구현해 보자.
☞ if($(this).val() == "") { });
대분류 <option>에는 전체 / 국내도서 / 외국도서 가 있다.
사용자가 <option>전체</option>을 선택했을 땐 그 어떤 중분류 및 소분류 옵션이 나오면 안 되므로 그에 따른 처리를 해주는 if문이다.
사용자가 "전체"를 선택했을 땐 <option>--</option>이 선택되도록 한다.
☞ if(value.code_ref_md == 0 && value.code_ref_mn == main_code) { }
중분류 데이터를 가져오기 위한 조건이다.
중분류 데이터는 공통적으로 code_ref_md에는 NULL이, code_ref_mn에는 대분류 코드가 저장되어 있다.
중분류 데이터만 Array 타입의 변수 middle_catgy_arr에 저장한다.
이 배열을 다시 루프를 돌리면서 중분류 <select> 박스의 <option>으로 추가한다.
☞ $('.sub_select').html("<option value=''>--</option>");
대분류 옵션을 새로 선택할 때 기존 대분류 옵션에 따른 중분류 옵션을 없애기 위한 코드이다.
// 대분류 select 요소가 변경되었을 때 실행
$(document).on("change", "select.main_select", function() {
// 대분류 미선택시 중/소분류 옵션 표시
if($(this).val() == "") {
$('.middle_select, .sub_select').html("<option value=''>--</option>");
}
else {
var middle_catgy_arr = new Array();
var middle_catgy = new Object();
var main_code = $(this).val();
// 중분류 select 박스에 넣을 데이터 준비
$.each(catgys["catgys"], function(index, value) {
if(value.code_ref_md == 0 && value.code_ref_mn == main_code) {
middle_catgy = new Object();
middle_catgy.code = value.code;
middle_catgy.name = value.name;
middle_catgy_arr.push(middle_catgy);
}
});
// 중분류 select 요소
var middle_select = $(".middle_select");
// 기존 대분류에 따른 중분류 및 소분류 옵션 삭제
$('.sub_select').html("<option value=''>--</option>");
// 중분류 옵션 추가
var html = "<option value=''>선택</option>";
$.each(middle_catgy_arr, function(index, value) {
html += "<option value='" + value.code + "'>" + value.name + "</option>";
});
middle_select.html(html);
}
});
▼ 화면 확인
대분류에서 "국내 도서" 옵션을 선택하니 그에 따른 중분류 옵션이 출력된다.
여기서 다시 대분류 "전체" 옵션을 선택하면 중분류 및 소분류 옵션이 "--"으로 변경될 것이다.
4. 소분류 <select> 박스
마지막, 대분류와 중분류 옵션을 클릭했을 때의 소분류 <select> 박스를 구현해 보자.
☞ var main_code = $('.main_select').val();
var middle_code = $(this).val();
중분류 <select> 박스 옵션이 변경되었을 때,
해당 요소의 값을 변수 middle_code에, 대분류 <select> 요소의 값을 변수 main_code변수에 저장한다.
이 값들로 소분류 데이터를 추출할 것이다.
☞ if(value.code_ref_md == middle_code && value.code_ref_mn == main_code) { }
카테고리 데이터들 중, 동일한 대분류 및 중분류 값을 가진 소분류 데이터만 추출한다.
// 중분류 select 요소가 변경되었을 때 실행
$(document).on("change", "select.middle_select", function() {
var sub_catgy_arr = new Array();
var sub_catgy = new Object();
var main_code = $('.main_select').val();
var middle_code = $(this).val();
// 소분류 select 박스에 넣을 데이터 준비
$.each(catgys["catgys"], function(index, value) {
if(value.code_ref_md == middle_code && value.code_ref_mn == main_code) {
sub_catgy = new Object();
sub_catgy.code = value.code;
sub_catgy.name = value.name;
sub_catgy_arr.push(sub_catgy);
}
});
// 소분류 select 요소
var sub_select = $(".sub_select");
// 기존 중분류에 따른 소분류 옵션 삭제
sub_select.html("<option value=''>--</option>");
// 소분류 select 박스에 옵션 추가
var html = "<option value=''>선택</option>";
$.each(sub_catgy_arr, function(index, value) {
html += "<option value='" + value.code + "'>" + value.name + "</option>";
});
sub_select.html(html);
});
▼ 화면 확인
대분류에서 "국내 도서" 옵션을 선택하고, 중분류에서 "경제/경영" 옵션을 선택하면 해당 소분류 옵션들이 출력된다.
▼ JS 전체 코드
/**
* 도서 카테고리 분류
*/
$(document).ready(function() {
console.log(catgys);
var main_catgy_arr = new Array();
var main_catgy = new Object();
// 대분류 select 박스에 넣을 데이터 준비
$.each(catgys["catgys"], function(index, value) {
if(value.code_ref_md == 0 && value.code_ref_mn == 0) {
// init
main_catgy = new Object();
main_catgy.code = value.code;
main_catgy.name = value.name;
main_catgy_arr.push(main_catgy);
}
});
$.each(main_catgy_arr, function(index, value) {
console.log(value.name);
});
// 대분류 select 박스에 데이터 삽입
var main_select = $(".main_select");
$.each(main_catgy_arr, function(index, value) {
main_select.append("<option value='" + value.code + "'>" + value.name + "</option>");
});
// 대분류 select 요소가 변경되었을 때 실행
$(document).on("change", "select.main_select", function() {
// 대분류 미선택시 중/소분류 옵션 표시
if($(this).val() == "") {
$('.middle_select, .sub_select').html("<option value=''>--</option>");
}
else {
var middle_catgy_arr = new Array();
var middle_catgy = new Object();
var main_code = $(this).val();
// 중분류 select 박스에 넣을 데이터 준비
$.each(catgys["catgys"], function(index, value) {
if(value.code_ref_md == 0 && value.code_ref_mn == main_code) {
middle_catgy = new Object();
middle_catgy.code = value.code;
middle_catgy.name = value.name;
middle_catgy_arr.push(middle_catgy);
}
});
// 중분류 select 요소
var middle_select = $(".middle_select");
// 기존 대분류에 따른 중분류 및 소분류 옵션 삭제
$('.sub_select').html("<option value=''>--</option>");
// 중분류 옵션 추가
var html = "<option value=''>선택</option>";
$.each(middle_catgy_arr, function(index, value) {
html += "<option value='" + value.code + "'>" + value.name + "</option>";
});
middle_select.html(html);
}
});
// 중분류 select 요소가 변경되었을 때 실행
$(document).on("change", "select.middle_select", function() {
var sub_catgy_arr = new Array();
var sub_catgy = new Object();
var main_code = $('.main_select').val();
var middle_code = $(this).val();
// 소분류 select 박스에 넣을 데이터 준비
$.each(catgys["catgys"], function(index, value) {
if(value.code_ref_md == middle_code && value.code_ref_mn == main_code) {
sub_catgy = new Object();
sub_catgy.code = value.code;
sub_catgy.name = value.name;
sub_catgy_arr.push(sub_catgy);
}
});
// 소분류 select 요소
var sub_select = $(".sub_select");
// 기존 중분류에 따른 소분류 옵션 삭제
sub_select.html("<option value=''>--</option>");
// 소분류 select 박스에 옵션 추가
var html = "<option value=''>선택</option>";
$.each(sub_catgy_arr, function(index, value) {
html += "<option value='" + value.code + "'>" + value.name + "</option>";
});
sub_select.html(html);
});
});
위의 코드를 토대로 최종적으로 정리한 코드는 아래와 같다.
최종 코드
1. 도서 등록 페이지의 스크립트 부분
☞ <script>
$(document).ready(function() { });
</script>
JSP 페이지 <body> 하단에 위치한 JS 코드의 스크립트가 해당 HTML 문서가 완전히 로드된 후에 실행되도록 설정한다.
☞ $.catgys = ${catgys};
requestScope에 저장된 속성 catgys가 외부 JS 파일에서 사용되므로 전역변수에 저장한다.
☞ 외부 JS 파일 스크립트 위치
<body> 요소 하단에 포함된 JS 파일들은 일반적으로 상대적인 순서대로 읽힌다.
즉, 코드 상에서 위에서 아래로 작성된 순서대로 파일이 로드되고 실행되기 때문에 외부 파일을 변수 catgys를 선언한 스크립트 아래에 넣어준다.
<script type="text/javascript">
$(document).ready(function() {
$.catgys = ${catgys};
console.log($.catgys);
});
</script>
<script language=JavaScript src="/js/yj/book.select-catgy.js"></script>
2. 외부 JS 파일(book.select-catgy.js)
☞ 전역 변수 선언 및 초기화
대분류 / 중분류 / 소분류 데이터를 저장할 Array 타입의 변수를 전역 변수로 선언한다.
☞ 상수 선언
각각의 대분류 / 중분류 / 소분류 <select> 요소를 상수로 저장한다.
☞ function sort_catgys($.catgys);
서버에서 넘어온 카테고리 데이터를 대 / 중 / 소분류로 분류한다.
이 함수가 호출되면 각각의 전역 변수 *_catgy_arr에 대 / 중 / 소분류 데이터가 저장된다.
/**
* 도서 카테고리 분류
*/
$(document).ready(function() {
/* 전역 변수 선언 및 초기화 */
$.main_catgy_arr = new Array();
$.middle_catgy_arr = new Array();
$.sub_catgy_arr = new Array();
/* final 변수 선언 */
const main_select = $(".main_select");
const middle_select = $(".middle_select");
const sub_select = $(".sub_select");
/* 데이터 분류 */
sort_catgys($.catgys);
/* 대분류 select 박스에 데이터 삽입 */
$.each($.main_catgy_arr, function(index, value) {
main_select.append("<option value='" + value.code + "'>" + value.name + "</option>");
});
/** 대분류 select 요소가 변경되었을 때 실행 */
$(document).on("change", "select.main_select", function() {
/* 대분류 미선택시 중/소분류 옵션 표시 */
if($(this).val() == "") {
$('.middle_select, .sub_select').html("<option value=''>--</option>");
}
else {
let main_code = $(this).val();
// 기존 대분류에 따른 중분류 및 소분류 옵션 삭제
$('.sub_select').html("<option value=''>--</option>");
/* 중분류 옵션 추가 */
let html = "<option value=''>선택</option>";
$.each($.middle_catgy_arr, function(index, value) {
if(value.code_ref_mn == main_code) {
html += "<option value='" + value.code + "'>" + value.name + "</option>";
}
});
middle_select.html(html);
}
});
/** 중분류 select 요소가 변경되었을 때 실행 */
$(document).on("change", "select.middle_select", function() {
let main_code = $('.main_select').val();
let middle_code = $(this).val();
// 기존 중분류에 따른 소분류 옵션 삭제
sub_select.html("<option value=''>--</option>");
// 소분류 select 박스에 옵션 추가
let html = "<option value=''>선택</option>";
$.each($.sub_catgy_arr, function(index, value) {
if(value.code_ref_mn == main_code && value.code_ref_md == middle_code) {
html += "<option value='" + value.code + "'>" + value.name + "</option>";
}
});
sub_select.html(html);
});
/** 변수 catgys를 대/중/소분류로 분류하는 함수 */
function sort_catgys(obj) {
$.each(obj["catgys"], function(index, value) {
// 대분류
if(value.code_ref_md == 0 && value.code_ref_mn == 0) {
// init
let main_catgy = new Object();
main_catgy.code = value.code;
main_catgy.name = value.name;
// 전역 변수에 push
$.main_catgy_arr.push(main_catgy);
}
// 중분류
else if(value.code_ref_md == 0 && value.code_ref_mn !== 0) {
let middle_catgy = new Object();
middle_catgy.code = value.code;
middle_catgy.name = value.name;
middle_catgy.code_ref_mn = value.code_ref_mn;
$.middle_catgy_arr.push(middle_catgy);
}
// 소분류
else {
let sub_catgy = new Object();
sub_catgy.code = value.code;
sub_catgy.name = value.name;
sub_catgy.code_ref_md = value.code_ref_md;
sub_catgy.code_ref_mn = value.code_ref_mn;
$.sub_catgy_arr.push(sub_catgy);
}
});
}
});
이렇게 해서 도서 등록 페이지에서의 카테고리 구현이 완성되었다.
카테고리 구현 끝.
'JSP > MVC' 카테고리의 다른 글
[JSP][MVC][MySQL] 도서 사이트에서 다중 카테고리 구현하기 #1. 구현 틀 잡기 (2) | 2023.06.12 |
---|---|
[JSP][MVC][MySQL] 도서 사이트에서 다중 카테고리 구현하기 #3. 데이터 저장하기 (2) | 2023.06.07 |
[JSP][MVC][MySQL] 도서 사이트에서 다중 카테고리 구현하기 #2. 데이터 입력하기(클라 딴) (0) | 2023.06.05 |
[JSP][MVC][MySQL] 도서 등록 페이지 카테고리 구현하기 #2. 서버 딴 구현 (0) | 2023.05.31 |
[JSP][MVC][MySQL] 도서 등록 페이지 카테고리 구현하기 #1. 기본 세팅 (0) | 2023.05.31 |
[JSP][MVC][MySQL] Select 박스 옵션에 따른 페이징 처리 구현하기 #3. 로직 구현(마지막) (0) | 2023.05.27 |