@schukai/monster 3.55.0 → 3.55.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (99) hide show
  1. package/CHANGELOG.md +16 -0
  2. package/package.json +1 -1
  3. package/source/components/datatable/datasource/rest.mjs +313 -326
  4. package/source/components/datatable/datatable/header.mjs +1 -1
  5. package/source/components/datatable/datatable.mjs +586 -591
  6. package/source/components/datatable/embedded-pagination.mjs +42 -49
  7. package/source/components/datatable/filter/util.mjs +115 -99
  8. package/source/components/datatable/filter.mjs +901 -842
  9. package/source/components/datatable/pagination.mjs +333 -334
  10. package/source/components/datatable/status.mjs +134 -156
  11. package/source/components/datatable/stylesheet/column-bar.mjs +14 -8
  12. package/source/components/datatable/stylesheet/dataset.mjs +14 -8
  13. package/source/components/datatable/stylesheet/datasource.mjs +14 -8
  14. package/source/components/datatable/stylesheet/datatable.mjs +14 -8
  15. package/source/components/datatable/stylesheet/embedded-pagination.mjs +14 -8
  16. package/source/components/datatable/stylesheet/filter-button.mjs +14 -8
  17. package/source/components/datatable/stylesheet/filter-controls-defaults.mjs +14 -8
  18. package/source/components/datatable/stylesheet/filter-date-range.mjs +14 -8
  19. package/source/components/datatable/stylesheet/filter-range.mjs +14 -8
  20. package/source/components/datatable/stylesheet/filter.mjs +14 -8
  21. package/source/components/datatable/stylesheet/pagination.mjs +14 -8
  22. package/source/components/datatable/stylesheet/select-filter.mjs +14 -8
  23. package/source/components/datatable/stylesheet/status.mjs +14 -8
  24. package/source/components/form/action-button.mjs +3 -1
  25. package/source/components/form/confirm-button.mjs +3 -1
  26. package/source/components/form/context-error.mjs +161 -164
  27. package/source/components/form/context-help.mjs +3 -1
  28. package/source/components/form/form.mjs +3 -1
  29. package/source/components/form/message-state-button.mjs +3 -1
  30. package/source/components/form/popper-button.mjs +6 -4
  31. package/source/components/form/popper.mjs +310 -310
  32. package/source/components/form/select.mjs +2 -2
  33. package/source/components/form/state-button.mjs +3 -1
  34. package/source/components/form/stylesheet/action-button.mjs +14 -8
  35. package/source/components/form/stylesheet/api-button.mjs +14 -8
  36. package/source/components/form/stylesheet/button-bar.mjs +14 -8
  37. package/source/components/form/stylesheet/button.mjs +14 -8
  38. package/source/components/form/stylesheet/confirm-button.mjs +14 -8
  39. package/source/components/form/stylesheet/context-error.mjs +14 -8
  40. package/source/components/form/stylesheet/context-help.mjs +14 -8
  41. package/source/components/form/stylesheet/form.mjs +14 -8
  42. package/source/components/form/stylesheet/message-state-button.mjs +14 -8
  43. package/source/components/form/stylesheet/popper-button.mjs +14 -8
  44. package/source/components/form/stylesheet/popper.mjs +14 -8
  45. package/source/components/form/stylesheet/select.mjs +14 -8
  46. package/source/components/form/stylesheet/state-button.mjs +14 -8
  47. package/source/components/form/stylesheet/tabs.mjs +14 -8
  48. package/source/components/form/stylesheet/tree-select.mjs +14 -8
  49. package/source/components/form/tabs.mjs +754 -758
  50. package/source/components/host/collapse.mjs +2 -4
  51. package/source/components/host/config-manager.mjs +11 -9
  52. package/source/components/host/stylesheet/call-button.mjs +14 -8
  53. package/source/components/host/stylesheet/collapse.mjs +14 -8
  54. package/source/components/host/stylesheet/config-manager.mjs +14 -8
  55. package/source/components/host/stylesheet/details.mjs +14 -8
  56. package/source/components/host/stylesheet/host.mjs +14 -8
  57. package/source/components/host/stylesheet/overlay.mjs +14 -8
  58. package/source/components/host/stylesheet/toggle-button.mjs +14 -8
  59. package/source/components/host/stylesheet/viewer.mjs +14 -8
  60. package/source/components/host/util.mjs +2 -2
  61. package/source/components/notify/stylesheet/message.mjs +14 -8
  62. package/source/components/notify/stylesheet/notify.mjs +14 -8
  63. package/source/components/state/stylesheet/log.mjs +14 -8
  64. package/source/components/state/stylesheet/state.mjs +14 -8
  65. package/source/components/stylesheet/badge.mjs +14 -8
  66. package/source/components/stylesheet/border.mjs +14 -8
  67. package/source/components/stylesheet/button.mjs +14 -8
  68. package/source/components/stylesheet/card.mjs +14 -8
  69. package/source/components/stylesheet/color.mjs +14 -8
  70. package/source/components/stylesheet/common.mjs +14 -8
  71. package/source/components/stylesheet/control.mjs +14 -8
  72. package/source/components/stylesheet/data-grid.mjs +14 -8
  73. package/source/components/stylesheet/display.mjs +14 -8
  74. package/source/components/stylesheet/floating-ui.mjs +14 -8
  75. package/source/components/stylesheet/form.mjs +14 -8
  76. package/source/components/stylesheet/host.mjs +14 -8
  77. package/source/components/stylesheet/icons.mjs +14 -8
  78. package/source/components/stylesheet/link.mjs +14 -8
  79. package/source/components/stylesheet/normalize.mjs +14 -8
  80. package/source/components/stylesheet/popper.mjs +14 -8
  81. package/source/components/stylesheet/property.mjs +14 -8
  82. package/source/components/stylesheet/ripple.mjs +14 -8
  83. package/source/components/stylesheet/skeleton.mjs +14 -8
  84. package/source/components/stylesheet/space.mjs +14 -8
  85. package/source/components/stylesheet/spinner.mjs +14 -8
  86. package/source/components/stylesheet/table.mjs +14 -8
  87. package/source/components/stylesheet/theme.mjs +14 -8
  88. package/source/components/stylesheet/typography.mjs +14 -8
  89. package/source/components/tree-menu/stylesheet/tree-menu.mjs +14 -8
  90. package/source/data/transformer.mjs +6 -8
  91. package/source/dom/attributes.mjs +5 -5
  92. package/source/dom/customelement.mjs +1 -1
  93. package/source/dom/updater.mjs +697 -700
  94. package/source/dom/util.mjs +2 -2
  95. package/source/monster.mjs +0 -1
  96. package/source/types/noderecursiveiterator.mjs +9 -7
  97. package/source/types/version.mjs +1 -1
  98. package/source/util/sleep.mjs +3 -4
  99. package/test/cases/monster.mjs +1 -1
@@ -4,32 +4,32 @@
4
4
  */
5
5
 
6
6
  import {
7
- assembleMethodSymbol,
8
- CustomElement,
9
- registerCustomElement,
7
+ assembleMethodSymbol,
8
+ CustomElement,
9
+ registerCustomElement,
10
10
  } from "../../dom/customelement.mjs";
11
- import {ThemeStyleSheet} from "../stylesheet/theme.mjs";
12
- import {ATTRIBUTE_DATASOURCE_SELECTOR} from "./constants.mjs";
13
- import {Datasource} from "./datasource.mjs";
14
- import {Observer} from "../../types/observer.mjs";
15
- import {ATTRIBUTE_ROLE} from "../../dom/constants.mjs";
16
- import {findTargetElementFromEvent} from "../../dom/events.mjs";
17
- import {EmbeddedPaginationStyleSheet} from "./stylesheet/embedded-pagination.mjs";
18
- import {PaginationStyleSheet} from "./stylesheet/pagination.mjs";
11
+ import { ThemeStyleSheet } from "../stylesheet/theme.mjs";
12
+ import { ATTRIBUTE_DATASOURCE_SELECTOR } from "./constants.mjs";
13
+ import { Datasource } from "./datasource.mjs";
14
+ import { Observer } from "../../types/observer.mjs";
15
+ import { ATTRIBUTE_ROLE } from "../../dom/constants.mjs";
16
+ import { findTargetElementFromEvent } from "../../dom/events.mjs";
17
+ import { EmbeddedPaginationStyleSheet } from "./stylesheet/embedded-pagination.mjs";
18
+ import { PaginationStyleSheet } from "./stylesheet/pagination.mjs";
19
19
  //import {SpinnerStyleSheet} from "../stylesheet/spinner.mjs";
20
- import {DisplayStyleSheet} from "../stylesheet/display.mjs";
21
- import {isString} from "../../types/is.mjs";
22
- import {Pathfinder} from "../../data/pathfinder.mjs";
23
- import {instanceSymbol} from "../../constants.mjs";
24
- import {Formatter} from "../../text/formatter.mjs";
20
+ import { DisplayStyleSheet } from "../stylesheet/display.mjs";
21
+ import { isString } from "../../types/is.mjs";
22
+ import { Pathfinder } from "../../data/pathfinder.mjs";
23
+ import { instanceSymbol } from "../../constants.mjs";
24
+ import { Formatter } from "../../text/formatter.mjs";
25
25
  import "../form/select.mjs";
26
- import {addAttributeToken} from "../../dom/attributes.mjs";
27
- import {ATTRIBUTE_ERRORMESSAGE} from "../../dom/constants.mjs";
26
+ import { addAttributeToken } from "../../dom/attributes.mjs";
27
+ import { ATTRIBUTE_ERRORMESSAGE } from "../../dom/constants.mjs";
28
28
 
29
29
  import "./datasource/dom.mjs";
30
30
  import "./datasource/rest.mjs";
31
31
 
32
- export {Pagination};
32
+ export { Pagination };
33
33
 
34
34
  /**
35
35
  * @private
@@ -76,144 +76,143 @@ const datasourceLinkedElementSymbol = Symbol("datasourceLinkedElement");
76
76
  * @summary A datatable
77
77
  */
78
78
  class Pagination extends CustomElement {
79
- /**
80
- */
81
- constructor() {
82
- super();
83
- this[datasourceLinkedElementSymbol] = null;
84
- }
85
-
86
- /**
87
- * This method is called by the `instanceof` operator.
88
- * @returns {symbol}
89
- */
90
- static get [instanceSymbol]() {
91
- return Symbol.for("@schukai/monster/components/pagination");
92
- }
93
-
94
- /**
95
- * To set the options via the html tag the attribute `data-monster-options` must be used.
96
- * @see {@link https://monsterjs.org/en/doc/#configurate-a-monster-control}
97
- *
98
- * The individual configuration values can be found in the table.
99
- *
100
- * @property {Object} templates Template definitions
101
- * @property {string} templates.main Main template
102
- * @property {int} offset Current offset
103
- * @property {int} nextOffset Next offset
104
- * @property {int} prevOffset Previous offset
105
- * @property {int} objectsPerPage Number of objects per page
106
- * @property {int} currentPage Current page
107
- * @property {int} pages Total number of pages
108
- * @property {int} total Total number of objects
109
- */
110
- get defaults() {
111
- return Object.assign(
112
- {},
113
- super.defaults,
114
- {
115
- templates: {
116
- main: getTemplate(),
117
- },
118
-
119
- datasource: {
120
- selector: null,
121
- },
122
-
123
- labels: {
124
- page: "${page}",
125
- description: "Page ${page}",
126
- previous: "Previous",
127
- next: "Next",
128
- of: "of",
129
- },
130
-
131
- href: "page-${page}",
132
-
133
- currentPage: undefined,
134
- pages: undefined,
135
- objectsPerPage: 20,
136
-
137
- mapping: {
138
- pages: "sys.pagination.pages",
139
- objectsPerPage: "sys.pagination.objectsPerPage",
140
- currentPage: "sys.pagination.currentPage",
141
- },
142
-
143
- // classes: {
144
- // // spinner: "monster-spinner monster-theme-primary-3",
145
- // // spinnerContainer: "monster-theme-primary-1 ",
146
- // // error: "monster-theme-error-2 monster-bg-color-primary-2",
147
- // // errorContainer: "monster-theme-primary-1",
148
- // },
149
-
150
- // state: {
151
- // // spinner: false,
152
- // // error: false,
153
- // },
154
-
155
- pagination: {
156
- items: [],
157
- },
158
- },
159
- initOptionsFromArguments.call(this),
160
- );
161
- }
162
-
163
- /**
164
- *
165
- * @return {string}
166
- */
167
- static getTag() {
168
- return "monster-pagination";
169
- }
170
-
171
- /**
172
- *
173
- * @return {Monster.Components.Form.Form}
174
- */
175
- [assembleMethodSymbol]() {
176
- super[assembleMethodSymbol]();
177
-
178
- initControlReferences.call(this);
179
- initEventHandler.call(this);
180
-
181
- const selector = this.getOption("datasource.selector", "");
182
-
183
- if (isString(selector)) {
184
- const elements = document.querySelectorAll(selector);
185
- if (elements.length !== 1) {
186
- throw new Error("the selector must match exactly one element");
187
- }
188
-
189
- const element = elements[0];
190
- if (!(element instanceof Datasource)) {
191
- throw new TypeError("the element must be a datasource");
192
- }
193
-
194
- this[datasourceLinkedElementSymbol] = element;
195
- element.datasource.attachObserver(
196
- new Observer(handleDataSourceChanges.bind(this)),
197
- );
198
- }
199
-
200
- }
201
-
202
- /**
203
- * @private
204
- * @returns {CSSStyleSheet}
205
- */
206
- static getControlCSSStyleSheet() {
207
- return PaginationStyleSheet;
208
- }
209
-
210
- /**
211
- *
212
- * @return [CSSStyleSheet]
213
- */
214
- static getCSSStyleSheet() {
215
- return [this.getControlCSSStyleSheet(), DisplayStyleSheet, ThemeStyleSheet];
216
- }
79
+ /**
80
+ */
81
+ constructor() {
82
+ super();
83
+ this[datasourceLinkedElementSymbol] = null;
84
+ }
85
+
86
+ /**
87
+ * This method is called by the `instanceof` operator.
88
+ * @returns {symbol}
89
+ */
90
+ static get [instanceSymbol]() {
91
+ return Symbol.for("@schukai/monster/components/pagination");
92
+ }
93
+
94
+ /**
95
+ * To set the options via the html tag the attribute `data-monster-options` must be used.
96
+ * @see {@link https://monsterjs.org/en/doc/#configurate-a-monster-control}
97
+ *
98
+ * The individual configuration values can be found in the table.
99
+ *
100
+ * @property {Object} templates Template definitions
101
+ * @property {string} templates.main Main template
102
+ * @property {int} offset Current offset
103
+ * @property {int} nextOffset Next offset
104
+ * @property {int} prevOffset Previous offset
105
+ * @property {int} objectsPerPage Number of objects per page
106
+ * @property {int} currentPage Current page
107
+ * @property {int} pages Total number of pages
108
+ * @property {int} total Total number of objects
109
+ */
110
+ get defaults() {
111
+ return Object.assign(
112
+ {},
113
+ super.defaults,
114
+ {
115
+ templates: {
116
+ main: getTemplate(),
117
+ },
118
+
119
+ datasource: {
120
+ selector: null,
121
+ },
122
+
123
+ labels: {
124
+ page: "${page}",
125
+ description: "Page ${page}",
126
+ previous: "Previous",
127
+ next: "Next",
128
+ of: "of",
129
+ },
130
+
131
+ href: "page-${page}",
132
+
133
+ currentPage: undefined,
134
+ pages: undefined,
135
+ objectsPerPage: 20,
136
+
137
+ mapping: {
138
+ pages: "sys.pagination.pages",
139
+ objectsPerPage: "sys.pagination.objectsPerPage",
140
+ currentPage: "sys.pagination.currentPage",
141
+ },
142
+
143
+ // classes: {
144
+ // // spinner: "monster-spinner monster-theme-primary-3",
145
+ // // spinnerContainer: "monster-theme-primary-1 ",
146
+ // // error: "monster-theme-error-2 monster-bg-color-primary-2",
147
+ // // errorContainer: "monster-theme-primary-1",
148
+ // },
149
+
150
+ // state: {
151
+ // // spinner: false,
152
+ // // error: false,
153
+ // },
154
+
155
+ pagination: {
156
+ items: [],
157
+ },
158
+ },
159
+ initOptionsFromArguments.call(this),
160
+ );
161
+ }
162
+
163
+ /**
164
+ *
165
+ * @return {string}
166
+ */
167
+ static getTag() {
168
+ return "monster-pagination";
169
+ }
170
+
171
+ /**
172
+ *
173
+ * @return {Monster.Components.Form.Form}
174
+ */
175
+ [assembleMethodSymbol]() {
176
+ super[assembleMethodSymbol]();
177
+
178
+ initControlReferences.call(this);
179
+ initEventHandler.call(this);
180
+
181
+ const selector = this.getOption("datasource.selector", "");
182
+
183
+ if (isString(selector)) {
184
+ const elements = document.querySelectorAll(selector);
185
+ if (elements.length !== 1) {
186
+ throw new Error("the selector must match exactly one element");
187
+ }
188
+
189
+ const element = elements[0];
190
+ if (!(element instanceof Datasource)) {
191
+ throw new TypeError("the element must be a datasource");
192
+ }
193
+
194
+ this[datasourceLinkedElementSymbol] = element;
195
+ element.datasource.attachObserver(
196
+ new Observer(handleDataSourceChanges.bind(this)),
197
+ );
198
+ }
199
+ }
200
+
201
+ /**
202
+ * @private
203
+ * @returns {CSSStyleSheet}
204
+ */
205
+ static getControlCSSStyleSheet() {
206
+ return PaginationStyleSheet;
207
+ }
208
+
209
+ /**
210
+ *
211
+ * @return [CSSStyleSheet]
212
+ */
213
+ static getCSSStyleSheet() {
214
+ return [this.getControlCSSStyleSheet(), DisplayStyleSheet, ThemeStyleSheet];
215
+ }
217
216
  }
218
217
 
219
218
  /**
@@ -222,73 +221,73 @@ class Pagination extends CustomElement {
222
221
  * @throws {Error} no shadow-root is defined
223
222
  */
224
223
  function initControlReferences() {
225
- if (!this.shadowRoot) {
226
- throw new Error("no shadow-root is defined");
227
- }
224
+ if (!this.shadowRoot) {
225
+ throw new Error("no shadow-root is defined");
226
+ }
228
227
 
229
- this[paginationElementSymbol] = this.shadowRoot.querySelector(
230
- "[data-monster-role=pagination]",
231
- );
228
+ this[paginationElementSymbol] = this.shadowRoot.querySelector(
229
+ "[data-monster-role=pagination]",
230
+ );
232
231
  }
233
232
 
234
233
  /**
235
234
  * @private
236
235
  */
237
236
  function initEventHandler() {
238
- const self = this;
239
-
240
- self[paginationElementSymbol].addEventListener("click", function (event) {
241
- let element = null;
242
- const datasource = self[datasourceLinkedElementSymbol];
243
- if (!datasource) {
244
- return;
245
- }
246
-
247
- element = findTargetElementFromEvent(
248
- event,
249
- ATTRIBUTE_ROLE,
250
- "pagination-item",
251
- );
252
- if (!element) {
253
- element = findTargetElementFromEvent(
254
- event,
255
- ATTRIBUTE_ROLE,
256
- "pagination-next",
257
- );
258
- if (!element) {
259
- element = findTargetElementFromEvent(
260
- event,
261
- ATTRIBUTE_ROLE,
262
- "pagination-prev",
263
- );
264
- if (!element) {
265
- return;
266
- }
267
- }
268
- }
269
-
270
- let page = null;
271
-
272
- if (!element.hasAttribute("data-page-no")) {
273
- return;
274
- }
275
-
276
- page = element.getAttribute("data-page-no");
277
- event.preventDefault();
278
-
279
- if (
280
- !page ||
281
- page === "" ||
282
- page === null ||
283
- page === undefined ||
284
- page === "undefined" ||
285
- page === "null"
286
- ) {
287
- return;
288
- }
289
-
290
- datasource.setParameters({page}).reload();
291
- });
237
+ const self = this;
238
+
239
+ self[paginationElementSymbol].addEventListener("click", function (event) {
240
+ let element = null;
241
+ const datasource = self[datasourceLinkedElementSymbol];
242
+ if (!datasource) {
243
+ return;
244
+ }
245
+
246
+ element = findTargetElementFromEvent(
247
+ event,
248
+ ATTRIBUTE_ROLE,
249
+ "pagination-item",
250
+ );
251
+ if (!element) {
252
+ element = findTargetElementFromEvent(
253
+ event,
254
+ ATTRIBUTE_ROLE,
255
+ "pagination-next",
256
+ );
257
+ if (!element) {
258
+ element = findTargetElementFromEvent(
259
+ event,
260
+ ATTRIBUTE_ROLE,
261
+ "pagination-prev",
262
+ );
263
+ if (!element) {
264
+ return;
265
+ }
266
+ }
267
+ }
268
+
269
+ let page = null;
270
+
271
+ if (!element.hasAttribute("data-page-no")) {
272
+ return;
273
+ }
274
+
275
+ page = element.getAttribute("data-page-no");
276
+ event.preventDefault();
277
+
278
+ if (
279
+ !page ||
280
+ page === "" ||
281
+ page === null ||
282
+ page === undefined ||
283
+ page === "undefined" ||
284
+ page === "null"
285
+ ) {
286
+ return;
287
+ }
288
+
289
+ datasource.setParameters({ page }).reload();
290
+ });
292
291
  }
293
292
 
294
293
  /**
@@ -304,46 +303,46 @@ function initEventHandler() {
304
303
  * @throws {Error} the datasource could not be initialized
305
304
  */
306
305
  function initOptionsFromArguments() {
307
- const options = {};
308
- const selector = this.getAttribute(ATTRIBUTE_DATASOURCE_SELECTOR);
309
- if (selector) {
310
- options.datasource = {selector: selector};
311
- }
306
+ const options = {};
307
+ const selector = this.getAttribute(ATTRIBUTE_DATASOURCE_SELECTOR);
308
+ if (selector) {
309
+ options.datasource = { selector: selector };
310
+ }
312
311
 
313
- return options;
312
+ return options;
314
313
  }
315
314
 
316
315
  /**
317
316
  * @private
318
317
  */
319
318
  function handleDataSourceChanges() {
320
- let pagination;
321
-
322
- if (!this[datasourceLinkedElementSymbol]) {
323
- return;
324
- }
325
-
326
- const mapping = this.getOption("mapping");
327
- for (const key in mapping) {
328
- const path = mapping[key];
329
-
330
- let value;
331
- try {
332
- value = new Pathfinder(this[datasourceLinkedElementSymbol].data).getVia(
333
- path,
334
- );
335
- this.setOption(key, value);
336
- } catch (e) {
337
- addAttributeToken(this, ATTRIBUTE_ERRORMESSAGE, e.message);
338
- }
339
- }
340
-
341
- pagination = buildPagination.call(
342
- this,
343
- this.getOption("currentPage"),
344
- this.getOption("pages"),
345
- );
346
- this.setOption("pagination", pagination);
319
+ let pagination;
320
+
321
+ if (!this[datasourceLinkedElementSymbol]) {
322
+ return;
323
+ }
324
+
325
+ const mapping = this.getOption("mapping");
326
+ for (const key in mapping) {
327
+ const path = mapping[key];
328
+
329
+ let value;
330
+ try {
331
+ value = new Pathfinder(this[datasourceLinkedElementSymbol].data).getVia(
332
+ path,
333
+ );
334
+ this.setOption(key, value);
335
+ } catch (e) {
336
+ addAttributeToken(this, ATTRIBUTE_ERRORMESSAGE, e.message);
337
+ }
338
+ }
339
+
340
+ pagination = buildPagination.call(
341
+ this,
342
+ this.getOption("currentPage"),
343
+ this.getOption("pages"),
344
+ );
345
+ this.setOption("pagination", pagination);
347
346
  }
348
347
 
349
348
  /**
@@ -353,88 +352,88 @@ function handleDataSourceChanges() {
353
352
  * @returns {object}
354
353
  */
355
354
  function buildPagination(current, max) {
356
- let prev = current === 1 ? null : current - 1;
357
- let next = current === max ? null : current + 1;
358
- const itemList = [1];
359
-
360
- if (current > 4) itemList.push("…");
361
-
362
- const r = 2;
363
- const r1 = current - r;
364
- const r2 = current + r;
365
-
366
- for (let i = r1 > 2 ? r1 : 2; i <= Math.min(max, r2); i++) itemList.push(i);
367
-
368
- if (r2 + 1 < max) itemList.push("…");
369
- if (r2 < max) itemList.push(max);
370
-
371
- let prevClass = "";
372
-
373
- if (prev === null) {
374
- prevClass = " disabled";
375
- }
376
-
377
- let nextClass = "";
378
- if (next === null) {
379
- nextClass = " disabled";
380
- }
381
-
382
- const items = itemList.map((item) => {
383
- const p = `${item}`;
384
- const c = `${current}`;
385
-
386
- const obj = {
387
- pageNo: item, // as integer
388
- page: p, // as string
389
- current: p === c,
390
- class: (p === c ? "current" : "").trim(),
391
- };
392
-
393
- if (p === "…") {
394
- obj.class += " disabled".trim();
395
- }
396
-
397
- const formatter = new Formatter(obj);
398
-
399
- obj.description = formatter.format(this.getOption("labels.description"));
400
- obj.label = formatter.format(this.getOption("labels.page"));
401
- obj.href =
402
- p === "…"
403
- ? "#"
404
- : p === c
405
- ? "#"
406
- : p === "1"
407
- ? "#"
408
- : `#${formatter.format(this.getOption("href"))}`;
409
- return obj;
410
- });
411
-
412
- const nextNo = next;
413
- next = `${next}`;
414
-
415
- const nextHref =
416
- next === "null"
417
- ? "#"
418
- : `#${new Formatter({page: next}).format(this.getOption("href"))}`;
419
- const prevNo = prev;
420
- prev = `${prev}`;
421
- const prevHref =
422
- prev === "null"
423
- ? "#"
424
- : `#${new Formatter({page: prev}).format(this.getOption("href"))}`;
425
-
426
- return {
427
- current,
428
- nextNo,
429
- next,
430
- nextClass,
431
- nextHref,
432
- prevNo,
433
- prev,
434
- prevClass,
435
- prevHref,
436
- items,
437
- };
355
+ let prev = current === 1 ? null : current - 1;
356
+ let next = current === max ? null : current + 1;
357
+ const itemList = [1];
358
+
359
+ if (current > 4) itemList.push("…");
360
+
361
+ const r = 2;
362
+ const r1 = current - r;
363
+ const r2 = current + r;
364
+
365
+ for (let i = r1 > 2 ? r1 : 2; i <= Math.min(max, r2); i++) itemList.push(i);
366
+
367
+ if (r2 + 1 < max) itemList.push("…");
368
+ if (r2 < max) itemList.push(max);
369
+
370
+ let prevClass = "";
371
+
372
+ if (prev === null) {
373
+ prevClass = " disabled";
374
+ }
375
+
376
+ let nextClass = "";
377
+ if (next === null) {
378
+ nextClass = " disabled";
379
+ }
380
+
381
+ const items = itemList.map((item) => {
382
+ const p = `${item}`;
383
+ const c = `${current}`;
384
+
385
+ const obj = {
386
+ pageNo: item, // as integer
387
+ page: p, // as string
388
+ current: p === c,
389
+ class: (p === c ? "current" : "").trim(),
390
+ };
391
+
392
+ if (p === "…") {
393
+ obj.class += " disabled".trim();
394
+ }
395
+
396
+ const formatter = new Formatter(obj);
397
+
398
+ obj.description = formatter.format(this.getOption("labels.description"));
399
+ obj.label = formatter.format(this.getOption("labels.page"));
400
+ obj.href =
401
+ p === "…"
402
+ ? "#"
403
+ : p === c
404
+ ? "#"
405
+ : p === "1"
406
+ ? "#"
407
+ : `#${formatter.format(this.getOption("href"))}`;
408
+ return obj;
409
+ });
410
+
411
+ const nextNo = next;
412
+ next = `${next}`;
413
+
414
+ const nextHref =
415
+ next === "null"
416
+ ? "#"
417
+ : `#${new Formatter({ page: next }).format(this.getOption("href"))}`;
418
+ const prevNo = prev;
419
+ prev = `${prev}`;
420
+ const prevHref =
421
+ prev === "null"
422
+ ? "#"
423
+ : `#${new Formatter({ page: prev }).format(this.getOption("href"))}`;
424
+
425
+ return {
426
+ current,
427
+ nextNo,
428
+ next,
429
+ nextClass,
430
+ nextHref,
431
+ prevNo,
432
+ prev,
433
+ prevClass,
434
+ prevHref,
435
+ items,
436
+ };
438
437
  }
439
438
 
440
439
  /**
@@ -442,8 +441,8 @@ function buildPagination(current, max) {
442
441
  * @return {string}
443
442
  */
444
443
  function getTemplate() {
445
- // language=HTML
446
- return `
444
+ // language=HTML
445
+ return `
447
446
  <template id="items">
448
447
  <li><a data-monster-attributes="class path:items.class,
449
448
  href path:items.href,