mirror of
https://github.com/prymitive/karma
synced 2026-05-13 03:56:59 +00:00
fix(ui): use a custom pagination component
This commit is contained in:
committed by
Łukasz Mierzwa
parent
c454601b3b
commit
9171a529ca
1001
ui/package-lock.json
generated
1001
ui/package-lock.json
generated
File diff suppressed because it is too large
Load Diff
@@ -43,7 +43,6 @@
|
||||
"react-hotkeys-hook": "3.4.4",
|
||||
"react-idle-timer": "4.6.4",
|
||||
"react-intersection-observer": "8.33.1",
|
||||
"react-js-pagination": "3.0.3",
|
||||
"react-json-pretty": "2.2.0",
|
||||
"react-linkify": "0.2.2",
|
||||
"react-media-hook": "0.4.9",
|
||||
@@ -76,7 +75,6 @@
|
||||
"@types/qs": "6.9.7",
|
||||
"@types/react": "17.0.38",
|
||||
"@types/react-dom": "17.0.11",
|
||||
"@types/react-js-pagination": "3.0.4",
|
||||
"@types/semver": "7.3.9",
|
||||
"@wojtekmaj/enzyme-adapter-react-17": "0.6.6",
|
||||
"diffable-html": "5.0.0",
|
||||
|
||||
@@ -58,6 +58,54 @@ describe("<PageSelect />", () => {
|
||||
expect(setPageCallback).toHaveBeenLastCalledWith(1);
|
||||
});
|
||||
|
||||
it("calls setPageCallback on button press", () => {
|
||||
const setPageCallback = jest.fn();
|
||||
|
||||
const tree = mount(
|
||||
<PageSelect
|
||||
totalPages={15}
|
||||
maxPerPage={5}
|
||||
totalItemsCount={15 * 5}
|
||||
setPageCallback={setPageCallback}
|
||||
/>
|
||||
);
|
||||
tree.simulate("focus");
|
||||
|
||||
for (const elem of [
|
||||
{ index: 0, page: 1, label: "" }, // <<
|
||||
{ index: 1, page: 1, label: "" }, // <
|
||||
{ index: 2, page: 1, label: "1" }, // <<12345>> -> <<12345>>
|
||||
{ index: 3, page: 2, label: "2" }, // <<12345>> -> <<12345>>
|
||||
{ index: 4, page: 3, label: "3" }, // <<12345>> -> <<12345>>
|
||||
{ index: 5, page: 4, label: "4" }, // <<12345>> -> <<23456>>
|
||||
{ index: 4, page: 4, label: "4" }, // <<23456>> -> <<23456>>
|
||||
{ index: 0, page: 1, label: "" }, // <<23456>> -> <<12345>>
|
||||
{ index: 6, page: 5, label: "5" }, // <<12345>> -> <<34567>>
|
||||
{ index: 7, page: 6, label: "" }, // <<34567>> -> <<45678>>
|
||||
{ index: 1, page: 5, label: "" }, // <<34567>> -> <<23456>>
|
||||
{ index: 8, page: 15, label: "" }, // <<23456>> -> <<end>>
|
||||
]) {
|
||||
expect(tree.find("button.page-link").at(elem.index).text()).toBe(
|
||||
elem.label
|
||||
);
|
||||
tree.find("button.page-link").at(elem.index).simulate("click");
|
||||
expect(setPageCallback).toHaveBeenLastCalledWith(elem.page);
|
||||
}
|
||||
});
|
||||
|
||||
it("doesn't render anything if totalItemsCount <= maxPerPage", () => {
|
||||
global.innerWidth = 1024;
|
||||
const tree = mount(
|
||||
<PageSelect
|
||||
totalPages={1}
|
||||
maxPerPage={5}
|
||||
totalItemsCount={5}
|
||||
setPageCallback={jest.fn()}
|
||||
/>
|
||||
);
|
||||
expect(tree.find(".page-link")).toHaveLength(0);
|
||||
});
|
||||
|
||||
it("renders 5 page range on desktop", () => {
|
||||
global.innerWidth = 1024;
|
||||
const tree = mount(
|
||||
|
||||
@@ -2,8 +2,6 @@ import { useState, useEffect, FC } from "react";
|
||||
|
||||
import { useHotkeys } from "react-hotkeys-hook";
|
||||
|
||||
import Pagination from "react-js-pagination";
|
||||
|
||||
import { FontAwesomeIcon } from "@fortawesome/react-fontawesome";
|
||||
import { faAngleLeft } from "@fortawesome/free-solid-svg-icons/faAngleLeft";
|
||||
import { faAngleRight } from "@fortawesome/free-solid-svg-icons/faAngleRight";
|
||||
@@ -27,6 +25,7 @@ const PageSelect: FC<{
|
||||
initialPage = 1,
|
||||
setPageCallback,
|
||||
}) => {
|
||||
const [pages, setPages] = useState<number[]>([]);
|
||||
const [activePage, setActivePage] = useState<number>(initialPage);
|
||||
|
||||
const onChange = (page: number) => {
|
||||
@@ -34,13 +33,30 @@ const PageSelect: FC<{
|
||||
setPageCallback(page);
|
||||
};
|
||||
|
||||
useEffect(() => {
|
||||
const allPages = Array.from(Array(totalPages).keys()).map((k) => k + 1);
|
||||
const gap = IsMobile() ? 1 : 2;
|
||||
|
||||
let minPage = activePage - gap;
|
||||
let maxPage = activePage + gap;
|
||||
if (minPage < 1) {
|
||||
maxPage = Math.min(maxPage + -minPage + 1, totalPages);
|
||||
minPage = 1;
|
||||
}
|
||||
if (maxPage > totalPages) {
|
||||
minPage = Math.max(1, minPage - (maxPage - totalPages));
|
||||
maxPage = totalPages;
|
||||
}
|
||||
setPages(allPages.slice(minPage - 1, maxPage));
|
||||
}, [activePage, totalPages]);
|
||||
|
||||
useEffect(() => {
|
||||
if (activePage > totalPages) {
|
||||
const page = Math.max(1, totalPages);
|
||||
setActivePage(page);
|
||||
setPageCallback(page);
|
||||
}
|
||||
}, [activePage, maxPerPage, totalPages, setPageCallback]);
|
||||
}, [activePage, totalPages, setPageCallback]);
|
||||
|
||||
useHotkeys(
|
||||
"left",
|
||||
@@ -67,25 +83,65 @@ const PageSelect: FC<{
|
||||
return (
|
||||
<div className="components-pagination">
|
||||
{totalItemsCount > maxPerPage ? (
|
||||
<div className="mt-3">
|
||||
<Pagination
|
||||
<ul className="pagination justify-content-center mt-3">
|
||||
{totalPages >= 10 ? (
|
||||
<li className={`page-item ${activePage > 1 ? "" : "disabled"}`}>
|
||||
<button className="page-link" onClick={() => onChange(1)}>
|
||||
<FontAwesomeIcon icon={faAngleDoubleLeft} />
|
||||
</button>
|
||||
</li>
|
||||
) : null}
|
||||
<li className={`page-item ${activePage > 1 ? "" : "disabled"}`}>
|
||||
<button
|
||||
className="page-link"
|
||||
onClick={() => onChange(Math.max(1, activePage - 1))}
|
||||
>
|
||||
<FontAwesomeIcon icon={faAngleLeft} />
|
||||
</button>
|
||||
</li>
|
||||
{pages.map((page) => (
|
||||
<li
|
||||
key={page}
|
||||
className={`page-item ${
|
||||
page === activePage ? "active font-weight-bold" : ""
|
||||
}`}
|
||||
>
|
||||
<button className="page-link" onClick={() => onChange(page)}>
|
||||
{page}
|
||||
</button>
|
||||
</li>
|
||||
))}
|
||||
<li
|
||||
className={`page-item ${activePage < totalPages ? "" : "disabled"}`}
|
||||
>
|
||||
<button
|
||||
className="page-link"
|
||||
onClick={() => onChange(Math.min(activePage + 1, totalPages))}
|
||||
>
|
||||
<FontAwesomeIcon icon={faAngleRight} />
|
||||
</button>
|
||||
</li>
|
||||
{totalPages >= 10 ? (
|
||||
<li
|
||||
className={`page-item ${
|
||||
activePage < totalPages ? "" : "disabled"
|
||||
}`}
|
||||
>
|
||||
<button
|
||||
className="page-link"
|
||||
onClick={() => onChange(totalPages)}
|
||||
>
|
||||
<FontAwesomeIcon icon={faAngleDoubleRight} />
|
||||
</button>
|
||||
</li>
|
||||
) : null}
|
||||
{/* <Pagination
|
||||
activePage={activePage}
|
||||
itemsCountPerPage={maxPerPage}
|
||||
totalItemsCount={totalItemsCount}
|
||||
pageRangeDisplayed={IsMobile() ? 3 : 5}
|
||||
onChange={onChange}
|
||||
hideFirstLastPages={totalPages < 10}
|
||||
innerClass="pagination justify-content-center"
|
||||
itemClass="page-item"
|
||||
linkClass="page-link"
|
||||
activeClass="active"
|
||||
activeLinkClass="font-weight-bold"
|
||||
prevPageText={<FontAwesomeIcon icon={faAngleLeft} />}
|
||||
nextPageText={<FontAwesomeIcon icon={faAngleRight} />}
|
||||
firstPageText={<FontAwesomeIcon icon={faAngleDoubleLeft} />}
|
||||
lastPageText={<FontAwesomeIcon icon={faAngleDoubleRight} />}
|
||||
/>
|
||||
</div>
|
||||
/> */}
|
||||
</ul>
|
||||
) : null}
|
||||
</div>
|
||||
);
|
||||
|
||||
@@ -12,85 +12,63 @@ exports[`<SilencePreview /> matches snapshot 1`] = `
|
||||
</ul>
|
||||
</div>
|
||||
<div class=\\"components-pagination\\">
|
||||
<div class=\\"mt-3\\">
|
||||
<ul class=\\"pagination justify-content-center\\">
|
||||
<li class=\\"page-item disabled\\">
|
||||
<a
|
||||
class=\\"page-link\\"
|
||||
href=\\"#\\"
|
||||
aria-label=\\"Go to previous page\\"
|
||||
<ul class=\\"pagination justify-content-center mt-3\\">
|
||||
<li class=\\"page-item disabled\\">
|
||||
<button class=\\"page-link\\">
|
||||
<svg
|
||||
aria-hidden=\\"true\\"
|
||||
focusable=\\"false\\"
|
||||
data-prefix=\\"fas\\"
|
||||
data-icon=\\"angle-left\\"
|
||||
class=\\"svg-inline--fa fa-angle-left fa-w-8 \\"
|
||||
role=\\"img\\"
|
||||
xmlns=\\"http://www.w3.org/2000/svg\\"
|
||||
viewbox=\\"0 0 256 512\\"
|
||||
>
|
||||
<svg
|
||||
aria-hidden=\\"true\\"
|
||||
focusable=\\"false\\"
|
||||
data-prefix=\\"fas\\"
|
||||
data-icon=\\"angle-left\\"
|
||||
class=\\"svg-inline--fa fa-angle-left fa-w-8 \\"
|
||||
role=\\"img\\"
|
||||
xmlns=\\"http://www.w3.org/2000/svg\\"
|
||||
viewbox=\\"0 0 256 512\\"
|
||||
<path
|
||||
fill=\\"currentColor\\"
|
||||
d=\\"M31.7 239l136-136c9.4-9.4 24.6-9.4 33.9 0l22.6 22.6c9.4 9.4 9.4 24.6 0 33.9L127.9 256l96.4 96.4c9.4 9.4 9.4 24.6 0 33.9L201.7 409c-9.4 9.4-24.6 9.4-33.9 0l-136-136c-9.5-9.4-9.5-24.6-.1-34z\\"
|
||||
>
|
||||
<path
|
||||
fill=\\"currentColor\\"
|
||||
d=\\"M31.7 239l136-136c9.4-9.4 24.6-9.4 33.9 0l22.6 22.6c9.4 9.4 9.4 24.6 0 33.9L127.9 256l96.4 96.4c9.4 9.4 9.4 24.6 0 33.9L201.7 409c-9.4 9.4-24.6 9.4-33.9 0l-136-136c-9.5-9.4-9.5-24.6-.1-34z\\"
|
||||
>
|
||||
</path>
|
||||
</svg>
|
||||
</a>
|
||||
</li>
|
||||
<li class=\\"page-item active\\">
|
||||
<a
|
||||
class=\\"page-link font-weight-bold\\"
|
||||
href=\\"#\\"
|
||||
aria-label=\\"Go to page number 1\\"
|
||||
</path>
|
||||
</svg>
|
||||
</button>
|
||||
</li>
|
||||
<li class=\\"page-item active font-weight-bold\\">
|
||||
<button class=\\"page-link\\">
|
||||
1
|
||||
</button>
|
||||
</li>
|
||||
<li class=\\"page-item \\">
|
||||
<button class=\\"page-link\\">
|
||||
2
|
||||
</button>
|
||||
</li>
|
||||
<li class=\\"page-item \\">
|
||||
<button class=\\"page-link\\">
|
||||
3
|
||||
</button>
|
||||
</li>
|
||||
<li class=\\"page-item \\">
|
||||
<button class=\\"page-link\\">
|
||||
<svg
|
||||
aria-hidden=\\"true\\"
|
||||
focusable=\\"false\\"
|
||||
data-prefix=\\"fas\\"
|
||||
data-icon=\\"angle-right\\"
|
||||
class=\\"svg-inline--fa fa-angle-right fa-w-8 \\"
|
||||
role=\\"img\\"
|
||||
xmlns=\\"http://www.w3.org/2000/svg\\"
|
||||
viewbox=\\"0 0 256 512\\"
|
||||
>
|
||||
1
|
||||
</a>
|
||||
</li>
|
||||
<li class=\\"page-item\\">
|
||||
<a
|
||||
class=\\"page-link\\"
|
||||
href=\\"#\\"
|
||||
aria-label=\\"Go to page number 2\\"
|
||||
>
|
||||
2
|
||||
</a>
|
||||
</li>
|
||||
<li class=\\"page-item\\">
|
||||
<a
|
||||
class=\\"page-link\\"
|
||||
href=\\"#\\"
|
||||
aria-label=\\"Go to page number 3\\"
|
||||
>
|
||||
3
|
||||
</a>
|
||||
</li>
|
||||
<li class=\\"page-item\\">
|
||||
<a
|
||||
class=\\"page-link\\"
|
||||
href=\\"#\\"
|
||||
aria-label=\\"Go to next page\\"
|
||||
>
|
||||
<svg
|
||||
aria-hidden=\\"true\\"
|
||||
focusable=\\"false\\"
|
||||
data-prefix=\\"fas\\"
|
||||
data-icon=\\"angle-right\\"
|
||||
class=\\"svg-inline--fa fa-angle-right fa-w-8 \\"
|
||||
role=\\"img\\"
|
||||
xmlns=\\"http://www.w3.org/2000/svg\\"
|
||||
viewbox=\\"0 0 256 512\\"
|
||||
<path
|
||||
fill=\\"currentColor\\"
|
||||
d=\\"M224.3 273l-136 136c-9.4 9.4-24.6 9.4-33.9 0l-22.6-22.6c-9.4-9.4-9.4-24.6 0-33.9l96.4-96.4-96.4-96.4c-9.4-9.4-9.4-24.6 0-33.9L54.3 103c9.4-9.4 24.6-9.4 33.9 0l136 136c9.5 9.4 9.5 24.6.1 34z\\"
|
||||
>
|
||||
<path
|
||||
fill=\\"currentColor\\"
|
||||
d=\\"M224.3 273l-136 136c-9.4 9.4-24.6 9.4-33.9 0l-22.6-22.6c-9.4-9.4-9.4-24.6 0-33.9l96.4-96.4-96.4-96.4c-9.4-9.4-9.4-24.6 0-33.9L54.3 103c9.4-9.4 24.6-9.4 33.9 0l136 136c9.5 9.4 9.5 24.6.1 34z\\"
|
||||
>
|
||||
</path>
|
||||
</svg>
|
||||
</a>
|
||||
</li>
|
||||
</ul>
|
||||
</div>
|
||||
</path>
|
||||
</svg>
|
||||
</button>
|
||||
</li>
|
||||
</ul>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
@@ -1,3 +1,8 @@
|
||||
.components-pagination:focus {
|
||||
outline: none;
|
||||
}
|
||||
|
||||
button.page-link:focus {
|
||||
color: $pagination-hover-color;
|
||||
background-color: $pagination-hover-bg;
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user