@momo-kits/foundation 0.75.1-beta.3
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/Assets/header-background.png +0 -0
- package/Assets/icon.json +3947 -0
- package/Button/index.tsx +247 -0
- package/Button/styles.ts +41 -0
- package/CheckBox/index.tsx +61 -0
- package/CheckBox/styles.ts +15 -0
- package/CheckBox/types.ts +10 -0
- package/Consts/colors+spacing+radius.ts +214 -0
- package/Consts/index.ts +3 -0
- package/Consts/styles.ts +78 -0
- package/Consts/theme.ts +121 -0
- package/Divider/index.tsx +19 -0
- package/Icon/index.tsx +37 -0
- package/Icon/types.ts +8 -0
- package/IconButton/index.tsx +128 -0
- package/IconButton/styles.ts +19 -0
- package/Image/index.tsx +80 -0
- package/Image/styles.ts +13 -0
- package/Image/types.ts +3 -0
- package/Input/Input.tsx +142 -0
- package/Input/InputMoney.tsx +132 -0
- package/Input/InputSearch.tsx +161 -0
- package/Input/InputTextArea.tsx +152 -0
- package/Input/common.tsx +125 -0
- package/Input/index.tsx +41 -0
- package/Input/styles.ts +122 -0
- package/Input/utils.ts +63 -0
- package/Layout/Card.tsx +87 -0
- package/Layout/GridSystem.tsx +124 -0
- package/Layout/ScreenContainer.tsx +122 -0
- package/Layout/Section.tsx +143 -0
- package/Layout/index.ts +16 -0
- package/Layout/types.ts +21 -0
- package/Layout/utils.ts +50 -0
- package/Navigation/BottomTab.tsx +39 -0
- package/Navigation/Components.tsx +329 -0
- package/Navigation/ModalScreen.tsx +207 -0
- package/Navigation/Navigation.ts +38 -0
- package/Navigation/NavigationButton.tsx +54 -0
- package/Navigation/NavigationContainer.tsx +82 -0
- package/Navigation/Navigator.ts +66 -0
- package/Navigation/Observer.ts +79 -0
- package/Navigation/StackScreen.tsx +40 -0
- package/Navigation/index.ts +14 -0
- package/Navigation/types.ts +149 -0
- package/Navigation/utils.tsx +167 -0
- package/Pagination/Dot.tsx +16 -0
- package/Pagination/PaginationDot.tsx +33 -0
- package/Pagination/PaginationNumber.tsx +23 -0
- package/Pagination/PaginationScroll.tsx +88 -0
- package/Pagination/PaginationWhiteDot.tsx +32 -0
- package/Pagination/index.tsx +25 -0
- package/Pagination/styles.ts +47 -0
- package/Pagination/types.ts +19 -0
- package/Popup/PopupNotify.tsx +215 -0
- package/Popup/PopupPromotion.tsx +77 -0
- package/Popup/index.tsx +4 -0
- package/Popup/types.ts +22 -0
- package/Radio/index.tsx +65 -0
- package/Radio/styles.ts +11 -0
- package/Radio/types.ts +10 -0
- package/Skeleton/index.tsx +72 -0
- package/Skeleton/styles.ts +5 -0
- package/Skeleton/types.ts +3 -0
- package/Switch/index.tsx +40 -0
- package/Switch/styles.ts +23 -0
- package/Switch/types.ts +8 -0
- package/Tag/index.tsx +79 -0
- package/Tag/styles.ts +24 -0
- package/Tag/types.ts +10 -0
- package/Text/index.tsx +110 -0
- package/Text/styles.ts +35 -0
- package/Text/types.ts +40 -0
- package/index.ts +38 -0
- package/package.json +41 -0
- package/publish.sh +26 -0
|
@@ -0,0 +1,66 @@
|
|
|
1
|
+
import {StackActions} from '@react-navigation/native';
|
|
2
|
+
import {BottomSheetParams, ModalParams, ScreenParams} from './types';
|
|
3
|
+
import {requestApi} from './utils';
|
|
4
|
+
|
|
5
|
+
class Navigator {
|
|
6
|
+
ref?: any;
|
|
7
|
+
utilityToolConfig: any;
|
|
8
|
+
|
|
9
|
+
constructor(navigation: any) {
|
|
10
|
+
this.ref = navigation;
|
|
11
|
+
}
|
|
12
|
+
|
|
13
|
+
push = (params: ScreenParams) => {
|
|
14
|
+
this.ref.current.dispatch(StackActions.push('Stack', params));
|
|
15
|
+
};
|
|
16
|
+
|
|
17
|
+
replace = (params: ScreenParams) => {
|
|
18
|
+
this.ref.current.dispatch(StackActions.replace('Stack', params));
|
|
19
|
+
};
|
|
20
|
+
|
|
21
|
+
pop = (count?: number) => {
|
|
22
|
+
this.ref.current.dispatch(StackActions.pop(count ?? 1));
|
|
23
|
+
};
|
|
24
|
+
|
|
25
|
+
present = (params: ScreenParams) => {
|
|
26
|
+
this.ref.current.dispatch(StackActions.push('Dialog', params));
|
|
27
|
+
};
|
|
28
|
+
|
|
29
|
+
showModal = (params: ModalParams) => {
|
|
30
|
+
this.ref.current.dispatch(StackActions.push('Modal', params));
|
|
31
|
+
};
|
|
32
|
+
|
|
33
|
+
showBottomSheet = (params: BottomSheetParams) => {
|
|
34
|
+
this.ref.current.dispatch(
|
|
35
|
+
StackActions.push('Modal', {
|
|
36
|
+
...params,
|
|
37
|
+
isBottomSheet: true,
|
|
38
|
+
}),
|
|
39
|
+
);
|
|
40
|
+
};
|
|
41
|
+
|
|
42
|
+
popToTop = () => {
|
|
43
|
+
this.ref.current.dispatch(StackActions.popToTop());
|
|
44
|
+
};
|
|
45
|
+
|
|
46
|
+
getToolkit = async () => {
|
|
47
|
+
if (this.utilityToolConfig) return this.utilityToolConfig;
|
|
48
|
+
return new Promise(resolve => {
|
|
49
|
+
requestApi('getToolkit', [null], (result: any) => {
|
|
50
|
+
if (result === true) {
|
|
51
|
+
requestApi('getToolkitConfig', [null], (config: any) => {
|
|
52
|
+
this.utilityToolConfig = {
|
|
53
|
+
...config?.utilityToolConfig,
|
|
54
|
+
appCode: config?.appCode,
|
|
55
|
+
};
|
|
56
|
+
resolve(this.utilityToolConfig);
|
|
57
|
+
});
|
|
58
|
+
} else {
|
|
59
|
+
resolve(undefined);
|
|
60
|
+
}
|
|
61
|
+
});
|
|
62
|
+
});
|
|
63
|
+
};
|
|
64
|
+
}
|
|
65
|
+
|
|
66
|
+
export default Navigator;
|
|
@@ -0,0 +1,79 @@
|
|
|
1
|
+
class Subject {
|
|
2
|
+
private observers: any[];
|
|
3
|
+
constructor() {
|
|
4
|
+
this.observers = [];
|
|
5
|
+
}
|
|
6
|
+
|
|
7
|
+
attach(observer: any) {
|
|
8
|
+
observer && this.observers.push(observer);
|
|
9
|
+
}
|
|
10
|
+
|
|
11
|
+
detach(observer: any) {
|
|
12
|
+
this.observers = this.observers.filter(item => item !== observer);
|
|
13
|
+
}
|
|
14
|
+
|
|
15
|
+
notify(newState: any) {
|
|
16
|
+
this.observers.forEach(observer => {
|
|
17
|
+
if (typeof observer === 'function') {
|
|
18
|
+
observer(newState);
|
|
19
|
+
} else {
|
|
20
|
+
observer.updateData && observer.updateData(newState);
|
|
21
|
+
}
|
|
22
|
+
});
|
|
23
|
+
}
|
|
24
|
+
}
|
|
25
|
+
|
|
26
|
+
class ObserverInstance {
|
|
27
|
+
private readonly props: any;
|
|
28
|
+
constructor(props: any) {
|
|
29
|
+
this.props = props;
|
|
30
|
+
}
|
|
31
|
+
|
|
32
|
+
remove() {
|
|
33
|
+
const {detach, observer} = this.props;
|
|
34
|
+
detach && detach(observer);
|
|
35
|
+
}
|
|
36
|
+
}
|
|
37
|
+
|
|
38
|
+
export default class Observer {
|
|
39
|
+
static SCHEMA = 'Observer';
|
|
40
|
+
|
|
41
|
+
static instances: any = {};
|
|
42
|
+
private schema: any;
|
|
43
|
+
private subject: Subject;
|
|
44
|
+
private data: null;
|
|
45
|
+
private loaded: boolean;
|
|
46
|
+
|
|
47
|
+
constructor(props: any) {
|
|
48
|
+
this.schema = props.schema;
|
|
49
|
+
this.subject = new Subject();
|
|
50
|
+
this.data = null;
|
|
51
|
+
this.loaded = false;
|
|
52
|
+
this.initilize();
|
|
53
|
+
}
|
|
54
|
+
|
|
55
|
+
static getInstance(schema: string, Class = Observer) {
|
|
56
|
+
schema = schema || Class.SCHEMA;
|
|
57
|
+
let instance = Observer.instances[schema];
|
|
58
|
+
if (!instance) {
|
|
59
|
+
instance = new Class({schema});
|
|
60
|
+
Observer.instances[schema] = instance;
|
|
61
|
+
}
|
|
62
|
+
return instance;
|
|
63
|
+
}
|
|
64
|
+
|
|
65
|
+
initilize = () => {};
|
|
66
|
+
|
|
67
|
+
notify = (state: any) => {
|
|
68
|
+
this.subject.notify(state);
|
|
69
|
+
};
|
|
70
|
+
|
|
71
|
+
attach = (observer: any) => {
|
|
72
|
+
this.subject.attach(observer);
|
|
73
|
+
return new ObserverInstance({observer, detach: this.detach});
|
|
74
|
+
};
|
|
75
|
+
|
|
76
|
+
detach = (observer: any) => {
|
|
77
|
+
this.subject.detach(observer);
|
|
78
|
+
};
|
|
79
|
+
}
|
|
@@ -0,0 +1,40 @@
|
|
|
1
|
+
import React, {useContext, useEffect} from 'react';
|
|
2
|
+
import {ScreenParams} from './types';
|
|
3
|
+
import Navigation from './Navigation';
|
|
4
|
+
import {ApplicationContext} from './NavigationContainer';
|
|
5
|
+
import {HeaderToolkitAction} from './Components';
|
|
6
|
+
|
|
7
|
+
const StackScreen: React.FC<any> = props => {
|
|
8
|
+
const {route, navigation} = props;
|
|
9
|
+
const {screen: Component, options}: ScreenParams = route.params;
|
|
10
|
+
const {theme, navigator} = useContext(ApplicationContext);
|
|
11
|
+
|
|
12
|
+
const params = {
|
|
13
|
+
...route.params,
|
|
14
|
+
navigation: new Navigation(navigation, theme),
|
|
15
|
+
};
|
|
16
|
+
|
|
17
|
+
delete params.screen;
|
|
18
|
+
|
|
19
|
+
useEffect(() => {
|
|
20
|
+
navigator?.getToolkit().then(utilityToolConfig => {
|
|
21
|
+
if (utilityToolConfig) {
|
|
22
|
+
params.navigation.setOptions({
|
|
23
|
+
headerRight: (props: any) => (
|
|
24
|
+
<HeaderToolkitAction
|
|
25
|
+
{...props}
|
|
26
|
+
utilityToolConfig={utilityToolConfig}
|
|
27
|
+
/>
|
|
28
|
+
),
|
|
29
|
+
});
|
|
30
|
+
}
|
|
31
|
+
});
|
|
32
|
+
if (options) {
|
|
33
|
+
params.navigation.setOptions(options);
|
|
34
|
+
}
|
|
35
|
+
}, [options]);
|
|
36
|
+
|
|
37
|
+
return <Component {...params} />;
|
|
38
|
+
};
|
|
39
|
+
|
|
40
|
+
export default StackScreen;
|
|
@@ -0,0 +1,14 @@
|
|
|
1
|
+
import {NavigationContainer, ApplicationContext} from './NavigationContainer';
|
|
2
|
+
import ScreenContainer from '../Layout/ScreenContainer';
|
|
3
|
+
import NavigationButton from './NavigationButton';
|
|
4
|
+
import {HeaderRightAction} from './Components';
|
|
5
|
+
import BottomTab from './BottomTab';
|
|
6
|
+
|
|
7
|
+
export {
|
|
8
|
+
NavigationContainer,
|
|
9
|
+
ApplicationContext,
|
|
10
|
+
ScreenContainer,
|
|
11
|
+
NavigationButton,
|
|
12
|
+
HeaderRightAction,
|
|
13
|
+
BottomTab,
|
|
14
|
+
};
|
|
@@ -0,0 +1,149 @@
|
|
|
1
|
+
import {Animated, ScrollViewProps, ViewProps} from 'react-native';
|
|
2
|
+
import React from 'react';
|
|
3
|
+
import Navigator from './Navigator';
|
|
4
|
+
import {PopupNotifyProps} from '../Popup/types';
|
|
5
|
+
|
|
6
|
+
export type Theme = {
|
|
7
|
+
dark: boolean;
|
|
8
|
+
colors: {
|
|
9
|
+
primary: string;
|
|
10
|
+
secondary: string;
|
|
11
|
+
background: {
|
|
12
|
+
default: string;
|
|
13
|
+
surface: string;
|
|
14
|
+
tonal: string;
|
|
15
|
+
pressed: string;
|
|
16
|
+
selected: string;
|
|
17
|
+
disable: string;
|
|
18
|
+
};
|
|
19
|
+
text: {
|
|
20
|
+
default: string;
|
|
21
|
+
secondary: string;
|
|
22
|
+
hint: string;
|
|
23
|
+
disable: string;
|
|
24
|
+
};
|
|
25
|
+
border: {
|
|
26
|
+
default: string;
|
|
27
|
+
disable: string;
|
|
28
|
+
};
|
|
29
|
+
success: {
|
|
30
|
+
primary: string;
|
|
31
|
+
secondary: string;
|
|
32
|
+
container: string;
|
|
33
|
+
};
|
|
34
|
+
warning: {
|
|
35
|
+
primary: string;
|
|
36
|
+
secondary: string;
|
|
37
|
+
container: string;
|
|
38
|
+
};
|
|
39
|
+
error: {
|
|
40
|
+
primary: string;
|
|
41
|
+
secondary: string;
|
|
42
|
+
container: string;
|
|
43
|
+
};
|
|
44
|
+
highlight: {
|
|
45
|
+
primary: string;
|
|
46
|
+
secondary: string;
|
|
47
|
+
container: string;
|
|
48
|
+
};
|
|
49
|
+
interactive: {
|
|
50
|
+
primary: string;
|
|
51
|
+
secondary: string;
|
|
52
|
+
container: string;
|
|
53
|
+
};
|
|
54
|
+
};
|
|
55
|
+
font: string;
|
|
56
|
+
assets?: {
|
|
57
|
+
headerBackground?: string;
|
|
58
|
+
};
|
|
59
|
+
};
|
|
60
|
+
|
|
61
|
+
export type Context = {
|
|
62
|
+
theme: Theme;
|
|
63
|
+
navigator?: Navigator;
|
|
64
|
+
};
|
|
65
|
+
|
|
66
|
+
export type NavigationContainerProps = {
|
|
67
|
+
screen: React.ElementType;
|
|
68
|
+
options?: NavigationOptions;
|
|
69
|
+
theme: Theme;
|
|
70
|
+
};
|
|
71
|
+
|
|
72
|
+
export interface ScreenContainerProps extends ViewProps {
|
|
73
|
+
enableKeyboardAvoidingView?: boolean;
|
|
74
|
+
headerBackground?: string;
|
|
75
|
+
scrollable?: boolean;
|
|
76
|
+
scrollY?: Animated.Value;
|
|
77
|
+
scrollViewProps?: ScrollViewProps;
|
|
78
|
+
footerComponent?: React.ElementType;
|
|
79
|
+
}
|
|
80
|
+
|
|
81
|
+
export type ScreenParams = {
|
|
82
|
+
[key: string]: any;
|
|
83
|
+
screen: React.ElementType;
|
|
84
|
+
options?: NavigationOptions;
|
|
85
|
+
};
|
|
86
|
+
|
|
87
|
+
export interface ModalParams extends ScreenParams {
|
|
88
|
+
[key: string]: any;
|
|
89
|
+
screen: React.ElementType;
|
|
90
|
+
onDismiss?: (mounted?: boolean) => void;
|
|
91
|
+
barrierDismissible?: boolean;
|
|
92
|
+
}
|
|
93
|
+
|
|
94
|
+
export interface BottomSheetParams extends ScreenParams {
|
|
95
|
+
[key: string]: any;
|
|
96
|
+
onDismiss?: () => void;
|
|
97
|
+
}
|
|
98
|
+
|
|
99
|
+
export type NavigationButtonProps = {
|
|
100
|
+
icon: string;
|
|
101
|
+
tintColor?: string;
|
|
102
|
+
backgroundColor?: string;
|
|
103
|
+
useBorder?: boolean;
|
|
104
|
+
onPress: () => void;
|
|
105
|
+
accessibilityLabel?: string;
|
|
106
|
+
};
|
|
107
|
+
|
|
108
|
+
export type NavigationOptions = {
|
|
109
|
+
preventBack?: PopupNotifyProps;
|
|
110
|
+
surface?: boolean;
|
|
111
|
+
title?: string;
|
|
112
|
+
headerTitleAlign?: 'left' | 'center';
|
|
113
|
+
customTitle?: TitleCustomProps;
|
|
114
|
+
headerRight?: (props?: any) => React.ReactElement;
|
|
115
|
+
animatedValue?: Animated.Value;
|
|
116
|
+
};
|
|
117
|
+
|
|
118
|
+
export type HeaderBackProps = {
|
|
119
|
+
tintColor?: string;
|
|
120
|
+
preventBack?: PopupNotifyProps;
|
|
121
|
+
};
|
|
122
|
+
|
|
123
|
+
export type HeaderBackgroundProps = {
|
|
124
|
+
image?: string | null;
|
|
125
|
+
backgroundColor?: string | null;
|
|
126
|
+
animatedValue?: Animated.Value;
|
|
127
|
+
};
|
|
128
|
+
|
|
129
|
+
export type TitleCustomProps = {
|
|
130
|
+
title?: string;
|
|
131
|
+
subTitle?: string;
|
|
132
|
+
image?: string;
|
|
133
|
+
imageShape?: 'circle' | 'square';
|
|
134
|
+
dotColor?: string;
|
|
135
|
+
tintColor?: string;
|
|
136
|
+
content?: React.ReactNode;
|
|
137
|
+
};
|
|
138
|
+
|
|
139
|
+
export type BottomTabItemProps = {
|
|
140
|
+
label: string;
|
|
141
|
+
icon: string;
|
|
142
|
+
showDot?: boolean;
|
|
143
|
+
badgeLabel?: string;
|
|
144
|
+
screen: React.ComponentType<any>;
|
|
145
|
+
};
|
|
146
|
+
|
|
147
|
+
export type BottomTabProps = {
|
|
148
|
+
tabs: BottomTabItemProps[];
|
|
149
|
+
};
|
|
@@ -0,0 +1,167 @@
|
|
|
1
|
+
import React from 'react';
|
|
2
|
+
import {
|
|
3
|
+
StackNavigationOptions,
|
|
4
|
+
TransitionPresets,
|
|
5
|
+
} from '@react-navigation/stack';
|
|
6
|
+
import {DeviceEventEmitter} from 'react-native';
|
|
7
|
+
import {
|
|
8
|
+
HeaderBackground,
|
|
9
|
+
HeaderCustom,
|
|
10
|
+
HeaderLeft,
|
|
11
|
+
HeaderTitle,
|
|
12
|
+
} from './Components';
|
|
13
|
+
import {NavigationOptions, Theme} from './types';
|
|
14
|
+
import {Colors} from '../Consts';
|
|
15
|
+
|
|
16
|
+
const requestApi = (func: any, args: any = [], callback: any) => {
|
|
17
|
+
const instance: any = global;
|
|
18
|
+
if (instance?.miniAppApi?.dispatch) {
|
|
19
|
+
instance?.miniAppApi?.dispatch?.(func, ...args, callback);
|
|
20
|
+
} else {
|
|
21
|
+
let listener: any;
|
|
22
|
+
const responseId = new Date().getTime();
|
|
23
|
+
const responseListener = `KIT_RESPONSE_MESSAGE_${responseId}`;
|
|
24
|
+
const TIME_OUT = 5000;
|
|
25
|
+
const timeout = setTimeout(() => {
|
|
26
|
+
listener?.remove?.();
|
|
27
|
+
}, TIME_OUT);
|
|
28
|
+
listener = DeviceEventEmitter.addListener(responseListener, result => {
|
|
29
|
+
listener?.remove?.();
|
|
30
|
+
clearTimeout(timeout);
|
|
31
|
+
callback?.(result);
|
|
32
|
+
});
|
|
33
|
+
DeviceEventEmitter.emit('KITS_REQUEST_MESSAGE', {
|
|
34
|
+
func,
|
|
35
|
+
args,
|
|
36
|
+
responseListener,
|
|
37
|
+
});
|
|
38
|
+
}
|
|
39
|
+
};
|
|
40
|
+
|
|
41
|
+
const getTintColor = (theme: Theme): any => {
|
|
42
|
+
if (theme.assets?.headerBackground) {
|
|
43
|
+
return {
|
|
44
|
+
headerTintColor: Colors.black_01,
|
|
45
|
+
};
|
|
46
|
+
}
|
|
47
|
+
return {
|
|
48
|
+
headerTintColor: theme.colors.text.default,
|
|
49
|
+
};
|
|
50
|
+
};
|
|
51
|
+
|
|
52
|
+
const getStackOptions = (theme: Theme): StackNavigationOptions => {
|
|
53
|
+
return {
|
|
54
|
+
headerTitleAlign: 'center',
|
|
55
|
+
headerTitle: HeaderTitle,
|
|
56
|
+
headerBackground: HeaderBackground,
|
|
57
|
+
headerLeft: (props: any) => <HeaderLeft {...props} />,
|
|
58
|
+
...getTintColor(theme),
|
|
59
|
+
};
|
|
60
|
+
};
|
|
61
|
+
|
|
62
|
+
const getDialogOptions = (theme: Theme): StackNavigationOptions => {
|
|
63
|
+
return {
|
|
64
|
+
headerTitleAlign: 'center',
|
|
65
|
+
headerTitle: HeaderTitle,
|
|
66
|
+
headerLeft: (props: any) => <HeaderLeft {...props} />,
|
|
67
|
+
headerBackground: HeaderBackground,
|
|
68
|
+
...getTintColor(theme),
|
|
69
|
+
...TransitionPresets.ModalTransition,
|
|
70
|
+
};
|
|
71
|
+
};
|
|
72
|
+
|
|
73
|
+
const getModalOptions = (): StackNavigationOptions => {
|
|
74
|
+
return {
|
|
75
|
+
headerShown: false,
|
|
76
|
+
headerBackground: undefined,
|
|
77
|
+
cardStyle: {backgroundColor: 'transparent'},
|
|
78
|
+
cardOverlayEnabled: true,
|
|
79
|
+
animationEnabled: false,
|
|
80
|
+
cardStyleInterpolator: ({current: {progress}}) => ({
|
|
81
|
+
cardStyle: {
|
|
82
|
+
opacity: progress.interpolate({
|
|
83
|
+
inputRange: [0, 0.5, 0.9, 1],
|
|
84
|
+
outputRange: [0, 0.25, 0.7, 1],
|
|
85
|
+
}),
|
|
86
|
+
},
|
|
87
|
+
overlayStyle: {
|
|
88
|
+
opacity: progress.interpolate({
|
|
89
|
+
inputRange: [0, 0.5, 0.9, 1],
|
|
90
|
+
outputRange: [0, 0.2, 0.4, 0.6],
|
|
91
|
+
extrapolate: 'clamp',
|
|
92
|
+
}),
|
|
93
|
+
},
|
|
94
|
+
}),
|
|
95
|
+
};
|
|
96
|
+
};
|
|
97
|
+
|
|
98
|
+
const getOptions = (params: NavigationOptions, theme: Theme) => {
|
|
99
|
+
let backgroundProps = {};
|
|
100
|
+
let titleProps = {};
|
|
101
|
+
let options = {};
|
|
102
|
+
|
|
103
|
+
if (params.preventBack) {
|
|
104
|
+
options = {
|
|
105
|
+
...options,
|
|
106
|
+
headerLeft: (props: any) => (
|
|
107
|
+
<HeaderLeft {...props} preventBack={params.preventBack} />
|
|
108
|
+
),
|
|
109
|
+
};
|
|
110
|
+
}
|
|
111
|
+
if (params.surface == true) {
|
|
112
|
+
options = {
|
|
113
|
+
...options,
|
|
114
|
+
...getTintColor({
|
|
115
|
+
...theme,
|
|
116
|
+
assets: {...theme.assets, headerBackground: undefined},
|
|
117
|
+
}),
|
|
118
|
+
};
|
|
119
|
+
backgroundProps = {
|
|
120
|
+
...backgroundProps,
|
|
121
|
+
image: null,
|
|
122
|
+
backgroundColor: theme.colors.background.surface,
|
|
123
|
+
};
|
|
124
|
+
} else {
|
|
125
|
+
backgroundProps = {};
|
|
126
|
+
options = {...options, ...getTintColor(theme)};
|
|
127
|
+
}
|
|
128
|
+
|
|
129
|
+
if (params.animatedValue) {
|
|
130
|
+
backgroundProps = {...backgroundProps, animatedValue: params.animatedValue};
|
|
131
|
+
titleProps = {...titleProps, animatedValue: params.animatedValue};
|
|
132
|
+
options = {...options, headerTransparent: true};
|
|
133
|
+
} else {
|
|
134
|
+
options = {...options, headerTransparent: false};
|
|
135
|
+
}
|
|
136
|
+
|
|
137
|
+
if (params.customTitle) {
|
|
138
|
+
options = {
|
|
139
|
+
...options,
|
|
140
|
+
headerTitleAlign: 'left',
|
|
141
|
+
headerTitle: (props: any) => {
|
|
142
|
+
return <HeaderCustom {...params.customTitle} {...props} />;
|
|
143
|
+
},
|
|
144
|
+
};
|
|
145
|
+
} else {
|
|
146
|
+
options = {
|
|
147
|
+
...options,
|
|
148
|
+
headerTitle: (props: any) => {
|
|
149
|
+
return <HeaderTitle {...titleProps} {...props} />;
|
|
150
|
+
},
|
|
151
|
+
};
|
|
152
|
+
}
|
|
153
|
+
|
|
154
|
+
return {
|
|
155
|
+
...params,
|
|
156
|
+
...options,
|
|
157
|
+
headerBackground: () => <HeaderBackground {...backgroundProps} />,
|
|
158
|
+
};
|
|
159
|
+
};
|
|
160
|
+
|
|
161
|
+
export {
|
|
162
|
+
requestApi,
|
|
163
|
+
getStackOptions,
|
|
164
|
+
getDialogOptions,
|
|
165
|
+
getModalOptions,
|
|
166
|
+
getOptions,
|
|
167
|
+
};
|
|
@@ -0,0 +1,16 @@
|
|
|
1
|
+
import React, {FC, useContext} from 'react';
|
|
2
|
+
import {Animated} from 'react-native';
|
|
3
|
+
import styles from './styles';
|
|
4
|
+
import {DotProps} from './types';
|
|
5
|
+
import {ApplicationContext} from '../Navigation';
|
|
6
|
+
|
|
7
|
+
const Dot: FC<DotProps> = ({active, style}) => {
|
|
8
|
+
const {theme} = useContext(ApplicationContext);
|
|
9
|
+
const dotStyle = active
|
|
10
|
+
? [styles.activeDot]
|
|
11
|
+
: [styles.inactiveDot, {backgroundColor: theme.colors.background.pressed}];
|
|
12
|
+
|
|
13
|
+
return <Animated.View style={[style, dotStyle]} />;
|
|
14
|
+
};
|
|
15
|
+
|
|
16
|
+
export default Dot;
|
|
@@ -0,0 +1,33 @@
|
|
|
1
|
+
import React, {FC, useContext} from 'react';
|
|
2
|
+
import {View} from 'react-native';
|
|
3
|
+
import {ChildPaginationProps} from './types';
|
|
4
|
+
import Dot from './Dot';
|
|
5
|
+
import styles from './styles';
|
|
6
|
+
import {Spacing} from '../Consts';
|
|
7
|
+
import {ApplicationContext} from '../Navigation';
|
|
8
|
+
|
|
9
|
+
const PaginationDot: FC<ChildPaginationProps> = ({
|
|
10
|
+
dataLength = 2,
|
|
11
|
+
activeIndex = 0,
|
|
12
|
+
}) => {
|
|
13
|
+
const {theme} = useContext(ApplicationContext);
|
|
14
|
+
const renderDots = () => {
|
|
15
|
+
const dots = [];
|
|
16
|
+
for (let i = 0; i < dataLength; i++) {
|
|
17
|
+
dots.push(
|
|
18
|
+
<Dot
|
|
19
|
+
key={`Dot${i}`}
|
|
20
|
+
style={[
|
|
21
|
+
i !== dataLength - 1 ? {marginRight: Spacing.XS} : {},
|
|
22
|
+
{backgroundColor: theme.colors.primary},
|
|
23
|
+
]}
|
|
24
|
+
active={activeIndex === i}
|
|
25
|
+
/>,
|
|
26
|
+
);
|
|
27
|
+
}
|
|
28
|
+
return dots;
|
|
29
|
+
};
|
|
30
|
+
return <View style={styles.paginationPinkContainer}>{renderDots()}</View>;
|
|
31
|
+
};
|
|
32
|
+
|
|
33
|
+
export default PaginationDot;
|
|
@@ -0,0 +1,23 @@
|
|
|
1
|
+
import React, {FC, useContext} from 'react';
|
|
2
|
+
import {View} from 'react-native';
|
|
3
|
+
import {ChildPaginationProps} from './types';
|
|
4
|
+
import styles from './styles';
|
|
5
|
+
import {Text} from '../Text';
|
|
6
|
+
import {ApplicationContext} from '../Navigation';
|
|
7
|
+
import {Colors} from '../Consts';
|
|
8
|
+
|
|
9
|
+
const PaginationNumber: FC<ChildPaginationProps> = ({
|
|
10
|
+
activeIndex = 0,
|
|
11
|
+
dataLength = 2,
|
|
12
|
+
}) => {
|
|
13
|
+
const {theme} = useContext(ApplicationContext);
|
|
14
|
+
return (
|
|
15
|
+
<View style={[styles.paginationNumberContainer]}>
|
|
16
|
+
<Text color={Colors.black_01} typography={'label_default'}>{`${
|
|
17
|
+
activeIndex + 1
|
|
18
|
+
}/${dataLength}`}</Text>
|
|
19
|
+
</View>
|
|
20
|
+
);
|
|
21
|
+
};
|
|
22
|
+
|
|
23
|
+
export default PaginationNumber;
|
|
@@ -0,0 +1,88 @@
|
|
|
1
|
+
import React, {FC, useContext, useRef, useState} from 'react';
|
|
2
|
+
import {Animated, View} from 'react-native';
|
|
3
|
+
import {ScrollIndicatorProps} from './types';
|
|
4
|
+
import styles from './styles';
|
|
5
|
+
import {ApplicationContext} from '../Navigation';
|
|
6
|
+
|
|
7
|
+
const INDICATOR_WIDTH = 24;
|
|
8
|
+
const INDICATOR_CONTAINER_WIDTH = 72;
|
|
9
|
+
const PaginationScroll: FC<ScrollIndicatorProps> = ({
|
|
10
|
+
style,
|
|
11
|
+
children,
|
|
12
|
+
scrollViewRef,
|
|
13
|
+
}) => {
|
|
14
|
+
const {theme} = useContext(ApplicationContext);
|
|
15
|
+
const left = useRef(new Animated.Value(0)).current;
|
|
16
|
+
const [scrollViewWidth, setScrollViewWidth] = useState(0);
|
|
17
|
+
const [scrollContentWidth, setScrollContentWidth] = useState(0);
|
|
18
|
+
|
|
19
|
+
const translateX = () => {
|
|
20
|
+
if (scrollViewWidth && scrollContentWidth) {
|
|
21
|
+
const value = left.interpolate({
|
|
22
|
+
inputRange: [0, scrollContentWidth - scrollViewWidth],
|
|
23
|
+
outputRange: [0, INDICATOR_CONTAINER_WIDTH - INDICATOR_WIDTH],
|
|
24
|
+
extrapolate: 'clamp',
|
|
25
|
+
});
|
|
26
|
+
return {transform: [{translateX: value}]};
|
|
27
|
+
}
|
|
28
|
+
return {};
|
|
29
|
+
};
|
|
30
|
+
|
|
31
|
+
const renderScrollView = () => {
|
|
32
|
+
return (
|
|
33
|
+
<Animated.ScrollView
|
|
34
|
+
ref={scrollViewRef}
|
|
35
|
+
onScroll={Animated.event(
|
|
36
|
+
[
|
|
37
|
+
{
|
|
38
|
+
nativeEvent: {
|
|
39
|
+
contentOffset: {
|
|
40
|
+
x: left,
|
|
41
|
+
},
|
|
42
|
+
},
|
|
43
|
+
},
|
|
44
|
+
],
|
|
45
|
+
{useNativeDriver: true},
|
|
46
|
+
)}
|
|
47
|
+
alwaysBounceHorizontal={false}
|
|
48
|
+
showsHorizontalScrollIndicator={false}
|
|
49
|
+
horizontal
|
|
50
|
+
style={styles.scrollView}
|
|
51
|
+
onContentSizeChange={width => {
|
|
52
|
+
setScrollContentWidth(width);
|
|
53
|
+
}}
|
|
54
|
+
onLayout={e => {
|
|
55
|
+
setScrollViewWidth(e.nativeEvent.layout.width);
|
|
56
|
+
}}>
|
|
57
|
+
{children}
|
|
58
|
+
</Animated.ScrollView>
|
|
59
|
+
);
|
|
60
|
+
};
|
|
61
|
+
const renderIndicator = () => {
|
|
62
|
+
return (
|
|
63
|
+
<View
|
|
64
|
+
style={[
|
|
65
|
+
styles.indicatorContainer,
|
|
66
|
+
{backgroundColor: theme.colors.background.pressed},
|
|
67
|
+
]}>
|
|
68
|
+
<Animated.View
|
|
69
|
+
style={[
|
|
70
|
+
styles.indicator,
|
|
71
|
+
{
|
|
72
|
+
backgroundColor: theme.colors.primary,
|
|
73
|
+
},
|
|
74
|
+
translateX(),
|
|
75
|
+
]}
|
|
76
|
+
/>
|
|
77
|
+
</View>
|
|
78
|
+
);
|
|
79
|
+
};
|
|
80
|
+
return (
|
|
81
|
+
<View style={[style, styles.scrollContainer]}>
|
|
82
|
+
{renderScrollView()}
|
|
83
|
+
{renderIndicator()}
|
|
84
|
+
</View>
|
|
85
|
+
);
|
|
86
|
+
};
|
|
87
|
+
|
|
88
|
+
export default PaginationScroll;
|