Dynamic Pagination – xử lí phân trang

Giới thiệu

Hello những bạn, dạo gần đây cảm thấy lười viết blog quá, nhưng thời điểm ngày hôm nay mình mới tìm ra một chủ đề mới cho blog của mình 😄, đành phải bớt lười lại và viết bài viết này hy vọng nó giúp ích cho những bạn nhé 🔥 .
Như tất cả chúng ta đã biết, một website được xây dựng và hoạt động giải trí trong suốt khoảng chừng thời hạn đó thì việc những content mới sẽ được tạo ra và như thế thì website sẽ có rất nhiều content, để tăng vận tốc website cũng như thưởng thức người dùng tốt hơn ( UX ) thì tất cả chúng ta sử dụng Pagination – phân trang .
Hôm nay mình sẽ hướng dẫn cho những bạn một cách phân trang vận dụng cho hầu hết những trường hợp 😄 .

Dynamic Pagination

Đầu tiên chúng ta sẽ xem nó hoạt động như thế nào nhé:

Ở video trên mình đã số lượng giới hạn số trang là 10, những bạn hoàn toàn có thể test nhiều hơn 😄. Mình đã Truncate đi một vài link trang do đó tất cả chúng ta nhìn sẽ thấy gọn hơn rất nhiều .
Chúng ta sẽ cùng nhau khám phá về cách làm này nhé :
ở phần html, để đơn thuần mình sẽ chỉ tạo một thành phần để tiến hành code :

id

="pagination"

>

< / p div>

Đây là div mà từ Javascript sau khi có được số trang mình sẽ render hàng loạt link trang vào đây .
Phần Javascript :
Chúng ta sẽ lấy thành phần đã tạo ở trên, mình đặt thành phần này là pg :

const pg = document.getElementById(' pagination ');

Tiếp theo, khởi tạo một object chứa những thông tin thiết yếu cho pagination :

const valuePage = {
    truncate: true,  
    curPage: 1,  
    numLinksTwoSide: 1,  
    totalPages: 10,  
};

Mình sẽ giải thích giá trị numLinksTwoSide: 1, như mình đã giải thích ở trên thì đây là số liên kết hiển thị ở hai bên trang hiện tại. Giả sử mình đang ở trang thứ 5. và số lượng liên kết 2 bên ở trang thứ 5 mình muốn hiện thị là 1.

Ta sẽ được như hình sau đây :

ex1pg

Khởi tạo xong chúng ta cùng thực hiện tạo hàm pagination() để xử lí phân trang nhé 😄.

Trong hàm này tiên phong ta sẽ lấy những giá trị thiết yếu từ object valuePage để sử dụng. Mình dùng cú pháp destructuring assignment lấy những giá trị bên trong object .

function pagination() {
    const { totalPages, curPage, truncate, numLinksTwoSide: delta } =         valuePage;
}

Tiếp theo ta sẽ tạo một biến để kiểm tra giá trị delta và totalPages nếu tương thích với điều kiện kèm theo sẽ truncate. Mình gọi ràng buộc này là range :

const range = delta + 4; 

Biến này giúp ta trấn áp được số link bên trái Open và điều kiện kèm theo truncate nhờ vào một phần vào range .
Như ở video trên, số link bên trái = delta + 4 = 1 + 4 = 5

ex2pg

Nãy giờ hoàn toàn có thể những bạn vướng mắc số 4 này ở đâu ra vậy ta ? ? 🤨. Mình sẽ lý giải qua những hình ảnh để những bạn hiểu :
Giả sử mình muốn khi click vào số cuối của Left Side theo ví dụ là số 5, thì ta sẽ thực thi hành vi thu gọn những link trước lại. Để thu gọn thì mình sẽ số lượng giới hạn tối thiểu số trang bị rút gọn đi là 2 trang. Như hình trên mình đã thu gọn thành 1 … 4 5 ( bỏ trang 2,3 ) .
Điều kiện để thu gọn là lấy số trang hiện tại – số link muốn hiển thị phải lớn hơn 3 .
Mình sẽ thu gọn bên trái trước, bên phải sẽ tương tự như. Mình tạo một biến và làm như trên :

 
const numberTruncateLeft = curPage - delta;
const numberTruncateRight = curPage + delta;

Ví dụ : delta ( số link muốn hiển thị ở một bên trang hiện tại ) = 1, trang hiện tại là : 5 .
Ta tính được numberTruncateLeft = 5 – 1 = 4 > 3 ( Thu gọn được ). Tại sao lại lớn hơn 3 ? Vì sau khi chạy vòng for ta sẽ cho hiện những trang có index > 3 và chỉ số 4 sẽ được in ra ở bên trái trang hiện tại ( vì mình muốn số lượng trang hiển thị ở mỗi bên trang hiện tại là 1 => Từ trang hiện tại là 5 đi lùi về một số ít là 4 bên phải sẽ tăng lên 1 số là số 6 ) .
Ví dụ : delta = 1, trang hiện tại là : 4. numberTruncateLeft = 4 – 1 = 3 ( Không thu gọn ). Nếu bạn muốn thu gọn nó sẽ ra như này : 1 … 3 4

Như vậy chỉ có một trang bị thu gọn sẽ không hợp lý. Và đây chính là lí do mình số lượng giới hạn tối thiểu là 2 trang bị thu gọn. Do đó điều kiện kèm theo ta rút ra được là : numberTruncate = số trang hiện tại – số link muốn hiển thị một bên > 3

Một ví dụ nữa để những bạn hiểu hơn :
delta = 2 Trang hiện tại là 6
numberTruncateLeft = 6 – 2 = 4 ( Thu gọn ) .
Kết quả ta được :

ex3pg

Tới đây chắc những bạn đã hiểu ra sáng tạo độc đáo của cách phân trang này 😄. Nếu chưa hiểu thì liên tục nhé, mình sẽ lý giải tiếp :
Ở trên mình đã tiến hành một biến range = delta + 4 biến này khá quan trọng 👏. Vì mình muốn nếu thu gọn thì phải tối thiểu 2 thành phần bị thu gọn không tính số 1 nên range = delta + 4 .
Ví dụ : ta muốn số link muốn hiển thị một bên là delta = 2, range là số link bên trái hiển thị là 2 + 4 = 6
Như vậy khi bạn click vào số 6 dùng for ta lùi 2 số ta sẽ được : 1 … 4 5 6 .
Giải thích dài dòng nhưng mình muốn những bạn hiểu rõ hơn ^ ^ .
Sau đây ta tiến hành vòng lặp để hiển thị những link trang và xử lí truncate trong vòng for này nhé :

    let active = ' ';
    for (let pos = 1; pos < = totalPages; pos+ +) {
        active = pos = = curPage ? ' active ' : ' ';
        if (totalPages > = 2 * range - 

1

và và truncate) { ... } else { render + = renderPage(pos, active); } }

Trong vòng for mình đặt class “active” vào trang hiện tại.
Điều kiện thỏa mãn totalPages >= 2 * range - 1 && truncate sẽ thực hiện thu gọn liên kết trang nếu không thỏa sẽ hiển thị trang như bình thường. Mình sẽ giải thích điều kiền này sau.

Nếu thỏa ta sẽ chia ra ba trường hợp như video dưới :

3 Trường hợp đó là :

  • Thu gọn bên trái và cả bên phải
  • Thu gọn bên trái không thu gọn bên phải
  • Thu gọn bên phải không thu gọn bên trái

Mình sẽ lý giải khi code 3 trường hợp trên :
Trường hợp : Thu gọn bên trái và cả bên phải

Điều kiện:
numberTruncateLeft > 3 && numberTruncateRight < totalPages - 3 + 1
const numberTruncateLeft = curPage - delta;

Như mình đã giải thích ở trên để xảy ra thì số lượng liên kết muốn thu gọn một bên ít nhất là 2 do đó numberTruncateLeft = curPage - delta > 3.
Bên phải ta làm tương tự.

Ta sẽ lấy vị trí của những vị trí trang thỏa điều kiện kèm theo trên để hiển thị .

let renderTwoSide = ' ';
for (let pos = 1; pos < = totalPages; pos+ +) {
  active = pos = = curPage ? ' active ' : ' ';

   
  if (totalPages > = 2 * range - 1 và và truncate) {
    if (
      numberTruncateLeft > 3 và và
      numberTruncateRight < totalPages - 3 + 1
    ) {
       
      if (pos > = numberTruncateLeft và và pos < = numberTruncateRight) {
        renderTwoSide + = renderPage(pos, active);
      }
    } 
  } else {
     
    render + = renderPage(pos, active);
  }
}

Hình ảnh minh họa :

ex4pg

Nếu trường hợp trên không xảy ra ta sẽ thực thi code 2 trường hợp còn lại : Điều kiện xảy ra 2 trường hợp trên :

curPage < range và và pos < = range) | |
curPage > totalPages - range và và pos > = totalPages - range + 1)

Mình sẽ từ vị trí trang hiện tại tìm thành phần có vị trí thuộc vùng range nếu trang hiện tại ở trong vùng này. Trường hợp trang hiện tại nằm bên phải ta chỉ việc làm ngược lại trường hợp trên .

Trường hợp đặc biệt quan trọng là trang hiện tại nằm trong cả vùng range và vùng bên phải ví dụ trang hiện tại là 4 và tổng số trang là 7. Giả sử số link hiển thị 1 bên là delta = 1 => range = 4 + 1 = 5 như vậy trang hiện tại là 4 nằm trong vùng range và trang hiện tại cũng thuộc vùng bên phải. Điều này gây cho ta việc thu gọn trang ngoài ý muốn

Để tránh điều này mình đã thêm điều kiện kèm theo ở trên totalPages > = 2 * range - 1
Hình minh họa :

ex5pg

Xem thêm: Services là gì?

Để những bạn có cái hình tổng quát hơn thì tất cả chúng ta cùng xem hàng loạt phần code nhé :

Kết luận

Như vầy là tất cả chúng ta đã thực thi xử lí xong phần Dynamic Pagination rồi. Nếu có vướng mắc gì về bài viết những bạn hoàn toàn có thể liên hệ mình nhé .
Chúc những bạn học tốt 😃 .