본문 바로가기

BACK

[SpringBoot JSP] 게시판-페이징 처리/방법 1

728x90

1. domin 작성 (Page.java)

 

1) 필드 생성

- 최소 페이지 번호 min

- 최대 페이지 번호 max

- 이전 버튼의 페이지 번호 prevPage

- 다음 버튼의 페이지 번호 nextPage

- 전체 페이지 개수 pageCnt

- 현재 페이지 번호 currentPage

 

2) 생성자 생성

contentCnt : 전체글 개수,

currentPage : 현재 페이지 번호,

contentPageCnt : 페이지당 글의 개수,

paginationCnt : 페이지 버튼의 개수


public Page(int contentCnt, int currentPage, int contentPageCnt, int paginationCnt){

}

 

3) 생성자 = 선언과 동시에 초기화하여 사용할 수 있으므로 

                생성자 안 로직을 다른 클래스에서 바로 불러올 수 있다

                단, Page 변수 = new Page(~,~,~,~) 매개변수 갯수는 같아야하지만 매개변수 이름은 달라도 된다.

package com.example.crud.domain;

import lombok.Getter;
import lombok.Setter;

@Getter
@Setter
public class Page {

    // 최소 페이지 번호
    private int min;
    // 최대 페이지 번호
    private int max;

    // 이전 버튼의 페이지 번호
    private int prevPage;
    // 다음 버튼의 페이지 번호
    private int nextPage;

    // 전체 페이지 개수
    private int pageCnt;
    // 현재 페이지 번호
    private int currentPage;

    /*
     1) 1~10 : 1(최소), 10(최대)
        11~20 : 11(최소), 20(최대)
        21~30 : 21(최소), 30(최대)

     2) (currentPage-1) : 최대번호는 최소에 9를 더하므로 (10)-1을 계산해줌

     3) 페이지 당 글의 개수 나눔

     4) 페이지당 글의 개수로 다시 곱함
     */

    //-----------------------------------

    // contentCnt : 전체글 개수, currentPage : 현재 페이지 번호, contentPageCnt : 페이지당 글의 개수, paginationCnt : 페이지 버튼의 개수
    public Page(int contentCnt, int currentPage, int contentPageCnt, int paginationCnt){

        //현재 페이지 번호
        this.currentPage = currentPage;

        //전체 페이지 개수 (전체 글 개수 / 페이지당 글의 개수)
        pageCnt = contentCnt / contentPageCnt;
        //ex) 533/10=53.3이므로 나머지가 3이므로 1page 더 필요
        if(contentCnt % contentPageCnt > 0){
            pageCnt++;
        }

        //--------------------------------

        //최소값 = ((현재 페이지 번호-1) / 페이지 당 글의 개수) * 페이지 당 글의 개수 + 1
        //ex) ((1-1)/10)*10+1=1
        //    ((2-1)/10)*10+1=2
        //    ((3-1)/10)*10+1=3

        //ex) ((4-1)/11)*11+1=4
        //    ((5-1)/11)*11+1=5
        min = ((currentPage-1) / contentPageCnt) * contentPageCnt +1;

        //최대값 = min +  페이지 버튼의 개수
        //ex) 1 + 2 - 1 = 2 (페이지 버튼의 개수:2, 최소값:1 , 페이지 당 글의 개수:10)
        //(1,2)
        //ex) 4 + 10 -1 = 13 (페이지 버튼의 개수:10, 최소값:4 , 페이지 당 글의 개수:11)
        //(4,5,6,7,8,9,10,11,12,13)
        max = min + paginationCnt -1;

        //1페이지에 1~9번째 글이 존재할경우 max=1+2-1=2, pageCnt=10/9=1.1 -> 2페이지 필요
        //전체페이지를 넘어가지 않도록 세팅함
        if(max > pageCnt){
            max=pageCnt;
        }

        //---------------------------------------

        //이전페이지 누를경우
        prevPage = min-1;
        //다음페이지 누를경우
        nextPage = max+1;

        //마지막페이지를 넘어가지 않도록
        if(nextPage > pageCnt){
            nextPage = pageCnt;
        }

     }
}

 

2. repository

Repository에서 페이지 수 메소드 작성

//글 표시(select)
List<Content> appearNoticeInfo(RowBounds rowBounds);
int getPageCount();

 

3. xml

<!--2. 글내용 표시(select)-->
<select id="appearNoticeInfo" resultType="Content">
    select * from taehan.CONTENT ORDER BY contentIdx DESC
</select>

 

페이지 수가 몇 개 있는지 확인하기 위해 contentIdx로 카운트 한다.

<!--페이지 수(문의)-->
<select id="getPageCount" resultType="int">
    select count(contentIdx) from tae.CONTENT
</select>

 

4. service

-RowBounds 활용

더보기

RowBounds row = new RowBounds(offset , limit);
RowBounds 객체는 위와 같이 선언하여서 사용한다.

offset은 데이터를 가져오는 시작점에서 얼마나 떨어진 데이터인지를 의미하며
limit은 몇 개의 값을 가져올지를 의미한다.

//2. 글내용 표시(select)
public List<Content> appearNoticeInfo(int page){

    int start = (page-1)*contentPageCnt; //(2-1)*10=10 / (3-1)*10=20
    RowBounds rowBounds=new RowBounds(start,contentPageCnt); //0부터 시작해서 10개씩

    List<Content> boardAllList = noticeRepository.appearNoticeInfo(rowBounds);
    return boardAllList;
}

- 페이지에서 만든 생성자 불러와서 page로 리턴함

//페이지 수
// currentPage:현재 페이지 번호
public Page getPageCount(int currentPage){

    //전체 글의 갯수
    int contentsCnt = noticeRepository.getPageCount();
    Page page = new Page(contentsCnt, currentPage, contentPageCnt, paginationcnt);
    return page;

}

 

5. controller

//문의하기
//http://localhost8082/questions
@RequestMapping(path = "questions")
public ModelAndView questions(Model model, @RequestParam(defaultValue = "1") int pages) {
    // 등록된 게시판 불러오기
    List<Content> contents= noticeService.appearNoticeInfo(pages);
    // 모델에 담기
    model.addAttribute("contents", contents);

    //페이징처리
    Page pageCount = noticeService.getPageCount(pages);
    //모델에 담기
    model.addAttribute("pageCount",pageCount);

    return new ModelAndView("/notice/questions");
}

 

6. view

 <div class="community_pagination__V9VQ1">
        <div class="Pagination_container__SunX5">

            <c:choose>

                <c:when test="${pageCount.currentPage <=1}">
                    <a href="#" class="page-link">이전</a>
                </c:when>

                <c:otherwise>
                    <a href="questions?pages=${pageCount.currentPage-1}" class="page-link">이전</a>
                </c:otherwise>

            </c:choose>

            <div class="Pagination_pageWrapper__P796x">
                <c:forEach var='idx' begin="${ pageCount.min }" end="${ pageCount.max }">
                    <c:if test="${idx==pageCount.currentPage}">
                        <%--최소값에서 최대값까지 돌때 idx가 현재페이지와 같으면 보라색--%>
                        <a href="questions?pages=${idx}" class="Pagination_page__T9uPQ Pagination_selected__AWwCP">${ idx }</a>
                    </c:if>
                    <c:if test="${idx!=pageCount.currentPage}">
                         <%--최소값에서 최대값까지 돌때 idx가 현재페이지와 다르면 무색--%>-
                        <a href="questions?pages=${idx}" class="Pagination_page__T9uPQ" >${ idx }</a>
                    </c:if>
                </c:forEach>
            </div>

            <c:choose>
                <%--전체페이지 수 보다 현재페이지번호가 크거나 같으면 페이지 넘어가지 않게--%>
                <c:when test="${pageCount.currentPage >= pageCount.pageCnt}">
                    <a href="#" class="page-link">다음</a>
                </c:when>
                <c:otherwise>
                    <a href="questions?pages=${pageCount.currentPage+1}" class="page-link">다음</a>
                </c:otherwise>
            </c:choose>
        </div>

    </div>
</div>
728x90