lupine.web 1.0.15 → 1.0.17

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 (78) hide show
  1. package/README.md +1 -1
  2. package/package.json +1 -5
  3. package/src/core/bind-lang.ts +6 -5
  4. package/src/core/bind-links.ts +2 -2
  5. package/src/core/bind-meta.tsx +52 -0
  6. package/src/core/bind-theme.ts +11 -9
  7. package/src/core/export-lupine.ts +64 -0
  8. package/src/core/index.ts +3 -1
  9. package/src/core/{core.ts → initialize.ts} +12 -79
  10. package/src/core/page-router.ts +3 -2
  11. package/src/core/server-cookie.ts +5 -3
  12. package/src/index.ts +2 -3
  13. package/src/lib/index.ts +2 -13
  14. package/src/lib/is-frontend.ts +3 -0
  15. package/src/models/index.ts +2 -0
  16. package/src/models/json-props.ts +8 -0
  17. package/src/models/theme-props.ts +7 -0
  18. package/src/{types → styles}/index.ts +0 -2
  19. package/src/assets/themes/base-themes.ts +0 -16
  20. package/src/assets/themes/dark-themes.ts +0 -85
  21. package/src/assets/themes/index.ts +0 -4
  22. package/src/assets/themes/light-themes.ts +0 -92
  23. package/src/assets/themes/shared-themes.ts +0 -50
  24. package/src/components/button-push-animation.tsx +0 -138
  25. package/src/components/button.tsx +0 -55
  26. package/src/components/drag-refresh.tsx +0 -110
  27. package/src/components/editable-label.tsx +0 -83
  28. package/src/components/float-window.tsx +0 -226
  29. package/src/components/grid.tsx +0 -18
  30. package/src/components/html-var.tsx +0 -41
  31. package/src/components/index.ts +0 -36
  32. package/src/components/input-with-title.tsx +0 -24
  33. package/src/components/link-item.tsx +0 -13
  34. package/src/components/link-list.tsx +0 -62
  35. package/src/components/menu-bar.tsx +0 -220
  36. package/src/components/menu-item-props.tsx +0 -10
  37. package/src/components/menu-sidebar.tsx +0 -289
  38. package/src/components/message-box.tsx +0 -44
  39. package/src/components/meta-data.tsx +0 -54
  40. package/src/components/meta-description.tsx +0 -19
  41. package/src/components/meta-title.tsx +0 -19
  42. package/src/components/modal.tsx +0 -29
  43. package/src/components/notice-message.tsx +0 -119
  44. package/src/components/paging-link.tsx +0 -100
  45. package/src/components/panel.tsx +0 -24
  46. package/src/components/popup-menu.tsx +0 -218
  47. package/src/components/progress.tsx +0 -91
  48. package/src/components/redirect.tsx +0 -19
  49. package/src/components/resizable-splitter.tsx +0 -129
  50. package/src/components/select-with-title.tsx +0 -37
  51. package/src/components/spinner.tsx +0 -100
  52. package/src/components/svg.tsx +0 -24
  53. package/src/components/tabs.tsx +0 -252
  54. package/src/components/text-glow.tsx +0 -36
  55. package/src/components/text-wave.tsx +0 -54
  56. package/src/components/theme-selector.tsx +0 -35
  57. package/src/components/toggle-base.tsx +0 -260
  58. package/src/components/toggle-switch.tsx +0 -156
  59. package/src/lib/date-utils.ts +0 -317
  60. package/src/lib/deep-merge.ts +0 -37
  61. package/src/lib/document-ready.ts +0 -36
  62. package/src/lib/dom/calculate-text-width.ts +0 -13
  63. package/src/lib/dom/download-stream.ts +0 -17
  64. package/src/lib/dom/download.ts +0 -12
  65. package/src/lib/dom/index.ts +0 -71
  66. package/src/lib/dynamical-load.ts +0 -138
  67. package/src/lib/format-bytes.ts +0 -11
  68. package/src/lib/lite-dom.ts +0 -227
  69. package/src/lib/message-hub.ts +0 -105
  70. package/src/lib/observable.ts +0 -188
  71. package/src/lib/promise-timeout.ts +0 -1
  72. package/src/lib/simple-storage.ts +0 -40
  73. package/src/lib/stop-propagation.ts +0 -7
  74. package/src/lib/upload-file.ts +0 -68
  75. package/src/types/css-types.ts +0 -17
  76. package/src/types/media-query.ts +0 -93
  77. /package/src/lib/{dom/cookie.ts → cookie.ts} +0 -0
  78. /package/src/{types → styles}/css-styles.ts +0 -0
@@ -1,289 +0,0 @@
1
- import { bindGlobalStyles, getRenderPageProps } from '../core';
2
- import { CssProps, RefProps } from '../jsx';
3
- import { stopPropagation } from '../lib';
4
- import { MediaQueryMaxWidth } from '../types';
5
- import { NestMenuItemProps } from './menu-item-props';
6
-
7
- const fetchMenu = async (menuId: string) => {
8
- const data = await getRenderPageProps().renderPageFunctions.fetchData(`/api/menu/get/${menuId}`);
9
- return data.json;
10
- };
11
-
12
- export type MenuSidebarProps = {
13
- mobileMenu?: boolean;
14
- desktopMenu?: boolean;
15
- menuId?: string;
16
- items: NestMenuItemProps[];
17
- className?: string;
18
- maxWidthMobileMenu?: string;
19
- maxWidth?: string;
20
- color?: string;
21
- backgroundColor?: string;
22
- };
23
- export const MenuSidebar = ({
24
- mobileMenu,
25
- desktopMenu,
26
- menuId,
27
- items,
28
- className,
29
- color = 'white',
30
- backgroundColor = 'dark',
31
- maxWidth = '100%',
32
- maxWidthMobileMenu = MediaQueryMaxWidth.TabletMax,
33
- }: MenuSidebarProps) => {
34
- const css: CssProps = {
35
- backgroundColor,
36
- '.menu-sidebar-top': {
37
- width: '100%',
38
- backgroundColor: 'var(--sidebar-bg-color)',
39
- maxWidth: maxWidth,
40
- margin: 'auto',
41
- // height: 'auto',
42
- position: 'relative',
43
-
44
- display: 'flex',
45
- // width: '100%',
46
- justifyContent: 'center',
47
- flexDirection: 'column',
48
- },
49
- '&.mobile .menu-sidebar-top': {
50
- position: 'absolute',
51
- },
52
- '.menu-sidebar-item': {
53
- display: 'inline-block',
54
- color,
55
- cursor: 'pointer',
56
- padding: '14px 16px',
57
- textDecoration: 'none',
58
- position: 'relative',
59
- borderBottom: 'var(--sidebar-border)',
60
- },
61
- // select parent when hover on a child, .menu-sidebar-sub-box:hover > .menu-sidebar-item
62
- '.menu-sidebar-item:hover': {
63
- color: 'var(--activatable-color-hover)',
64
- backgroundColor: 'var(--activatable-bg-color-hover)',
65
- },
66
- '.menu-sidebar-sub-box .menu-sidebar-sub': {
67
- display: 'none',
68
- // position: 'absolute',
69
- // color: 'var(--sidebar-sub-color)',
70
- // backgroundColor: 'var(--sidebar-sub-bg-color)',
71
- minWidth: '160px',
72
- // boxShadow: '0px 8px 16px 0px rgba(0,0,0,0.2)',
73
- zIndex: 'var(--layer-sidebar-sub)',
74
- flexDirection: 'column',
75
- },
76
- '.menu-sidebar-sub-box > .menu-sidebar-item': {
77
- padding: '14px 26px 14px 16px',
78
- width: '100%',
79
- },
80
- '.menu-sidebar-sub-box > .menu-sidebar-sub > .menu-sidebar-item': {
81
- paddingLeft: '32px',
82
- },
83
- '.menu-sidebar-sub-box > .menu-sidebar-item::after': {
84
- content: '""',
85
- position: 'absolute',
86
- top: '50%',
87
- transform: 'translateY(-50%) rotate(-90deg)',
88
- marginLeft: '6px',
89
- width: 0,
90
- height: 0,
91
- borderLeft: '5px solid transparent',
92
- borderRight: '5px solid transparent',
93
- borderTop: '5px solid ' + color,
94
- right: '10px',
95
- transition: 'all 300ms ease-in-out',
96
- },
97
- '.menu-sidebar-sub-box.open > .menu-sidebar-item::after': {
98
- transform: 'rotate(0deg)',
99
- },
100
- '&.mobile .menu-sidebar-sub-box > .menu-sidebar-item::after': {
101
- transform: 'rotate(0deg)',
102
- },
103
- // '.menu-sidebar-sub-box .menu-sidebar-sub > .menu-sidebar-item': {
104
- // color: 'black',
105
- // },
106
- '.menu-sidebar-sub-box.open > .menu-sidebar-sub': {
107
- display: 'flex',
108
- },
109
- '.menu-sidebar-sub-box .menu-sidebar-sub .menu-sidebar-item:hover': {
110
- color: 'var(--activatable-color-hover)',
111
- backgroundColor: 'var(--activatable-bg-color-hover)',
112
- },
113
- '.menu-sidebar-mobile': {
114
- display: 'none',
115
- position: 'relative',
116
- backgroundColor: 'var(--primary-bg-color)',
117
- padding: '5px 4px 6px',
118
- '.menu-sidebar-toggle': {
119
- cursor: 'pointer',
120
- padding: '6px 0 8px 0',
121
- 'span, span::before, span::after': {
122
- cursor: 'pointer',
123
- height: '3px',
124
- width: '25px',
125
- borderRadius: '1px',
126
- background: 'var(--primary-color)',
127
- position: 'absolute',
128
- display: 'block',
129
- transition: 'all 300ms ease-in-out',
130
- },
131
- 'span::before, span::after': {
132
- content: '""',
133
- },
134
- 'span::before': {
135
- top: '-7px',
136
- },
137
- 'span::after': {
138
- bottom: '-7px',
139
- },
140
- },
141
- '.menu-sidebar-toggle.active span': {
142
- backgroundColor: 'transparent',
143
- },
144
- '.menu-sidebar-toggle.active span::before': {
145
- transform: 'rotate(45deg)',
146
- top: 0,
147
- },
148
- '.menu-sidebar-toggle.active span::after': {
149
- transform: 'rotate(-45deg)',
150
- top: 0,
151
- },
152
- },
153
- // hide menu for mobile place
154
- '&.mobile': {
155
- display: 'none',
156
- // width: '33px',
157
- },
158
- '&.mobile .menu-sidebar-mobile': {
159
- display: 'block',
160
- width: '33px',
161
- },
162
- ['@media only screen and (max-width: ' + maxWidthMobileMenu + ')']: {
163
- // hide menu for not mobile place
164
- display: 'none',
165
- // show menu for mobile place
166
- '&.mobile': {
167
- display: 'block',
168
- },
169
- '.menu-sidebar-top': {
170
- display: 'none',
171
- },
172
- '.menu-sidebar-top.open': {
173
- display: 'flex',
174
- flexDirection: 'column',
175
- zIndex: 'var(--layer-sidebar)',
176
- },
177
- '.menu-sidebar-top.open .menu-sidebar-sub-box > .menu-sidebar-sub': {
178
- display: 'flex',
179
- position: 'unset',
180
- '.menu-sidebar-item': {
181
- paddingLeft: '32px',
182
- color,
183
- backgroundColor,
184
- },
185
- '.menu-sidebar-item:hover': {
186
- color: 'var(--activatable-color-hover)',
187
- backgroundColor: 'var(--activatable-bg-color-hover)',
188
- },
189
- },
190
- '.menu-sidebar-sub-box:hover > .menu-sidebar-item': {
191
- backgroundColor: 'unset',
192
- },
193
- '.menu-sidebar-sub-box:hover > .menu-sidebar-item:hover': {
194
- color: 'var(--activatable-color-hover)',
195
- backgroundColor: 'var(--activatable-bg-color-hover)',
196
- },
197
- },
198
- };
199
-
200
- // first level is grouped
201
- const renderItems = (items: NestMenuItemProps[], className: string) => {
202
- return (
203
- <div class={className}>
204
- {items.map((item) => {
205
- let ref: RefProps = {};
206
- return item.items ? (
207
- <div ref={ref} class='menu-sidebar-sub-box' onClick={() => onItemToggleClick(ref)}>
208
- <div class='menu-sidebar-item'>{item.text}</div>
209
- {renderItems(item.items, 'menu-sidebar-sub')}
210
- </div>
211
- ) : item.js ? (
212
- <a
213
- class='menu-sidebar-item'
214
- href='javascript:void(0)'
215
- alt={item.alt || item.text}
216
- onClick={(event) => {
217
- stopPropagation(event);
218
- // hide menu
219
- onToggleClick();
220
- item.js && item.js();
221
- }}
222
- >
223
- {item.text}
224
- </a>
225
- ) : (
226
- <a class='menu-sidebar-item' href={item.url} alt={item.alt || item.text}>
227
- {item.text}
228
- </a>
229
- );
230
- })}
231
- </div>
232
- );
233
- };
234
-
235
- const ref: RefProps = {
236
- onLoad: async () => {
237
- if (menuId) {
238
- const menu = await fetchMenu(menuId);
239
- if (menu.result.items.length > 0) {
240
- const items = menu.result.items.map((i: any) => {
241
- const l = i.split('\t');
242
- return { text: l[5], url: l[4] };
243
- });
244
- const newDom = renderItems(items, 'menu-sidebar-top');
245
- //mountComponents('.menu-sidebar-top', newDom);
246
- }
247
- }
248
- },
249
- };
250
- const onToggleClick = () => {
251
- const menu = ref.$('.menu-sidebar-mobile .menu-sidebar-toggle');
252
- menu.classList.toggle('active');
253
- const topMenu = ref.$('.menu-sidebar-top');
254
- topMenu.classList.toggle('open');
255
- };
256
- const onItemToggleClick = (ref: RefProps) => {
257
- // if (event.target != ref.current && (event.target as any).parentNode != ref.current) {
258
- // return;
259
- // }
260
- ref.current.classList.toggle('open');
261
- };
262
-
263
- // if this component is used twice, then the Global styles is only set at the first time
264
- bindGlobalStyles('menu-sidebar-box', '.menu-sidebar-box', css);
265
-
266
- // show the menu on both mobile and desktop
267
- const newCss: CssProps =
268
- (!desktopMenu && !mobileMenu) || (desktopMenu && mobileMenu)
269
- ? {
270
- ['@media only screen and (max-width: ' + maxWidthMobileMenu + ')']: {
271
- display: 'block',
272
- '.menu-sidebar-top': {
273
- display: 'block',
274
- },
275
- },
276
- }
277
- : {};
278
- return (
279
- <div css={newCss} ref={ref} class={['menu-sidebar-box', className, mobileMenu ? 'mobile' : ''].join(' ')}>
280
- <div class='menu-sidebar-mobile'>
281
- <div class='menu-sidebar-toggle' onClick={onToggleClick}>
282
- <span></span>
283
- </div>
284
- </div>
285
-
286
- {renderItems(items, 'menu-sidebar-top')}
287
- </div>
288
- );
289
- };
@@ -1,44 +0,0 @@
1
- import { FloatWindow, FloatWindowCloseProps, FloatWindowShowProps } from './float-window';
2
-
3
- export enum MessageBoxButtonProps {
4
- YesNo = 'yesno',
5
- OkCancel = 'okcancel',
6
- Ok = 'ok',
7
- }
8
- export type MessageBoxProps = FloatWindowShowProps & {
9
- buttonType: MessageBoxButtonProps;
10
- };
11
-
12
- export class MessageBox {
13
- static async show({
14
- title,
15
- children,
16
- contentMaxHeight,
17
- contentMinWidth,
18
- buttonType = MessageBoxButtonProps.OkCancel,
19
- noMoving = false,
20
- noModal = false,
21
- closeEvent,
22
- handleClicked,
23
- closeWhenClickOutside = false,
24
- }: MessageBoxProps): Promise<FloatWindowCloseProps> {
25
- const buttons =
26
- buttonType === MessageBoxButtonProps.OkCancel
27
- ? ['OK', 'Cancel']
28
- : buttonType === MessageBoxButtonProps.YesNo
29
- ? ['Yes', 'No']
30
- : ['OK'];
31
- return FloatWindow.show({
32
- title,
33
- children,
34
- contentMaxHeight,
35
- contentMinWidth,
36
- buttons,
37
- noMoving,
38
- noModal,
39
- closeEvent,
40
- handleClicked,
41
- closeWhenClickOutside,
42
- });
43
- }
44
- }
@@ -1,54 +0,0 @@
1
- // import { bindPageResetEvent } from '../core/page-reset-events';
2
- import { getMetaDescription } from './meta-description';
3
-
4
- type NameMeta = { name: string; content: string };
5
- type PropertyMeta = { property: string; content: string };
6
- type HttpEquivMeta = { httpEquiv: string; content: string };
7
- type AllMeta = NameMeta | PropertyMeta | HttpEquivMeta;
8
-
9
- function isNameMeta(data: any): data is NameMeta {
10
- return !!(data.name && data.content);
11
- }
12
- function isPropertyMeta(data: any): data is PropertyMeta {
13
- return !!(data.property && data.content);
14
- }
15
- function isHttpEquivMeta(data: any): data is HttpEquivMeta {
16
- return !!(data.httpEquiv && data.content);
17
- }
18
-
19
- let _metaData: { [key: string]: string } = {};
20
- // Shouldn't include <meta name="description" content="...">
21
- export const MetaData = (data: AllMeta) => {
22
- if (isNameMeta(data)) {
23
- _metaData[`name:${data.name}`] = `<meta name="${data.name}" content="${data.content}">`;
24
- } else if (isPropertyMeta(data)) {
25
- _metaData[`property:${data.property}`] = `<meta property="${data.property}" content="${data.content}">`;
26
- } else if (isHttpEquivMeta(data)) {
27
- _metaData[`http-equiv:${data.httpEquiv}`] = `<meta http-equiv="${data.httpEquiv}" content="${data.content}">`;
28
- } else if ((data as any).key && (data as any).string) {
29
- _metaData[`${(data as any).key}`] = `${(data as any).string}`;
30
- } else {
31
- console.warn('Unknown meta data:', data);
32
- }
33
- return <></>;
34
- };
35
-
36
- export const getMetaDataTags = () => {
37
- return Object.values(getMetaDataObject()).join('\n');
38
- };
39
-
40
- export const getMetaDataObject = () => {
41
- const metaDescription = getMetaDescription();
42
- return metaDescription
43
- ? Object.assign(
44
- {
45
- 'name:description': `<meta name="description" content="${metaDescription}">`,
46
- },
47
- _metaData
48
- )
49
- : _metaData;
50
- };
51
-
52
- // bindPageResetEvent(() => {
53
- // _metaData = {};
54
- // });
@@ -1,19 +0,0 @@
1
- // import { bindPageResetEvent } from '../core/page-reset-events';
2
-
3
- let _description = { value: '', defaultValue: '' };
4
- export const MetaDescription = ({ children }: { children: string }) => {
5
- _description.value = children;
6
- return <></>;
7
- };
8
-
9
- export const getMetaDescription = () => {
10
- return _description.value || _description.defaultValue;
11
- };
12
-
13
- export const setDefaultMetaDescription = (children: string) => {
14
- _description.defaultValue = children;
15
- };
16
-
17
- // bindPageResetEvent(() => {
18
- // _description.value = '';
19
- // });
@@ -1,19 +0,0 @@
1
- // import { bindPageResetEvent } from '../core/page-reset-events';
2
-
3
- let _title = { value: '', defaultValue: '' };
4
- export const MetaTitle = ({ children }: { children: string }) => {
5
- _title.value = children;
6
- return <></>;
7
- };
8
-
9
- export const getMetaTitle = () => {
10
- return _title.value || _title.defaultValue;
11
- };
12
-
13
- export const setDefaultMetaTitle = (children: string) => {
14
- _title.defaultValue = children;
15
- };
16
-
17
- // bindPageResetEvent(() => {
18
- // _title.value = '';
19
- // });
@@ -1,29 +0,0 @@
1
- import { FloatWindow, FloatWindowCloseProps, FloatWindowShowProps } from './float-window';
2
-
3
- export class ModalWindow {
4
- static async show({
5
- title,
6
- children,
7
- contentMaxHeight,
8
- contentMinWidth,
9
- buttons,
10
- noMoving = true,
11
- noModal = false,
12
- closeEvent,
13
- handleClicked,
14
- closeWhenClickOutside = true,
15
- }: FloatWindowShowProps): Promise<FloatWindowCloseProps> {
16
- return FloatWindow.show({
17
- title,
18
- children,
19
- contentMaxHeight,
20
- contentMinWidth,
21
- buttons,
22
- noMoving,
23
- noModal,
24
- closeEvent,
25
- handleClicked,
26
- closeWhenClickOutside,
27
- });
28
- }
29
- }
@@ -1,119 +0,0 @@
1
- import { bindGlobalStyles } from '../core';
2
- import { CssProps } from '../jsx';
3
- /**
4
- How to use:
5
- Notification.sendMessage(message);
6
- */
7
- export enum NotificationColor {
8
- Success = 'var(--success-bg-color)',
9
- Info = 'var(--info-bg-color)',
10
- Warning = 'var(--warning-bg-color)',
11
- Error = 'var(--error-bg-color)',
12
- }
13
- export const notificationColorFromValue = (value: string) => {
14
- switch (value) {
15
- case 'Success':
16
- return NotificationColor.Success;
17
- case 'Info':
18
- return NotificationColor.Info;
19
- case 'Warning':
20
- return NotificationColor.Warning;
21
- case 'Error':
22
- return NotificationColor.Error;
23
- }
24
- return NotificationColor.Info;
25
- };
26
- export class NotificationMessage {
27
- // public static readonly Color = NotificationColor;
28
-
29
- private static initialized = false;
30
- private static container: HTMLElement;
31
-
32
- static init() {
33
- /* styles for resizable splitter */
34
- const css: CssProps = {
35
- position: 'fixed',
36
- top: 0,
37
- right: 0,
38
- height: 'auto',
39
- overflowY: 'auto',
40
- maxHeight: '100%',
41
- width: '100%',
42
- maxWidth: '400px',
43
- // cursor: 'pointer',
44
- // backgroundColor: '#fefefe',
45
- padding: '0 10px',
46
- zIndex: 'var(--layer-notice)',
47
- // borderRadius: '6px',
48
- // boxShadow: '0px 0px 2px #000',
49
- '>div': {
50
- color: 'var(--notice-color-with-bg)',
51
- padding: '10px 8px',
52
- margin: '16px 0',
53
- borderRadius: '6px',
54
- boxShadow: 'var(--cover-box-shadow)', //'3px 3px 8px #767676',
55
- transition: 'all 0.5s',
56
- transform: 'scale(0.1)',
57
- opacity: 0,
58
- },
59
- '.close-btn': {
60
- position: 'absolute',
61
- top: '-2px',
62
- right: '3px',
63
- color: 'var(--notice-color-with-bg)',
64
- fontWeight: 'bold',
65
- fontSize: '22px',
66
- lineHeight: '20px',
67
- cursor: 'pointer',
68
- transition: '0.3s',
69
- },
70
-
71
- '.close-btn:hover': {
72
- color: 'black',
73
- },
74
- };
75
- bindGlobalStyles('lj_notification', '.lj_notification', css);
76
-
77
- let container = document.querySelector('.lj_notification');
78
- if (!container) {
79
- container = document.createElement('div');
80
- container.className = 'lj_notification';
81
- document.body.appendChild(container);
82
- this.container = container as HTMLElement;
83
- }
84
- }
85
-
86
- static sendMessage(message: string, backgroundColor = NotificationColor.Info, permanent = false, showTime = 3000) {
87
- if (!this.initialized) {
88
- this.initialized = true;
89
- this.init();
90
- }
91
- this.container.scrollTop = 0;
92
- const div = document.createElement('div');
93
- div.innerHTML = message;
94
- div.style.backgroundColor = backgroundColor;
95
- this.container.insertBefore(div, this.container.firstChild);
96
- setTimeout(() => {
97
- div.style.opacity = '1';
98
- div.style.transform = 'scale(1)';
99
- }, 0);
100
-
101
- if (permanent) {
102
- const closeBtn = document.createElement('span');
103
- closeBtn.innerHTML = '&times;';
104
- closeBtn.className = 'close-btn';
105
- div.appendChild(closeBtn);
106
- closeBtn.onclick = () => {
107
- this.container.removeChild(div);
108
- };
109
- } else {
110
- setTimeout(() => {
111
- div.style.opacity = '0';
112
- div.style.transform = 'scale(0.1)';
113
- setTimeout(() => {
114
- this.container.removeChild(div);
115
- }, 1000);
116
- }, showTime);
117
- }
118
- }
119
- }
@@ -1,100 +0,0 @@
1
- import { CssProps } from '../jsx';
2
- import { bindGlobalStyles, getRenderPageProps } from '../core';
3
-
4
- let _DEFAULT_PAGE_LIMIT = 7;
5
- export const getDefaultPageLimit = () => {
6
- return _DEFAULT_PAGE_LIMIT;
7
- };
8
- export const setDefaultPageLimit = (limit: number) => {
9
- _DEFAULT_PAGE_LIMIT = limit;
10
- };
11
- export type PagingLinkProps = {
12
- itemsCount: number;
13
- pageLimit?: number;
14
- pageIndex?: number;
15
- baseLink: string;
16
- onClick?: (index: number) => void; // if onClick is set then use it instead of href
17
- };
18
-
19
- export const PagingLink = (props: PagingLinkProps) => {
20
- const css: CssProps = {
21
- textAlign: 'right',
22
- paddingRight: '16px',
23
- '.paging-link-index': {
24
- padding: '0px 4px',
25
- },
26
- a: {
27
- textDecoration: 'none',
28
- },
29
- };
30
-
31
- bindGlobalStyles('paging-link-box', '.paging-link-box', css);
32
- const html = [];
33
- let pageIndex = props.pageIndex ?? (Number.parseInt(getRenderPageProps().query['pg_i'] || '') || 0);
34
- const pageLimit = props.pageLimit || _DEFAULT_PAGE_LIMIT;
35
- if (props.itemsCount > 0 && pageLimit > 0) {
36
- let maxPages = Math.floor(props.itemsCount / pageLimit);
37
- if (props.itemsCount % pageLimit !== 0) {
38
- maxPages++;
39
- }
40
- if (pageIndex > maxPages) {
41
- pageIndex = maxPages - 1;
42
- }
43
- if (pageIndex > 0) {
44
- html.push(
45
- <span class='paging-link-go'>
46
- <a
47
- href={props.onClick ? 'javascript:void(0)' : props.baseLink + '?pg_i=' + (pageIndex - 1)}
48
- onClick={() => props.onClick && props.onClick(pageIndex - 1)}
49
- >
50
- &lt;
51
- </a>
52
- </span>
53
- );
54
- } else {
55
- html.push(<span class='paging-link-go disabled'>&lt;</span>);
56
- }
57
- for (let i = 0; i < maxPages; i++) {
58
- if (i < 2 || i >= maxPages - 2 || (i > pageIndex - 3 && i < pageIndex + 3)) {
59
- if (i == pageIndex) {
60
- html.push(
61
- <span class='paging-link-index current'>
62
- <b>{'' + (i + 1)}</b>
63
- </span>
64
- );
65
- } else {
66
- html.push(
67
- <span class='paging-link-index'>
68
- <a
69
- href={props.onClick ? 'javascript:void(0)' : props.baseLink + '?pg_i=' + i}
70
- onClick={() => props.onClick && props.onClick(i)}
71
- >
72
- {'' + (i + 1)}
73
- </a>
74
- </span>
75
- );
76
- }
77
- } else {
78
- if (i == pageIndex - 4 || i == pageIndex + 4) {
79
- html.push(<span class='paging-link-skip'>...</span>);
80
- }
81
- }
82
- }
83
- if (pageIndex < maxPages - 1) {
84
- html.push(
85
- <span class='paging-link-go'>
86
- <a
87
- href={props.onClick ? 'javascript:void(0)' : props.baseLink + '?pg_i=' + (pageIndex + 1)}
88
- onClick={() => props.onClick && props.onClick(pageIndex + 1)}
89
- >
90
- &gt;
91
- </a>
92
- </span>
93
- );
94
- } else {
95
- html.push(<span class='paging-link-go disabled'>&gt;</span>);
96
- }
97
- }
98
-
99
- return html.length > 0 ? <div class='paging-link-box'>{html}</div> : <></>;
100
- };