lupine.components 1.1.48 → 1.1.50

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.
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "lupine.components",
3
- "version": "1.1.48",
3
+ "version": "1.1.50",
4
4
  "license": "MIT",
5
5
  "author": "uuware.com",
6
6
  "homepage": "https://github.com/uuware/lupine.js",
@@ -40,4 +40,4 @@
40
40
  "dependencies": {
41
41
  "lupine.web": "^1.0.0"
42
42
  }
43
- }
43
+ }
@@ -1,4 +1,4 @@
1
- import { CssProps, RefProps, VNode, mountInnerComponent } from 'lupine.web';
1
+ import { CssProps, RefProps, VNode, callUnload, mountInnerComponent } from 'lupine.web';
2
2
  import { backActionHelper } from '../lib';
3
3
  import { NotificationColor, NotificationMessage } from './notice-message';
4
4
 
@@ -55,7 +55,8 @@ export class ActionSheet {
55
55
  const handleClose = (reason?: ActionSheetCloseReasonProps) => {
56
56
  closeEvent?.(reason);
57
57
  ref.current.classList.remove('animation-open');
58
- setTimeout(() => {
58
+ setTimeout(async () => {
59
+ await callUnload(base);
59
60
  base.remove();
60
61
  }, 300);
61
62
  };
@@ -1,4 +1,4 @@
1
- import { CssProps, RefProps, VNode, mountInnerComponent } from 'lupine.web';
1
+ import { CssProps, RefProps, VNode, callUnload, mountInnerComponent } from 'lupine.web';
2
2
  import { stopPropagation, backActionHelper } from '../lib';
3
3
 
4
4
  export type FloatWindowCloseProps = () => void;
@@ -57,7 +57,8 @@ export class FloatWindow {
57
57
  closeEvent?.();
58
58
  ref.current.classList.add('transition');
59
59
  ref.current.classList.remove('animation');
60
- setTimeout(() => {
60
+ setTimeout(async () => {
61
+ await callUnload(base);
61
62
  base.remove();
62
63
  }, 300);
63
64
  };
@@ -1,5 +1,5 @@
1
1
  import { RefProps, Spinner02, SpinnerSize } from 'lupine.components';
2
- import { CssProps, mountInnerComponent } from 'lupine.components';
2
+ import { CssProps, callUnload, mountInnerComponent } from 'lupine.components';
3
3
 
4
4
  export type LoadingSpinHookProps = {
5
5
  show?: () => void;
@@ -46,7 +46,8 @@ export const LoadingSpinComponent = (props: LoadingSpinProps) => {
46
46
 
47
47
  export class LoadingSpin {
48
48
  static async show(): Promise<() => void> {
49
- const handleClose = () => {
49
+ const handleClose = async () => {
50
+ await callUnload(base);
50
51
  base.remove();
51
52
  };
52
53
 
@@ -1,4 +1,5 @@
1
1
  import { backActionHelper, CssProps, RefProps, VNode, MediaQueryRange } from 'lupine.components';
2
+ import { isSafeAreaSupported } from '../../lib/support-safe-area';
2
3
 
3
4
  export class MobileSideMenuHelper {
4
5
  static show() {
@@ -74,7 +75,7 @@ export class MobileSideMenuHelper {
74
75
  moveStart = false;
75
76
  pendingOpen = false;
76
77
  isOpen = maskDom.classList.contains('show');
77
-
78
+
78
79
  const menuDom = maskDom.querySelector('.mobile-side-menu') as HTMLDivElement;
79
80
  if (menuDom) {
80
81
  menuWidth = menuDom.offsetWidth || 210; // Fallback width roughly 70% of 300px
@@ -243,8 +244,8 @@ export const MobileSideMenu = (props: { children: VNode<any>; autoExtend?: boole
243
244
  overflowY: 'auto',
244
245
  transform: 'translateX(-100%)',
245
246
  boxShadow: 'var(--cover-box-shadow)',
246
- 'padding-top ': 'constant(safe-area-inset-top)',
247
- 'padding-top': 'env(safe-area-inset-top)',
247
+ 'padding-top ': isSafeAreaSupported() ? 'constant(safe-area-inset-top)' : '0',
248
+ 'padding-top': isSafeAreaSupported() ? 'env(safe-area-inset-top)' : '0',
248
249
  },
249
250
  [MediaQueryRange.TabletAbove]: {
250
251
  '&.auto-extend .mobile-side-menu-mask': {
@@ -2,13 +2,14 @@
2
2
  sliderFrameHook is for slider frame from right or bottom used in side-menu
3
3
  */
4
4
 
5
- import { VNode, CssProps, MediaQueryRange, SliderFrameHookProps, SliderFrame, RefProps } from 'lupine.components';
5
+ import { VNode, CssProps, MediaQueryRange, RefProps } from 'lupine.components';
6
6
  import { MobileFooterMenu } from '../components/mobile-components/mobile-footer-menu';
7
7
  import { DesktopFooter } from '../components/desktop-footer';
8
8
  import { DesktopHeader } from '../components/desktop-header';
9
9
  import { MobileHeaderComponent } from '../components/mobile-components/mobile-header-component';
10
10
  import { MobileSideMenu } from '../components/mobile-components/mobile-side-menu';
11
11
  import { IconMenuItemProps } from '../components/mobile-components/icon-menu-item-props';
12
+ import { isSafeAreaSupported } from '../lib/support-safe-area';
12
13
 
13
14
  export interface ResponsiveFrameProps {
14
15
  placeholderClassname: string;
@@ -37,8 +38,8 @@ export const ResponsiveFrame = (props: ResponsiveFrameProps) => {
37
38
  margin: '0 auto',
38
39
  overflowX: 'hidden',
39
40
  ...(!props.noSafeAreaTop ? {
40
- 'padding-top ': 'constant(safe-area-inset-top)',
41
- 'padding-top': 'env(safe-area-inset-top)',
41
+ 'padding-top ': isSafeAreaSupported() ? 'constant(safe-area-inset-top)' : '',
42
+ 'padding-top': isSafeAreaSupported() ? 'env(safe-area-inset-top)' : '',
42
43
  } : {}),
43
44
  '.frame-top-menu': {
44
45
  display: 'flex',
@@ -1,6 +1,7 @@
1
- import { CssProps, RefProps, VNode, mountInnerComponent } from 'lupine.web';
1
+ import { CssProps, RefProps, VNode, callUnload, mountInnerComponent } from 'lupine.web';
2
2
  import { backActionHelper, stopPropagation } from '../lib';
3
3
  import { MediaQueryMaxWidth, MediaQueryRange } from '../styles';
4
+ import { isSafeAreaSupported } from '../lib/support-safe-area';
4
5
 
5
6
  export type SliderHelperDirection = 'right' | 'left' | 'bottom' | 'top';
6
7
  export type SliderHelperCloseProps = () => void;
@@ -41,7 +42,8 @@ export class SliderHelper {
41
42
  closeEvent?.();
42
43
  ref.current?.classList.remove('show');
43
44
  ref.current?.classList.add(closeClassName);
44
- setTimeout(() => {
45
+ setTimeout(async () => {
46
+ await callUnload(base);
45
47
  base.remove();
46
48
  }, 400);
47
49
  };
@@ -95,21 +97,21 @@ export class SliderHelper {
95
97
 
96
98
  const contentCss: CssProps = isHorizontal
97
99
  ? {
98
- top: '0',
99
- bottom: '0',
100
- width: '100%',
101
- maxWidth,
102
- [direction]: '0',
103
- }
100
+ top: '0',
101
+ bottom: '0',
102
+ width: '100%',
103
+ maxWidth,
104
+ [direction]: '0',
105
+ }
104
106
  : {
105
- top: direction === 'top' ? '0' : 'auto',
106
- bottom: direction === 'bottom' ? '0' : 'auto',
107
- left: 'auto',
108
- right: '0',
109
- width: '100%',
110
- maxWidth,
111
- height: '100%',
112
- };
107
+ top: direction === 'top' ? '0' : 'auto',
108
+ bottom: direction === 'bottom' ? '0' : 'auto',
109
+ left: 'auto',
110
+ right: '0',
111
+ width: '100%',
112
+ maxWidth,
113
+ height: '100%',
114
+ };
113
115
 
114
116
  const cssContainer: CssProps = {
115
117
  display: 'flex',
@@ -155,8 +157,8 @@ export class SliderHelper {
155
157
  transform: startTransform,
156
158
  transition: 'transform 0.4s ease-in-out',
157
159
  // trick: to put two padding-top properties
158
- 'padding-top ': 'constant(safe-area-inset-top)',
159
- 'padding-top': 'env(safe-area-inset-top)',
160
+ 'padding-top ': isSafeAreaSupported() ? 'constant(safe-area-inset-top)' : '0',
161
+ 'padding-top': isSafeAreaSupported() ? 'env(safe-area-inset-top)' : '0',
160
162
  ...contentCss,
161
163
  '&::-webkit-scrollbar': {
162
164
  display: 'none',
@@ -2,6 +2,7 @@
2
2
  place to set safe-area-inset-top and other common styles
3
3
  */
4
4
  import { VNode, CssProps } from 'lupine.components';
5
+ import { isSafeAreaSupported } from '../lib/support-safe-area';
5
6
 
6
7
  // TopFrame and ResponsiveFrame both contain safe-area-inset-top, so can't use them togother
7
8
  export const TopFrame = async ({
@@ -27,9 +28,9 @@ export const TopFrame = async ({
27
28
  // trick: to put two padding-top properties
28
29
  ...(!noSafeAreaTop
29
30
  ? {
30
- 'padding-top ': 'constant(safe-area-inset-top)',
31
- 'padding-top': 'env(safe-area-inset-top)',
32
- }
31
+ 'padding-top ': isSafeAreaSupported() ? 'constant(safe-area-inset-top)' : '',
32
+ 'padding-top': isSafeAreaSupported() ? 'env(safe-area-inset-top)' : '',
33
+ }
33
34
  : {}),
34
35
  },
35
36
  };
package/src/lib/index.ts CHANGED
@@ -24,4 +24,5 @@ export * from './path-utils';
24
24
  export * from './promise-timeout';
25
25
  export * from './simple-storage';
26
26
  export * from './stop-propagation';
27
+ export * from './support-safe-area';
27
28
  export * from './upload-file';
@@ -0,0 +1,26 @@
1
+
2
+ const shouldApplySafeAreaTopPadding = () => {
3
+ if (typeof navigator === 'undefined') return true;
4
+ const ua = navigator.userAgent;
5
+
6
+ // match old Android devices
7
+ if (!/(vivo|oppo|xiaomi|redmi|huawei|honor)/i.test(ua)) return true;
8
+
9
+ // parse Android version
10
+ const match = ua.match(/Android\s+([\d\.]+)/i);
11
+ if (match) {
12
+ const version = parseFloat(match[1]);
13
+ // Android version < 10 has bug that return env value even if padding is added
14
+ if (version <= 10) return false;
15
+ }
16
+ return true;
17
+ };
18
+ const _safearea = {
19
+ supported: shouldApplySafeAreaTopPadding(),
20
+ }
21
+
22
+ export const isSafeAreaSupported = () => _safearea.supported;
23
+ // for customize development, disable safearea for some mobile devices
24
+ export const setSafeAreaSupported = (supported: boolean) => {
25
+ _safearea.supported = supported;
26
+ }