JS-Tech/resj

View on GitHub
app/javascript/controllers/list_controller.js

Summary

Maintainability
A
0 mins
Test Coverage
import { Controller } from "@hotwired/stimulus"

export default class ListController extends Controller {
  static targets = ["numberTemplate", "items", "number", "numbers", "previous", "next", "total"]

  items;

  updateItems(items) {
    this.items = items;
    this.update();
  }

  update() {
    this.itemsTarget.innerHTML = "";
    let content = ""
    if (this.items.length == 0) {
      content = this.notFoundMessage
    } else {
      const start = (this.currentPage - 1) * this.itemPerPage;
      let items = this.items.slice(start, start + this.itemPerPage);
      const updatedList = this.updateList(items);
      for (let i in updatedList) {
        content += updatedList[i];
      }
    }
    this.itemsTarget.innerHTML = content;
    this.updateMap(this.items);
    this.updatePagination();
    this.totalTarget.innerHTML = this.items.length;
  }

  updatePagination() {
    this.numbersTarget.innerHTML = "";
    for (let i = 1; i <= this.numberOfPages; i++) {
      this.numberTarget.innerHTML = i;
      this.numberTarget.classList.toggle("current", i == this.currentPage);
      this.numbersTarget.innerHTML += this.numberTemplateTarget.innerHTML;
    }
    this.previousTarget.classList.toggle("current", this.currentPage > 1);
    this.nextTarget.classList.toggle("current", this.currentPage < this.numberOfPages);
  }

  previous() {
    if (this.currentPage <= 1) throw "Current page is already the first.";
    this.currentPage--;
    this.update();
  }

  next() {
    if (this.currentPage >= this.numberOfPages) throw "Current page is already the last.";
    this.currentPage++;
    this.update();
  }

  go(event) {
    event.preventDefault();
    this.currentPage = event.target.innerHTML;
    this.update();
  }

  get currentPage() {
    return this.data.get("page");
  }

  set currentPage(i) {
    if (i <= 0) throw "Current page cannot be equal or lower than zero.";
    if (i > this.numberOfPages) throw "Current page cannot be greater than the total number"
    this.data.set("page", i);
  }

  get numberOfPages() {
    return Math.ceil(this.items.length / this.itemPerPage);
  }

  updateList(items) {
    throw "#updateList must be defined in the child class."
  }

  updateMap(items) {
    throw "#updateMap must be defined in the child class."
  }

  get itemPerPage() {
    throw "Getter #itemPerPage must be defined in the child class"
  }

  get notFoundMessage() {
    return `<div class="soon">Aucun résultat</div>`
  }

}