@aws-amplify/ui-react-native 0.0.0-in-app-messaging-20220826014803
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/.eslintrc.js +100 -0
- package/.lintstagedrc.js +6 -0
- package/.turbo/turbo-build.log +4 -0
- package/CHANGELOG.md +11 -0
- package/LICENSE +201 -0
- package/README.md +25 -0
- package/babel.config.js +3 -0
- package/dist/InAppMessaging/components/BannerMessage/BannerMessage.d.ts +3 -0
- package/dist/InAppMessaging/components/BannerMessage/BannerMessage.js +16 -0
- package/dist/InAppMessaging/components/BannerMessage/index.d.ts +2 -0
- package/dist/InAppMessaging/components/BannerMessage/index.js +1 -0
- package/dist/InAppMessaging/components/BannerMessage/styles.d.ts +7 -0
- package/dist/InAppMessaging/components/BannerMessage/styles.js +77 -0
- package/dist/InAppMessaging/components/BannerMessage/types.d.ts +12 -0
- package/dist/InAppMessaging/components/BannerMessage/types.js +1 -0
- package/dist/InAppMessaging/components/CarouselMessage/CarouselMessage.d.ts +3 -0
- package/dist/InAppMessaging/components/CarouselMessage/CarouselMessage.js +20 -0
- package/dist/InAppMessaging/components/CarouselMessage/CarouselMessageItem.d.ts +3 -0
- package/dist/InAppMessaging/components/CarouselMessage/CarouselMessageItem.js +18 -0
- package/dist/InAppMessaging/components/CarouselMessage/index.d.ts +2 -0
- package/dist/InAppMessaging/components/CarouselMessage/index.js +1 -0
- package/dist/InAppMessaging/components/CarouselMessage/styles.d.ts +5 -0
- package/dist/InAppMessaging/components/CarouselMessage/styles.js +98 -0
- package/dist/InAppMessaging/components/CarouselMessage/types.d.ts +18 -0
- package/dist/InAppMessaging/components/CarouselMessage/types.js +1 -0
- package/dist/InAppMessaging/components/FullScreenMessage/FullScreenMessage.d.ts +3 -0
- package/dist/InAppMessaging/components/FullScreenMessage/FullScreenMessage.js +18 -0
- package/dist/InAppMessaging/components/FullScreenMessage/index.d.ts +2 -0
- package/dist/InAppMessaging/components/FullScreenMessage/index.js +1 -0
- package/dist/InAppMessaging/components/FullScreenMessage/styles.d.ts +3 -0
- package/dist/InAppMessaging/components/FullScreenMessage/styles.js +86 -0
- package/dist/InAppMessaging/components/FullScreenMessage/types.d.ts +6 -0
- package/dist/InAppMessaging/components/FullScreenMessage/types.js +1 -0
- package/dist/InAppMessaging/components/InAppMessageDisplay/InAppMessageDisplay.d.ts +10 -0
- package/dist/InAppMessaging/components/InAppMessageDisplay/InAppMessageDisplay.js +29 -0
- package/dist/InAppMessaging/components/InAppMessageDisplay/handleMessageLinkAction.d.ts +3 -0
- package/dist/InAppMessaging/components/InAppMessageDisplay/handleMessageLinkAction.js +24 -0
- package/dist/InAppMessaging/components/InAppMessageDisplay/index.d.ts +2 -0
- package/dist/InAppMessaging/components/InAppMessageDisplay/index.js +1 -0
- package/dist/InAppMessaging/components/InAppMessageDisplay/types.d.ts +24 -0
- package/dist/InAppMessaging/components/InAppMessageDisplay/types.js +1 -0
- package/dist/InAppMessaging/components/MessageLayout/MessageLayout.d.ts +3 -0
- package/dist/InAppMessaging/components/MessageLayout/MessageLayout.js +34 -0
- package/dist/InAppMessaging/components/MessageLayout/index.d.ts +1 -0
- package/dist/InAppMessaging/components/MessageLayout/index.js +1 -0
- package/dist/InAppMessaging/components/MessageLayout/types.d.ts +7 -0
- package/dist/InAppMessaging/components/MessageLayout/types.js +1 -0
- package/dist/InAppMessaging/components/MessageWrapper/MessageWrapper.d.ts +3 -0
- package/dist/InAppMessaging/components/MessageWrapper/MessageWrapper.js +20 -0
- package/dist/InAppMessaging/components/MessageWrapper/index.d.ts +2 -0
- package/dist/InAppMessaging/components/MessageWrapper/index.js +1 -0
- package/dist/InAppMessaging/components/MessageWrapper/styles.d.ts +2 -0
- package/dist/InAppMessaging/components/MessageWrapper/styles.js +5 -0
- package/dist/InAppMessaging/components/MessageWrapper/types.d.ts +10 -0
- package/dist/InAppMessaging/components/MessageWrapper/types.js +1 -0
- package/dist/InAppMessaging/components/ModalMessage/ModalMessage.d.ts +3 -0
- package/dist/InAppMessaging/components/ModalMessage/ModalMessage.js +18 -0
- package/dist/InAppMessaging/components/ModalMessage/index.d.ts +2 -0
- package/dist/InAppMessaging/components/ModalMessage/index.js +1 -0
- package/dist/InAppMessaging/components/ModalMessage/styles.d.ts +4 -0
- package/dist/InAppMessaging/components/ModalMessage/styles.js +99 -0
- package/dist/InAppMessaging/components/ModalMessage/types.d.ts +6 -0
- package/dist/InAppMessaging/components/ModalMessage/types.js +1 -0
- package/dist/InAppMessaging/components/index.d.ts +6 -0
- package/dist/InAppMessaging/components/index.js +2 -0
- package/dist/InAppMessaging/components/withInAppMessaging/index.d.ts +1 -0
- package/dist/InAppMessaging/components/withInAppMessaging/index.js +1 -0
- package/dist/InAppMessaging/components/withInAppMessaging/withInAppMessaging.d.ts +5 -0
- package/dist/InAppMessaging/components/withInAppMessaging/withInAppMessaging.js +11 -0
- package/dist/InAppMessaging/constants.d.ts +31 -0
- package/dist/InAppMessaging/constants.js +43 -0
- package/dist/InAppMessaging/hooks/index.d.ts +2 -0
- package/dist/InAppMessaging/hooks/index.js +2 -0
- package/dist/InAppMessaging/hooks/useMessageImage/constants.d.ts +8 -0
- package/dist/InAppMessaging/hooks/useMessageImage/constants.js +18 -0
- package/dist/InAppMessaging/hooks/useMessageImage/index.d.ts +2 -0
- package/dist/InAppMessaging/hooks/useMessageImage/index.js +1 -0
- package/dist/InAppMessaging/hooks/useMessageImage/types.d.ts +15 -0
- package/dist/InAppMessaging/hooks/useMessageImage/types.js +6 -0
- package/dist/InAppMessaging/hooks/useMessageImage/useMessageImage.d.ts +10 -0
- package/dist/InAppMessaging/hooks/useMessageImage/useMessageImage.js +50 -0
- package/dist/InAppMessaging/hooks/useMessageImage/utils.d.ts +4 -0
- package/dist/InAppMessaging/hooks/useMessageImage/utils.js +56 -0
- package/dist/InAppMessaging/hooks/useMessageProps/index.d.ts +2 -0
- package/dist/InAppMessaging/hooks/useMessageProps/index.js +1 -0
- package/dist/InAppMessaging/hooks/useMessageProps/types.d.ts +109 -0
- package/dist/InAppMessaging/hooks/useMessageProps/types.js +1 -0
- package/dist/InAppMessaging/hooks/useMessageProps/useMessageProps.d.ts +12 -0
- package/dist/InAppMessaging/hooks/useMessageProps/useMessageProps.js +49 -0
- package/dist/InAppMessaging/hooks/useMessageProps/utils.d.ts +43 -0
- package/dist/InAppMessaging/hooks/useMessageProps/utils.js +192 -0
- package/dist/InAppMessaging/index.d.ts +2 -0
- package/dist/InAppMessaging/index.js +2 -0
- package/dist/__mocks__/react-native-safe-area-context.d.ts +3 -0
- package/dist/__mocks__/react-native-safe-area-context.js +4 -0
- package/dist/assets/close.png +0 -0
- package/dist/assets/index.d.ts +5 -0
- package/dist/assets/index.js +4 -0
- package/dist/assets/index.ts +7 -0
- package/dist/hooks/index.d.ts +1 -0
- package/dist/hooks/index.js +1 -0
- package/dist/hooks/useDeviceOrientation/index.d.ts +1 -0
- package/dist/hooks/useDeviceOrientation/index.js +1 -0
- package/dist/hooks/useDeviceOrientation/useDeviceOrientation.d.ts +6 -0
- package/dist/hooks/useDeviceOrientation/useDeviceOrientation.js +33 -0
- package/dist/index.d.ts +1 -0
- package/dist/index.js +1 -0
- package/dist/primitives/Button/Button.d.ts +3 -0
- package/dist/primitives/Button/Button.js +8 -0
- package/dist/primitives/Button/index.d.ts +2 -0
- package/dist/primitives/Button/index.js +1 -0
- package/dist/primitives/Button/styles.d.ts +2 -0
- package/dist/primitives/Button/styles.js +4 -0
- package/dist/primitives/Button/types.d.ts +7 -0
- package/dist/primitives/Button/types.js +1 -0
- package/dist/primitives/Carousel/Carousel.d.ts +3 -0
- package/dist/primitives/Carousel/Carousel.js +58 -0
- package/dist/primitives/Carousel/CarouselPageIndicator.d.ts +3 -0
- package/dist/primitives/Carousel/CarouselPageIndicator.js +10 -0
- package/dist/primitives/Carousel/constants.d.ts +9 -0
- package/dist/primitives/Carousel/constants.js +18 -0
- package/dist/primitives/Carousel/index.d.ts +3 -0
- package/dist/primitives/Carousel/index.js +2 -0
- package/dist/primitives/Carousel/styles.d.ts +2 -0
- package/dist/primitives/Carousel/styles.js +11 -0
- package/dist/primitives/Carousel/types.d.ts +19 -0
- package/dist/primitives/Carousel/types.js +1 -0
- package/dist/primitives/IconButton/IconButton.d.ts +3 -0
- package/dist/primitives/IconButton/IconButton.js +9 -0
- package/dist/primitives/IconButton/index.d.ts +2 -0
- package/dist/primitives/IconButton/index.js +1 -0
- package/dist/primitives/IconButton/styles.d.ts +2 -0
- package/dist/primitives/IconButton/styles.js +9 -0
- package/dist/primitives/IconButton/types.d.ts +18 -0
- package/dist/primitives/IconButton/types.js +1 -0
- package/dist/primitives/index.d.ts +3 -0
- package/dist/primitives/index.js +3 -0
- package/dist/utils/index.d.ts +1 -0
- package/dist/utils/index.js +4 -0
- package/jest.config.js +20 -0
- package/package.json +55 -0
- package/src/InAppMessaging/components/BannerMessage/BannerMessage.tsx +37 -0
- package/src/InAppMessaging/components/BannerMessage/__tests__/BannerMessage.spec.tsx +138 -0
- package/src/InAppMessaging/components/BannerMessage/__tests__/__snapshots__/BannerMessage.spec.tsx.snap +224 -0
- package/src/InAppMessaging/components/BannerMessage/index.ts +2 -0
- package/src/InAppMessaging/components/BannerMessage/styles.ts +105 -0
- package/src/InAppMessaging/components/BannerMessage/types.ts +15 -0
- package/src/InAppMessaging/components/CarouselMessage/CarouselMessage.tsx +42 -0
- package/src/InAppMessaging/components/CarouselMessage/CarouselMessageItem.tsx +37 -0
- package/src/InAppMessaging/components/CarouselMessage/__tests__/CarouselMessage.spec.tsx +55 -0
- package/src/InAppMessaging/components/CarouselMessage/__tests__/CarouselMessageItem.spec.tsx +56 -0
- package/src/InAppMessaging/components/CarouselMessage/__tests__/__snapshots__/CarouselMessage.spec.tsx.snap +86 -0
- package/src/InAppMessaging/components/CarouselMessage/__tests__/__snapshots__/CarouselMessageItem.spec.tsx.snap +248 -0
- package/src/InAppMessaging/components/CarouselMessage/index.ts +2 -0
- package/src/InAppMessaging/components/CarouselMessage/styles.ts +125 -0
- package/src/InAppMessaging/components/CarouselMessage/types.ts +28 -0
- package/src/InAppMessaging/components/FullScreenMessage/FullScreenMessage.tsx +38 -0
- package/src/InAppMessaging/components/FullScreenMessage/__tests__/FullScreenMessage.spec.tsx +53 -0
- package/src/InAppMessaging/components/FullScreenMessage/__tests__/__snapshots__/FullScreenMessage.spec.tsx.snap +236 -0
- package/src/InAppMessaging/components/FullScreenMessage/index.ts +2 -0
- package/src/InAppMessaging/components/FullScreenMessage/styles.ts +106 -0
- package/src/InAppMessaging/components/FullScreenMessage/types.ts +7 -0
- package/src/InAppMessaging/components/InAppMessageDisplay/InAppMessageDisplay.tsx +48 -0
- package/src/InAppMessaging/components/InAppMessageDisplay/__tests__/InAppMessageDisplay.spec.tsx +33 -0
- package/src/InAppMessaging/components/InAppMessageDisplay/__tests__/__snapshots__/InAppMessageDisplay.spec.tsx.snap +9 -0
- package/src/InAppMessaging/components/InAppMessageDisplay/__tests__/handleMessageLinkAction.spec.ts +51 -0
- package/src/InAppMessaging/components/InAppMessageDisplay/handleMessageLinkAction.ts +30 -0
- package/src/InAppMessaging/components/InAppMessageDisplay/index.ts +2 -0
- package/src/InAppMessaging/components/InAppMessageDisplay/types.ts +32 -0
- package/src/InAppMessaging/components/MessageLayout/MessageLayout.tsx +102 -0
- package/src/InAppMessaging/components/MessageLayout/index.ts +1 -0
- package/src/InAppMessaging/components/MessageLayout/types.ts +15 -0
- package/src/InAppMessaging/components/MessageWrapper/MessageWrapper.tsx +34 -0
- package/src/InAppMessaging/components/MessageWrapper/__tests__/MessageWrapper.spec.tsx +19 -0
- package/src/InAppMessaging/components/MessageWrapper/__tests__/__snapshots__/MessageWrapper.spec.tsx.snap +35 -0
- package/src/InAppMessaging/components/MessageWrapper/index.ts +2 -0
- package/src/InAppMessaging/components/MessageWrapper/styles.ts +7 -0
- package/src/InAppMessaging/components/MessageWrapper/types.ts +12 -0
- package/src/InAppMessaging/components/ModalMessage/ModalMessage.tsx +37 -0
- package/src/InAppMessaging/components/ModalMessage/__tests__/ModalMessage.spec.tsx +155 -0
- package/src/InAppMessaging/components/ModalMessage/__tests__/__snapshots__/ModalMessage.spec.tsx.snap +323 -0
- package/src/InAppMessaging/components/ModalMessage/index.ts +2 -0
- package/src/InAppMessaging/components/ModalMessage/styles.ts +132 -0
- package/src/InAppMessaging/components/ModalMessage/types.ts +8 -0
- package/src/InAppMessaging/components/index.ts +6 -0
- package/src/InAppMessaging/components/withInAppMessaging/__tests__/__snapshots__/withInAppMessaging.spec.tsx.snap +3 -0
- package/src/InAppMessaging/components/withInAppMessaging/__tests__/withInAppMessaging.spec.tsx +15 -0
- package/src/InAppMessaging/components/withInAppMessaging/index.ts +1 -0
- package/src/InAppMessaging/components/withInAppMessaging/withInAppMessaging.tsx +18 -0
- package/src/InAppMessaging/constants.ts +56 -0
- package/src/InAppMessaging/hooks/index.ts +9 -0
- package/src/InAppMessaging/hooks/useMessageImage/__tests__/useMessageImage.spec.ts +141 -0
- package/src/InAppMessaging/hooks/useMessageImage/__tests__/utils.spec.ts +107 -0
- package/src/InAppMessaging/hooks/useMessageImage/constants.ts +27 -0
- package/src/InAppMessaging/hooks/useMessageImage/index.ts +2 -0
- package/src/InAppMessaging/hooks/useMessageImage/types.ts +18 -0
- package/src/InAppMessaging/hooks/useMessageImage/useMessageImage.ts +74 -0
- package/src/InAppMessaging/hooks/useMessageImage/utils.ts +80 -0
- package/src/InAppMessaging/hooks/useMessageProps/__tests__/__snapshots__/utils.spec.ts.snap +223 -0
- package/src/InAppMessaging/hooks/useMessageProps/__tests__/useMessageProps.spec.ts +162 -0
- package/src/InAppMessaging/hooks/useMessageProps/__tests__/utils.spec.ts +354 -0
- package/src/InAppMessaging/hooks/useMessageProps/index.ts +8 -0
- package/src/InAppMessaging/hooks/useMessageProps/types.ts +131 -0
- package/src/InAppMessaging/hooks/useMessageProps/useMessageProps.ts +70 -0
- package/src/InAppMessaging/hooks/useMessageProps/utils.ts +274 -0
- package/src/InAppMessaging/index.ts +14 -0
- package/src/__mocks__/react-native-safe-area-context.ts +6 -0
- package/src/__tests__/__snapshots__/index.spec.ts.snap +15 -0
- package/src/__tests__/index.spec.ts +8 -0
- package/src/assets/close.png +0 -0
- package/src/assets/index.ts +7 -0
- package/src/hooks/index.ts +4 -0
- package/src/hooks/useDeviceOrientation/__tests__/useDeviceOrientation.spec.ts +87 -0
- package/src/hooks/useDeviceOrientation/index.ts +4 -0
- package/src/hooks/useDeviceOrientation/useDeviceOrientation.ts +47 -0
- package/src/index.ts +1 -0
- package/src/primitives/Button/Button.tsx +21 -0
- package/src/primitives/Button/__tests__/Button.spec.tsx +24 -0
- package/src/primitives/Button/__tests__/__snapshots__/Button.spec.tsx.snap +52 -0
- package/src/primitives/Button/index.ts +2 -0
- package/src/primitives/Button/styles.ts +6 -0
- package/src/primitives/Button/types.ts +9 -0
- package/src/primitives/Carousel/Carousel.tsx +115 -0
- package/src/primitives/Carousel/CarouselPageIndicator.tsx +39 -0
- package/src/primitives/Carousel/__tests__/Carousel.spec.tsx +185 -0
- package/src/primitives/Carousel/__tests__/CarouselPageIndicator.spec.tsx +71 -0
- package/src/primitives/Carousel/__tests__/__snapshots__/Carousel.spec.tsx.snap +216 -0
- package/src/primitives/Carousel/__tests__/__snapshots__/CarouselPageIndicator.spec.tsx.snap +191 -0
- package/src/primitives/Carousel/constants.ts +25 -0
- package/src/primitives/Carousel/index.ts +3 -0
- package/src/primitives/Carousel/styles.ts +14 -0
- package/src/primitives/Carousel/types.ts +22 -0
- package/src/primitives/IconButton/IconButton.tsx +20 -0
- package/src/primitives/IconButton/__tests__/IconButton.spec.tsx +13 -0
- package/src/primitives/IconButton/__tests__/__snapshots__/IconButton.spec.tsx.snap +34 -0
- package/src/primitives/IconButton/index.ts +2 -0
- package/src/primitives/IconButton/styles.ts +16 -0
- package/src/primitives/IconButton/types.ts +27 -0
- package/src/primitives/index.ts +3 -0
- package/src/utils/index.ts +6 -0
- package/tsconfig.dist.json +4 -0
- package/tsconfig.json +21 -0
|
@@ -0,0 +1,274 @@
|
|
|
1
|
+
import { StyleSheet } from 'react-native';
|
|
2
|
+
import {
|
|
3
|
+
MessageComponentBaseProps,
|
|
4
|
+
MessageLayout,
|
|
5
|
+
MessagePayloadStyle,
|
|
6
|
+
} from '@aws-amplify/ui-react-core';
|
|
7
|
+
|
|
8
|
+
import { DEFAULT_CAROUSEL_INDICATOR_SIZE } from '../../../primitives';
|
|
9
|
+
import { BUTTON_PRESSED_OPACITY, SPACING_EXTRA_LARGE } from '../../constants';
|
|
10
|
+
|
|
11
|
+
import {
|
|
12
|
+
MessageButtonStyleParams,
|
|
13
|
+
MessageButtonStyleProps,
|
|
14
|
+
MessageComponentStyles,
|
|
15
|
+
MessageContainerAndWrapperStyle,
|
|
16
|
+
MessageStyleParams,
|
|
17
|
+
} from './types';
|
|
18
|
+
|
|
19
|
+
// Carousel page indicator size + margins
|
|
20
|
+
const DEFAULT_CAROUSEL_INDICATOR_PADDING =
|
|
21
|
+
(DEFAULT_CAROUSEL_INDICATOR_SIZE * 5) / 3;
|
|
22
|
+
|
|
23
|
+
/**
|
|
24
|
+
* Parse and assign appropriate button container and text style from style objects params
|
|
25
|
+
*
|
|
26
|
+
* @param {MessageButtonStyleParams} params - message styleParams and button type
|
|
27
|
+
* @returns {MessageButtonStyleProps} resolved button container and text style arrays
|
|
28
|
+
*/
|
|
29
|
+
export const getComponentButtonStyle = ({
|
|
30
|
+
styleParams,
|
|
31
|
+
buttonType,
|
|
32
|
+
}: MessageButtonStyleParams): MessageButtonStyleProps => {
|
|
33
|
+
const { defaultStyle, payloadStyle, overrideStyle } = styleParams;
|
|
34
|
+
// default component styles defined at the UI component level
|
|
35
|
+
const {
|
|
36
|
+
buttonContainer: containerDefaultStyle = {},
|
|
37
|
+
buttonText: textDefaultStyle = {},
|
|
38
|
+
} = defaultStyle ?? {};
|
|
39
|
+
|
|
40
|
+
// message specific styles in the in-app message payload, overrides default component styles
|
|
41
|
+
const { backgroundColor, borderRadius, color } =
|
|
42
|
+
payloadStyle?.[buttonType] ?? {};
|
|
43
|
+
|
|
44
|
+
const containePayloadStyle = {
|
|
45
|
+
...(backgroundColor ? { backgroundColor } : null),
|
|
46
|
+
...(borderRadius ? { borderRadius } : null),
|
|
47
|
+
};
|
|
48
|
+
|
|
49
|
+
const textMessageStyle = { ...(color ? { color } : null) };
|
|
50
|
+
|
|
51
|
+
// custom component override styles passed as style prop, overrides all previous styles
|
|
52
|
+
const {
|
|
53
|
+
container: containerOverrideStyle = {},
|
|
54
|
+
text: textOverrideStyle = {},
|
|
55
|
+
} = overrideStyle?.[buttonType] ?? {};
|
|
56
|
+
|
|
57
|
+
return {
|
|
58
|
+
// the style prop of the React Native Pressable component used in the message UI accepts either a ViewStyle array
|
|
59
|
+
// or a function receiving a boolean reflecting whether the component is currently pressed, returning a ViewStyle
|
|
60
|
+
// array. Utilizing the latter, we add an opacity value to the UI message button style during press events
|
|
61
|
+
container: ({ pressed } = { pressed: false }) => {
|
|
62
|
+
// default button press interaction opacity
|
|
63
|
+
const pressedOpacity = pressed ? { opacity: BUTTON_PRESSED_OPACITY } : {};
|
|
64
|
+
|
|
65
|
+
// pass `pressed` to containerOverrideStyle and evaluate if the consumer passed a function for custom
|
|
66
|
+
// button style
|
|
67
|
+
const containerOverrideFinalStyle =
|
|
68
|
+
typeof containerOverrideStyle === 'function'
|
|
69
|
+
? containerOverrideStyle({ pressed })
|
|
70
|
+
: containerOverrideStyle;
|
|
71
|
+
|
|
72
|
+
return [
|
|
73
|
+
pressedOpacity,
|
|
74
|
+
containerDefaultStyle,
|
|
75
|
+
containePayloadStyle,
|
|
76
|
+
containerOverrideFinalStyle,
|
|
77
|
+
];
|
|
78
|
+
},
|
|
79
|
+
text: [textDefaultStyle, textMessageStyle, textOverrideStyle],
|
|
80
|
+
};
|
|
81
|
+
};
|
|
82
|
+
|
|
83
|
+
/**
|
|
84
|
+
* Utility for determining if the provided layout requires filling the entire device screen.
|
|
85
|
+
*
|
|
86
|
+
* @param {InAppMessageLayout} layout - message layout
|
|
87
|
+
* @returns {Boolean} boolean indicating whether entire screen should be filled
|
|
88
|
+
*/
|
|
89
|
+
|
|
90
|
+
export const shouldFillDeviceScreen = (layout: MessageLayout): boolean => {
|
|
91
|
+
switch (layout) {
|
|
92
|
+
case 'CAROUSEL':
|
|
93
|
+
case 'FULL_SCREEN': {
|
|
94
|
+
return true;
|
|
95
|
+
}
|
|
96
|
+
case 'MODAL':
|
|
97
|
+
case 'TOP_BANNER':
|
|
98
|
+
case 'MIDDLE_BANNER':
|
|
99
|
+
case 'BOTTOM_BANNER':
|
|
100
|
+
default: {
|
|
101
|
+
return false;
|
|
102
|
+
}
|
|
103
|
+
}
|
|
104
|
+
};
|
|
105
|
+
|
|
106
|
+
/**
|
|
107
|
+
* Parse and assign appropriate message container and wrapper style from style params
|
|
108
|
+
*
|
|
109
|
+
* @param {MessageStyleParams} params - message styleParams, layout, and device orientation
|
|
110
|
+
* @returns {ContainerAndWrapperStyle} resolved containerStyle and wrapperStyle
|
|
111
|
+
*/
|
|
112
|
+
|
|
113
|
+
export const getContainerAndWrapperStyle = ({
|
|
114
|
+
styleParams,
|
|
115
|
+
layout,
|
|
116
|
+
}: MessageStyleParams): MessageContainerAndWrapperStyle => {
|
|
117
|
+
const { defaultStyle, payloadStyle, overrideStyle } = styleParams;
|
|
118
|
+
|
|
119
|
+
const containerDefaultStyle = defaultStyle?.container ?? {};
|
|
120
|
+
const containerPayloadStyle = payloadStyle?.container ?? {};
|
|
121
|
+
const containerOverrideStyle = overrideStyle?.container ?? {};
|
|
122
|
+
|
|
123
|
+
const wrapperDefaultStyle = defaultStyle?.wrapper ?? {};
|
|
124
|
+
|
|
125
|
+
if (!shouldFillDeviceScreen(layout)) {
|
|
126
|
+
return {
|
|
127
|
+
wrapper: wrapperDefaultStyle,
|
|
128
|
+
container: [
|
|
129
|
+
containerDefaultStyle,
|
|
130
|
+
containerPayloadStyle,
|
|
131
|
+
containerOverrideStyle,
|
|
132
|
+
],
|
|
133
|
+
};
|
|
134
|
+
}
|
|
135
|
+
|
|
136
|
+
// in non-banner and landscape modal layouts container backgroundColor values should be applied as
|
|
137
|
+
// wrapper style to ensure that the backgroundColor is applied to the entire screen
|
|
138
|
+
const {
|
|
139
|
+
backgroundColor: defaultBackgroundColor,
|
|
140
|
+
...restContainerDefaultStyle
|
|
141
|
+
} = containerDefaultStyle;
|
|
142
|
+
const {
|
|
143
|
+
backgroundColor: messageBackgroundColor,
|
|
144
|
+
...restContainerPayloadStyle
|
|
145
|
+
} = containerPayloadStyle;
|
|
146
|
+
|
|
147
|
+
// flatten overrideStyle to access override backgroundColor
|
|
148
|
+
const {
|
|
149
|
+
backgroundColor: overrideBackgroundColor,
|
|
150
|
+
...restContainerOverrideStyle
|
|
151
|
+
} = StyleSheet.flatten(containerOverrideStyle);
|
|
152
|
+
|
|
153
|
+
// all non-backgroundColor container override style are applied to the container View
|
|
154
|
+
const container: MessageContainerAndWrapperStyle['container'] = [
|
|
155
|
+
restContainerDefaultStyle,
|
|
156
|
+
restContainerPayloadStyle,
|
|
157
|
+
restContainerOverrideStyle,
|
|
158
|
+
];
|
|
159
|
+
|
|
160
|
+
// use ternaries to prevent passing backgroundColor object with undefined or null value
|
|
161
|
+
const wrapper: MessageContainerAndWrapperStyle['wrapper'] = [
|
|
162
|
+
wrapperDefaultStyle,
|
|
163
|
+
defaultBackgroundColor ? { backgroundColor: defaultBackgroundColor } : {},
|
|
164
|
+
messageBackgroundColor ? { backgroundColor: messageBackgroundColor } : {},
|
|
165
|
+
overrideBackgroundColor ? { backgroundColor: overrideBackgroundColor } : {},
|
|
166
|
+
];
|
|
167
|
+
|
|
168
|
+
return { wrapper, container };
|
|
169
|
+
};
|
|
170
|
+
|
|
171
|
+
/**
|
|
172
|
+
* Utility for extracting message payload style
|
|
173
|
+
*
|
|
174
|
+
* @param {MessageComponentBaseProps} props - message props
|
|
175
|
+
* @returns {Object} message payload specific style
|
|
176
|
+
*/
|
|
177
|
+
|
|
178
|
+
export const getPayloadStyle = ({
|
|
179
|
+
body,
|
|
180
|
+
container,
|
|
181
|
+
header,
|
|
182
|
+
primaryButton,
|
|
183
|
+
secondaryButton,
|
|
184
|
+
}: MessageComponentBaseProps): MessagePayloadStyle => ({
|
|
185
|
+
body: body?.style ?? {},
|
|
186
|
+
container: container?.style ?? {},
|
|
187
|
+
header: header?.style ?? {},
|
|
188
|
+
primaryButton: primaryButton?.style ?? {},
|
|
189
|
+
secondaryButton: secondaryButton?.style ?? {},
|
|
190
|
+
});
|
|
191
|
+
|
|
192
|
+
/**
|
|
193
|
+
* Receives message styling and returns style property values for use with in-app message
|
|
194
|
+
* UI components. Handles resolvement style precedence between default, payload, and custom style
|
|
195
|
+
*
|
|
196
|
+
* Style param resolve precedence from lowest to highest:
|
|
197
|
+
* 1. defaultStyle
|
|
198
|
+
* 2. messageStyle
|
|
199
|
+
* 3. overrideStyle
|
|
200
|
+
*
|
|
201
|
+
* @param {MessageStyleParams} params - message style params, layout, and device orientation
|
|
202
|
+
* @returns {MessageStyles} message style props
|
|
203
|
+
*/
|
|
204
|
+
|
|
205
|
+
export function getMessageStyles({
|
|
206
|
+
styleParams,
|
|
207
|
+
layout,
|
|
208
|
+
}: MessageStyleParams): MessageComponentStyles {
|
|
209
|
+
// view style applied to the wrapper and primary container views
|
|
210
|
+
const { wrapper, container } = getContainerAndWrapperStyle({
|
|
211
|
+
styleParams,
|
|
212
|
+
layout,
|
|
213
|
+
});
|
|
214
|
+
|
|
215
|
+
// primary and secondary button container and text style
|
|
216
|
+
const primaryButton = getComponentButtonStyle({
|
|
217
|
+
styleParams,
|
|
218
|
+
buttonType: 'primaryButton',
|
|
219
|
+
});
|
|
220
|
+
const secondaryButton = getComponentButtonStyle({
|
|
221
|
+
styleParams,
|
|
222
|
+
buttonType: 'secondaryButton',
|
|
223
|
+
});
|
|
224
|
+
|
|
225
|
+
const { defaultStyle, payloadStyle, overrideStyle } = styleParams;
|
|
226
|
+
|
|
227
|
+
// image style composed of default and override style
|
|
228
|
+
const image = [defaultStyle?.image, overrideStyle?.image];
|
|
229
|
+
|
|
230
|
+
const iconButton = {
|
|
231
|
+
// view style applied to icon button
|
|
232
|
+
container: [defaultStyle?.iconButton, overrideStyle?.closeIconButton],
|
|
233
|
+
// close icon color, only specified as an overrideStyle
|
|
234
|
+
iconColor: overrideStyle?.closeIconColor,
|
|
235
|
+
};
|
|
236
|
+
|
|
237
|
+
// text style applied to message body and header respectively
|
|
238
|
+
const body = [defaultStyle?.body, payloadStyle?.body, overrideStyle?.body];
|
|
239
|
+
const header = [
|
|
240
|
+
defaultStyle?.header,
|
|
241
|
+
payloadStyle?.header,
|
|
242
|
+
overrideStyle?.header,
|
|
243
|
+
];
|
|
244
|
+
|
|
245
|
+
const { buttonsContainer, contentContainer, imageContainer, textContainer } =
|
|
246
|
+
defaultStyle ?? {};
|
|
247
|
+
|
|
248
|
+
const styleProps: MessageComponentStyles = {
|
|
249
|
+
body,
|
|
250
|
+
buttonsContainer,
|
|
251
|
+
wrapper,
|
|
252
|
+
contentContainer,
|
|
253
|
+
container,
|
|
254
|
+
header,
|
|
255
|
+
iconButton,
|
|
256
|
+
image,
|
|
257
|
+
imageContainer,
|
|
258
|
+
primaryButton,
|
|
259
|
+
secondaryButton,
|
|
260
|
+
textContainer,
|
|
261
|
+
};
|
|
262
|
+
|
|
263
|
+
if (layout === 'CAROUSEL') {
|
|
264
|
+
styleProps.container = [
|
|
265
|
+
styleProps.container,
|
|
266
|
+
// Add bottom padding for carousel page indicators
|
|
267
|
+
{
|
|
268
|
+
paddingBottom: SPACING_EXTRA_LARGE + DEFAULT_CAROUSEL_INDICATOR_PADDING,
|
|
269
|
+
},
|
|
270
|
+
];
|
|
271
|
+
}
|
|
272
|
+
|
|
273
|
+
return styleProps;
|
|
274
|
+
}
|
|
@@ -0,0 +1,14 @@
|
|
|
1
|
+
export {
|
|
2
|
+
InAppMessagingProvider,
|
|
3
|
+
useInAppMessaging,
|
|
4
|
+
} from '@aws-amplify/ui-react-core';
|
|
5
|
+
|
|
6
|
+
export {
|
|
7
|
+
BannerMessageProps,
|
|
8
|
+
CarouselMessageProps,
|
|
9
|
+
FullScreenMessageProps,
|
|
10
|
+
ModalMessageProps,
|
|
11
|
+
InAppMessageDisplay,
|
|
12
|
+
MessageComponents,
|
|
13
|
+
withInAppMessaging,
|
|
14
|
+
} from './components';
|
|
@@ -0,0 +1,15 @@
|
|
|
1
|
+
// Jest Snapshot v1, https://goo.gl/fbAQLP
|
|
2
|
+
|
|
3
|
+
exports[`@aws-amplify/ui-react-native exports should match snapshot 1`] = `
|
|
4
|
+
Array [
|
|
5
|
+
"BannerMessageProps",
|
|
6
|
+
"CarouselMessageProps",
|
|
7
|
+
"FullScreenMessageProps",
|
|
8
|
+
"InAppMessageDisplay",
|
|
9
|
+
"InAppMessagingProvider",
|
|
10
|
+
"MessageComponents",
|
|
11
|
+
"ModalMessageProps",
|
|
12
|
+
"useInAppMessaging",
|
|
13
|
+
"withInAppMessaging",
|
|
14
|
+
]
|
|
15
|
+
`;
|
|
Binary file
|
|
@@ -0,0 +1,87 @@
|
|
|
1
|
+
import { Dimensions, EventSubscription, ScaledSize } from 'react-native';
|
|
2
|
+
import { renderHook } from '@testing-library/react-hooks';
|
|
3
|
+
import useDeviceOrientation from '../useDeviceOrientation';
|
|
4
|
+
|
|
5
|
+
const dimensions = {
|
|
6
|
+
landscape: { height: 100, width: 300 },
|
|
7
|
+
portrait: { height: 300, width: 100 },
|
|
8
|
+
};
|
|
9
|
+
|
|
10
|
+
describe('useDeviceOrientation', () => {
|
|
11
|
+
const subscription: Pick<EventSubscription, 'remove'> = { remove: jest.fn() };
|
|
12
|
+
|
|
13
|
+
let getSpy: jest.SpyInstance;
|
|
14
|
+
let addEventListenerSpy: jest.SpyInstance;
|
|
15
|
+
let removeEventListener: jest.SpyInstance;
|
|
16
|
+
|
|
17
|
+
beforeEach(() => {
|
|
18
|
+
jest.resetAllMocks();
|
|
19
|
+
|
|
20
|
+
getSpy = jest.spyOn(Dimensions, 'get');
|
|
21
|
+
|
|
22
|
+
addEventListenerSpy = jest.spyOn(Dimensions, 'addEventListener');
|
|
23
|
+
|
|
24
|
+
removeEventListener = jest.spyOn(Dimensions, 'removeEventListener');
|
|
25
|
+
});
|
|
26
|
+
|
|
27
|
+
/* eslint-disable no-console */
|
|
28
|
+
// turn off console errors during tests, can be safely removed once React Native v0.64 is no longer supported
|
|
29
|
+
const consoleWarn = console.warn;
|
|
30
|
+
console.warn = jest.fn();
|
|
31
|
+
afterAll(() => {
|
|
32
|
+
console.warn = consoleWarn;
|
|
33
|
+
/* eslint-enable no-console */
|
|
34
|
+
});
|
|
35
|
+
|
|
36
|
+
it('should handle unsubscribing for React Native versions < 0.65', () => {
|
|
37
|
+
getSpy.mockImplementation((_: string) => dimensions['portrait']);
|
|
38
|
+
|
|
39
|
+
// mock an `undefined` return to simulate React Native versions < 0.65
|
|
40
|
+
addEventListenerSpy.mockReturnValueOnce(undefined);
|
|
41
|
+
|
|
42
|
+
const { unmount } = renderHook(() => useDeviceOrientation());
|
|
43
|
+
|
|
44
|
+
expect(getSpy).toHaveBeenCalledTimes(1);
|
|
45
|
+
expect(getSpy).toHaveBeenCalledWith('screen');
|
|
46
|
+
expect(addEventListenerSpy).toHaveBeenCalledTimes(1);
|
|
47
|
+
|
|
48
|
+
unmount();
|
|
49
|
+
|
|
50
|
+
expect(removeEventListener).toHaveBeenCalledTimes(1);
|
|
51
|
+
expect(subscription.remove).not.toHaveBeenCalled();
|
|
52
|
+
});
|
|
53
|
+
|
|
54
|
+
it('should handle unsubscribing for React Native versions >= 0.65', () => {
|
|
55
|
+
getSpy.mockImplementation((_: string) => dimensions['landscape']);
|
|
56
|
+
addEventListenerSpy.mockReturnValue(subscription);
|
|
57
|
+
|
|
58
|
+
const { unmount } = renderHook(() => useDeviceOrientation());
|
|
59
|
+
|
|
60
|
+
expect(getSpy).toHaveBeenCalledTimes(1);
|
|
61
|
+
expect(getSpy).toHaveBeenCalledWith('screen');
|
|
62
|
+
expect(addEventListenerSpy).toHaveBeenCalledTimes(1);
|
|
63
|
+
|
|
64
|
+
unmount();
|
|
65
|
+
|
|
66
|
+
expect(subscription.remove).toHaveBeenCalledTimes(1);
|
|
67
|
+
expect(removeEventListener).not.toHaveBeenCalled();
|
|
68
|
+
});
|
|
69
|
+
|
|
70
|
+
it.each([
|
|
71
|
+
['landscape', true, false],
|
|
72
|
+
['portrait', false, true],
|
|
73
|
+
])(
|
|
74
|
+
'returns the expected values when the device is in %s mode',
|
|
75
|
+
(deviceOrientation, isLandscapeMode, isPortraitMode) => {
|
|
76
|
+
getSpy.mockImplementation(
|
|
77
|
+
(_: string) => dimensions[deviceOrientation] as ScaledSize
|
|
78
|
+
);
|
|
79
|
+
|
|
80
|
+
const { result } = renderHook(() => useDeviceOrientation());
|
|
81
|
+
|
|
82
|
+
expect(result.current.deviceOrientation).toBe(deviceOrientation);
|
|
83
|
+
expect(result.current.isLandscapeMode).toBe(isLandscapeMode);
|
|
84
|
+
expect(result.current.isPortraitMode).toBe(isPortraitMode);
|
|
85
|
+
}
|
|
86
|
+
);
|
|
87
|
+
});
|
|
@@ -0,0 +1,47 @@
|
|
|
1
|
+
import { useEffect, useState } from 'react';
|
|
2
|
+
import { Dimensions, EventSubscription } from 'react-native';
|
|
3
|
+
|
|
4
|
+
export type DeviceOrientation = 'portrait' | 'landscape';
|
|
5
|
+
const getDeviceOrientation = (): DeviceOrientation => {
|
|
6
|
+
const { height, width } = Dimensions.get('screen');
|
|
7
|
+
return height >= width ? 'portrait' : 'landscape';
|
|
8
|
+
};
|
|
9
|
+
|
|
10
|
+
export default function useDeviceOrientation(): {
|
|
11
|
+
deviceOrientation: DeviceOrientation;
|
|
12
|
+
isLandscapeMode: boolean;
|
|
13
|
+
isPortraitMode: boolean;
|
|
14
|
+
} {
|
|
15
|
+
const [deviceOrientation, setDeviceOrientation] =
|
|
16
|
+
useState<DeviceOrientation>(getDeviceOrientation);
|
|
17
|
+
const isLandscapeMode = deviceOrientation === 'landscape';
|
|
18
|
+
const isPortraitMode = deviceOrientation === 'portrait';
|
|
19
|
+
|
|
20
|
+
useEffect(() => {
|
|
21
|
+
const handler = () => {
|
|
22
|
+
setDeviceOrientation(getDeviceOrientation);
|
|
23
|
+
};
|
|
24
|
+
|
|
25
|
+
// The below cast and conditional unsubscribe handling is due to subscription removal variation
|
|
26
|
+
// between `Dimensions.addEventListener` in React Native prior to and after v0.65.
|
|
27
|
+
//
|
|
28
|
+
// Beginning with v0.65, `Dimensions.addEventListener` returns an `EventSubscription` object,
|
|
29
|
+
// which includes a `remove` method for removing the subscription. Prior versions return
|
|
30
|
+
// `undefined`, and subscription removal is handled by `Dimensions.removeEventListener`,
|
|
31
|
+
// which is deprecated in v0.65
|
|
32
|
+
const subscription = Dimensions.addEventListener(
|
|
33
|
+
'change',
|
|
34
|
+
handler
|
|
35
|
+
) as unknown as EventSubscription;
|
|
36
|
+
|
|
37
|
+
return () => {
|
|
38
|
+
if (typeof subscription?.remove === 'function') {
|
|
39
|
+
subscription.remove();
|
|
40
|
+
} else {
|
|
41
|
+
Dimensions.removeEventListener('change', handler);
|
|
42
|
+
}
|
|
43
|
+
};
|
|
44
|
+
}, []);
|
|
45
|
+
|
|
46
|
+
return { deviceOrientation, isLandscapeMode, isPortraitMode };
|
|
47
|
+
}
|
package/src/index.ts
ADDED
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export * from './InAppMessaging';
|
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
import React from 'react';
|
|
2
|
+
import { Pressable, Text } from 'react-native';
|
|
3
|
+
|
|
4
|
+
import { styles } from './styles';
|
|
5
|
+
import { ButtonProps } from './types';
|
|
6
|
+
|
|
7
|
+
export default function Button({
|
|
8
|
+
children,
|
|
9
|
+
textStyle,
|
|
10
|
+
...pressableProps
|
|
11
|
+
}: ButtonProps): JSX.Element {
|
|
12
|
+
return (
|
|
13
|
+
<Pressable {...pressableProps}>
|
|
14
|
+
{typeof children === 'string' ? (
|
|
15
|
+
<Text style={[styles.text, textStyle]}>{children}</Text>
|
|
16
|
+
) : (
|
|
17
|
+
children
|
|
18
|
+
)}
|
|
19
|
+
</Pressable>
|
|
20
|
+
);
|
|
21
|
+
}
|
|
@@ -0,0 +1,24 @@
|
|
|
1
|
+
import React from 'react';
|
|
2
|
+
import { Text } from 'react-native';
|
|
3
|
+
import TestRenderer from 'react-test-renderer';
|
|
4
|
+
|
|
5
|
+
import Button from '../Button';
|
|
6
|
+
|
|
7
|
+
const title = 'A preesable button';
|
|
8
|
+
const Title = () => <Text>{title}</Text>;
|
|
9
|
+
|
|
10
|
+
describe('Button', () => {
|
|
11
|
+
it('renders as expected with a string passed as children', () => {
|
|
12
|
+
const button = TestRenderer.create(<Button>{title}</Button>);
|
|
13
|
+
expect(button.toJSON()).toMatchSnapshot();
|
|
14
|
+
});
|
|
15
|
+
|
|
16
|
+
it('renders as expected with a component passed as children', () => {
|
|
17
|
+
const button = TestRenderer.create(
|
|
18
|
+
<Button>
|
|
19
|
+
<Title />
|
|
20
|
+
</Button>
|
|
21
|
+
);
|
|
22
|
+
expect(button.toJSON()).toMatchSnapshot();
|
|
23
|
+
});
|
|
24
|
+
});
|
|
@@ -0,0 +1,52 @@
|
|
|
1
|
+
// Jest Snapshot v1, https://goo.gl/fbAQLP
|
|
2
|
+
|
|
3
|
+
exports[`Button renders as expected with a component passed as children 1`] = `
|
|
4
|
+
<View
|
|
5
|
+
accessible={true}
|
|
6
|
+
collapsable={false}
|
|
7
|
+
focusable={true}
|
|
8
|
+
onBlur={[Function]}
|
|
9
|
+
onClick={[Function]}
|
|
10
|
+
onFocus={[Function]}
|
|
11
|
+
onResponderGrant={[Function]}
|
|
12
|
+
onResponderMove={[Function]}
|
|
13
|
+
onResponderRelease={[Function]}
|
|
14
|
+
onResponderTerminate={[Function]}
|
|
15
|
+
onResponderTerminationRequest={[Function]}
|
|
16
|
+
onStartShouldSetResponder={[Function]}
|
|
17
|
+
>
|
|
18
|
+
<Text>
|
|
19
|
+
A preesable button
|
|
20
|
+
</Text>
|
|
21
|
+
</View>
|
|
22
|
+
`;
|
|
23
|
+
|
|
24
|
+
exports[`Button renders as expected with a string passed as children 1`] = `
|
|
25
|
+
<View
|
|
26
|
+
accessible={true}
|
|
27
|
+
collapsable={false}
|
|
28
|
+
focusable={true}
|
|
29
|
+
onBlur={[Function]}
|
|
30
|
+
onClick={[Function]}
|
|
31
|
+
onFocus={[Function]}
|
|
32
|
+
onResponderGrant={[Function]}
|
|
33
|
+
onResponderMove={[Function]}
|
|
34
|
+
onResponderRelease={[Function]}
|
|
35
|
+
onResponderTerminate={[Function]}
|
|
36
|
+
onResponderTerminationRequest={[Function]}
|
|
37
|
+
onStartShouldSetResponder={[Function]}
|
|
38
|
+
>
|
|
39
|
+
<Text
|
|
40
|
+
style={
|
|
41
|
+
Array [
|
|
42
|
+
Object {
|
|
43
|
+
"alignSelf": "center",
|
|
44
|
+
},
|
|
45
|
+
undefined,
|
|
46
|
+
]
|
|
47
|
+
}
|
|
48
|
+
>
|
|
49
|
+
A preesable button
|
|
50
|
+
</Text>
|
|
51
|
+
</View>
|
|
52
|
+
`;
|