@planningcenter/chat-react-native 3.46.0-rc.0 → 4.0.0-rc.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/build/components/conversation/attachments/video_attachment.d.ts.map +1 -1
- package/build/components/conversation/attachments/video_attachment.js +1 -1
- package/build/components/conversation/attachments/video_attachment.js.map +1 -1
- package/build/components/display/index.d.ts +1 -0
- package/build/components/display/index.d.ts.map +1 -1
- package/build/components/display/index.js +1 -0
- package/build/components/display/index.js.map +1 -1
- package/build/components/display/keyboard_scroll_view.d.ts +5 -0
- package/build/components/display/keyboard_scroll_view.d.ts.map +1 -0
- package/build/components/display/keyboard_scroll_view.js +37 -0
- package/build/components/display/keyboard_scroll_view.js.map +1 -0
- package/build/screens/bug_report_screen.d.ts.map +1 -1
- package/build/screens/bug_report_screen.js +5 -5
- package/build/screens/bug_report_screen.js.map +1 -1
- package/build/screens/message_report_screen.js +3 -3
- package/build/screens/message_report_screen.js.map +1 -1
- package/build/utils/native_adapters/video.d.ts +1 -4
- package/build/utils/native_adapters/video.d.ts.map +1 -1
- package/build/utils/native_adapters/video.js.map +1 -1
- package/package.json +2 -2
- package/src/__tests__/components/conversation/attachments/video_attachment.test.tsx +8 -11
- package/src/components/conversation/attachments/video_attachment.tsx +1 -2
- package/src/components/display/index.ts +1 -0
- package/src/components/display/keyboard_scroll_view.tsx +54 -0
- package/src/screens/bug_report_screen.tsx +143 -149
- package/src/screens/message_report_screen.tsx +38 -40
- package/src/types/react-native-scroll-view.d.ts +7 -0
- package/src/utils/native_adapters/video.ts +1 -4
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"video_attachment.d.ts","sourceRoot":"","sources":["../../../../src/components/conversation/attachments/video_attachment.tsx"],"names":[],"mappings":"AAIA,OAAO,EAAE,qCAAqC,EAAE,MAAM,2DAA2D,CAAA;AAOjH,wBAAgB,eAAe,CAAC,EAC9B,UAAU,EACV,4BAA4B,EAC5B,UAAU,GACX,EAAE;IACD,UAAU,EAAE,qCAAqC,CAAA;IACjD,4BAA4B,EAAE,CAAC,UAAU,EAAE,qCAAqC,KAAK,IAAI,CAAA;IACzF,UAAU,EAAE,OAAO,CAAA;CACpB,
|
|
1
|
+
{"version":3,"file":"video_attachment.d.ts","sourceRoot":"","sources":["../../../../src/components/conversation/attachments/video_attachment.tsx"],"names":[],"mappings":"AAIA,OAAO,EAAE,qCAAqC,EAAE,MAAM,2DAA2D,CAAA;AAOjH,wBAAgB,eAAe,CAAC,EAC9B,UAAU,EACV,4BAA4B,EAC5B,UAAU,GACX,EAAE;IACD,UAAU,EAAE,qCAAqC,CAAA;IACjD,4BAA4B,EAAE,CAAC,UAAU,EAAE,qCAAqC,KAAK,IAAI,CAAA;IACzF,UAAU,EAAE,OAAO,CAAA;CACpB,2CA4DA"}
|
|
@@ -28,7 +28,7 @@ export function VideoAttachment({ attachment, onMessageAttachmentLongPress, isDe
|
|
|
28
28
|
setIsOpen(false);
|
|
29
29
|
}
|
|
30
30
|
const viewRef = useRef(null);
|
|
31
|
-
return (_jsx(View, { style: styles.container, ref: viewRef, children: _jsxs(PlatformPressable, { onPress: openVideo, onLongPress: () => !isDeleting && onMessageAttachmentLongPress(attachment), android_ripple: { color: colors.androidRippleNeutral, foreground: true }, accessibilityLabel: "Play Video", accessibilityHint: "Press to play video. Long press for more options", disabled: isDeleting, children: [_jsx(View, { style: styles.thumbnailOverlay }), _jsx(Video.Player, { ref: videoRef, source: { uri: url }, aspectRatio: width / height, style: styles.video,
|
|
31
|
+
return (_jsx(View, { style: styles.container, ref: viewRef, children: _jsxs(PlatformPressable, { onPress: openVideo, onLongPress: () => !isDeleting && onMessageAttachmentLongPress(attachment), android_ripple: { color: colors.androidRippleNeutral, foreground: true }, accessibilityLabel: "Play Video", accessibilityHint: "Press to play video. Long press for more options", disabled: isDeleting, children: [_jsx(View, { style: styles.thumbnailOverlay }), _jsx(Video.Player, { ref: videoRef, source: { uri: url }, aspectRatio: width / height, style: styles.video, onFullscreenDismiss: closeVideo }), !isOpen && !isDeleting && (_jsx(View, { style: styles.playContainer, children: _jsx(View, { style: styles.playCircle, children: _jsx(Icon, { name: "services.play", style: styles.playIcon, accessibilityElementsHidden: true }) }) })), isDeleting && _jsx(AttachmentDeletingOverlay, {})] }) }));
|
|
32
32
|
}
|
|
33
33
|
const OVERLAY_Z_INDEX = 1;
|
|
34
34
|
const useStyles = () => {
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"video_attachment.js","sourceRoot":"","sources":["../../../../src/components/conversation/attachments/video_attachment.tsx"],"names":[],"mappings":";AAAA,OAAO,EAAE,iBAAiB,EAAE,MAAM,4BAA4B,CAAA;AAC9D,OAAc,EAAE,MAAM,EAAE,QAAQ,EAAE,MAAM,OAAO,CAAA;AAC/C,OAAO,EAAE,IAAI,EAAE,UAAU,EAAE,MAAM,cAAc,CAAA;AAC/C,OAAO,EAAE,QAAQ,EAAE,MAAM,gBAAgB,CAAA;AAEzC,OAAO,EAAE,KAAK,EAAqB,MAAM,gCAAgC,CAAA;AACzE,OAAO,EAAE,MAAM,EAAE,MAAM,iCAAiC,CAAA;AACxD,OAAO,EAAE,IAAI,EAAE,MAAM,eAAe,CAAA;AACpC,OAAO,EAAE,yBAAyB,EAAE,MAAM,+BAA+B,CAAA;AACzE,OAAO,EAAE,+BAA+B,EAAE,MAAM,aAAa,CAAA;AAE7D,MAAM,UAAU,eAAe,CAAC,EAC9B,UAAU,EACV,4BAA4B,EAC5B,UAAU,GAKX;IACC,MAAM,EAAE,MAAM,EAAE,GAAG,QAAQ,EAAE,CAAA;IAC7B,MAAM,MAAM,GAAG,SAAS,EAAE,CAAA;IAE1B,MAAM,EAAE,UAAU,EAAE,GAAG,UAAU,CAAA;IACjC,MAAM,EAAE,KAAK,GAAG,+BAA+B,EAAE,MAAM,GAAG,+BAA+B,EAAE,GACzF,UAAU,CAAC,QAAQ,IAAI,EAAE,CAAA;IAC3B,MAAM,EAAE,GAAG,EAAE,GAAG,UAAU,CAAA;IAE1B,MAAM,QAAQ,GAAG,MAAM,CAAoB,IAAI,CAAC,CAAA;IAChD,MAAM,CAAC,MAAM,EAAE,SAAS,CAAC,GAAG,QAAQ,CAAC,KAAK,CAAC,CAAA;IAE3C,SAAS,SAAS;QAChB,IAAI,CAAC,MAAM,IAAI,QAAQ,CAAC,OAAO,EAAE,CAAC;YAChC,QAAQ,CAAC,OAAO,CAAC,uBAAuB,EAAE,CAAA;YAC1C,QAAQ,CAAC,OAAO,CAAC,IAAI,EAAE,CAAA;YACvB,SAAS,CAAC,IAAI,CAAC,CAAA;QACjB,CAAC;IACH,CAAC;IAED,SAAS,UAAU;QACjB,QAAQ,CAAC,OAAO,EAAE,KAAK,EAAE,CAAA;QACzB,SAAS,CAAC,KAAK,CAAC,CAAA;IAClB,CAAC;IAED,MAAM,OAAO,GAAG,MAAM,CAAO,IAAI,CAAC,CAAA;IAElC,OAAO,CACL,KAAC,IAAI,IAAC,KAAK,EAAE,MAAM,CAAC,SAAS,EAAE,GAAG,EAAE,OAAO,YACzC,MAAC,iBAAiB,IAChB,OAAO,EAAE,SAAS,EAClB,WAAW,EAAE,GAAG,EAAE,CAAC,CAAC,UAAU,IAAI,4BAA4B,CAAC,UAAU,CAAC,EAC1E,cAAc,EAAE,EAAE,KAAK,EAAE,MAAM,CAAC,oBAAoB,EAAE,UAAU,EAAE,IAAI,EAAE,EACxE,kBAAkB,EAAC,YAAY,EAC/B,iBAAiB,EAAC,kDAAkD,EACpE,QAAQ,EAAE,UAAU,aAEpB,KAAC,IAAI,IAAC,KAAK,EAAE,MAAM,CAAC,gBAAgB,GAAI,EACxC,KAAC,KAAK,CAAC,MAAM,IACX,GAAG,EAAE,QAAQ,EACb,MAAM,EAAE,EAAE,GAAG,EAAE,GAAG,EAAE,EACpB,WAAW,EAAE,KAAK,GAAG,MAAM,EAC3B,KAAK,EAAE,MAAM,CAAC,KAAK,EACnB,
|
|
1
|
+
{"version":3,"file":"video_attachment.js","sourceRoot":"","sources":["../../../../src/components/conversation/attachments/video_attachment.tsx"],"names":[],"mappings":"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","sourcesContent":["import { PlatformPressable } from '@react-navigation/elements'\nimport React, { useRef, useState } from 'react'\nimport { View, StyleSheet } from 'react-native'\nimport { useTheme } from '../../../hooks'\nimport { DenormalizedMessageAttachmentResource } from '../../../types/resources/denormalized_attachment_resource'\nimport { Video, VideoPlayerHandle } from '../../../utils/native_adapters'\nimport { tokens } from '../../../vendor/tapestry/tokens'\nimport { Icon } from '../../display'\nimport { AttachmentDeletingOverlay } from './attachment_deleting_overlay'\nimport { MESSAGE_ATTACHMENT_WIDTH_SINGLE } from './constants'\n\nexport function VideoAttachment({\n attachment,\n onMessageAttachmentLongPress,\n isDeleting,\n}: {\n attachment: DenormalizedMessageAttachmentResource\n onMessageAttachmentLongPress: (attachment: DenormalizedMessageAttachmentResource) => void\n isDeleting: boolean\n}) {\n const { colors } = useTheme()\n const styles = useStyles()\n\n const { attributes } = attachment\n const { width = MESSAGE_ATTACHMENT_WIDTH_SINGLE, height = MESSAGE_ATTACHMENT_WIDTH_SINGLE } =\n attributes.metadata || {}\n const { url } = attributes\n\n const videoRef = useRef<VideoPlayerHandle>(null)\n const [isOpen, setIsOpen] = useState(false)\n\n function openVideo() {\n if (!isOpen && videoRef.current) {\n videoRef.current.presentFullscreenPlayer()\n videoRef.current.play()\n setIsOpen(true)\n }\n }\n\n function closeVideo() {\n videoRef.current?.pause()\n setIsOpen(false)\n }\n\n const viewRef = useRef<View>(null)\n\n return (\n <View style={styles.container} ref={viewRef}>\n <PlatformPressable\n onPress={openVideo}\n onLongPress={() => !isDeleting && onMessageAttachmentLongPress(attachment)}\n android_ripple={{ color: colors.androidRippleNeutral, foreground: true }}\n accessibilityLabel=\"Play Video\"\n accessibilityHint=\"Press to play video. Long press for more options\"\n disabled={isDeleting}\n >\n <View style={styles.thumbnailOverlay} />\n <Video.Player\n ref={videoRef}\n source={{ uri: url }}\n aspectRatio={width / height}\n style={styles.video}\n onFullscreenDismiss={closeVideo}\n />\n {!isOpen && !isDeleting && (\n <View style={styles.playContainer}>\n <View style={styles.playCircle}>\n <Icon\n name=\"services.play\"\n style={styles.playIcon}\n accessibilityElementsHidden={true}\n />\n </View>\n </View>\n )}\n {isDeleting && <AttachmentDeletingOverlay />}\n </PlatformPressable>\n </View>\n )\n}\nconst OVERLAY_Z_INDEX = 1\n\nconst useStyles = () => {\n const { colors } = useTheme()\n const overlayBackgroundColor =\n colors.name === 'light'\n ? tokens.fillColorTransparencyDark010\n : tokens.fillColorTransparencyDark030\n\n return StyleSheet.create({\n container: {\n borderRadius: 8,\n overflow: 'hidden',\n },\n video: {\n width: '100%',\n backgroundColor: colors.fillColorNeutral070,\n },\n thumbnailOverlay: {\n position: 'absolute',\n top: 0,\n left: 0,\n right: 0,\n bottom: 0,\n backgroundColor: overlayBackgroundColor,\n zIndex: OVERLAY_Z_INDEX,\n },\n playContainer: {\n position: 'absolute',\n top: 0,\n left: 0,\n right: 0,\n bottom: 0,\n justifyContent: 'center',\n alignItems: 'center',\n zIndex: OVERLAY_Z_INDEX + 1,\n },\n playCircle: {\n justifyContent: 'center',\n alignItems: 'center',\n width: 42,\n height: 42,\n borderRadius: 25,\n backgroundColor: colors.fillColorNeutral100Inverted,\n borderColor: colors.borderColorDefaultBase,\n borderWidth: 1,\n },\n playIcon: {\n fontSize: 20,\n },\n })\n}\n"]}
|
|
@@ -23,6 +23,7 @@ export * from './text_button';
|
|
|
23
23
|
export * from './text_inline_button';
|
|
24
24
|
export * from './text';
|
|
25
25
|
export * from './toggle_button';
|
|
26
|
+
export * from './keyboard_scroll_view';
|
|
26
27
|
export * from './keyboard_view';
|
|
27
28
|
export * from './platform_modal_header_buttons';
|
|
28
29
|
export * from './pressable_row';
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../../src/components/display/index.ts"],"names":[],"mappings":"AAAA,cAAc,gBAAgB,CAAA;AAC9B,cAAc,UAAU,CAAA;AACxB,cAAc,SAAS,CAAA;AACvB,cAAc,uBAAuB,CAAA;AACrC,cAAc,gBAAgB,CAAA;AAC9B,cAAc,eAAe,CAAA;AAC7B,cAAc,sBAAsB,CAAA;AACpC,cAAc,UAAU,CAAA;AACxB,cAAc,UAAU,CAAA;AACxB,cAAc,4BAA4B,CAAA;AAC1C,cAAc,gBAAgB,CAAA;AAC9B,cAAc,WAAW,CAAA;AACzB,cAAc,eAAe,CAAA;AAC7B,cAAc,QAAQ,CAAA;AACtB,cAAc,SAAS,CAAA;AACvB,cAAc,2BAA2B,CAAA;AACzC,cAAc,4BAA4B,CAAA;AAC1C,cAAc,4BAA4B,CAAA;AAC1C,cAAc,UAAU,CAAA;AACxB,cAAc,WAAW,CAAA;AACzB,cAAc,UAAU,CAAA;AACxB,cAAc,eAAe,CAAA;AAC7B,cAAc,sBAAsB,CAAA;AACpC,cAAc,QAAQ,CAAA;AACtB,cAAc,iBAAiB,CAAA;AAC/B,cAAc,iBAAiB,CAAA;AAC/B,cAAc,iCAAiC,CAAA;AAC/C,cAAc,iBAAiB,CAAA"}
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../../src/components/display/index.ts"],"names":[],"mappings":"AAAA,cAAc,gBAAgB,CAAA;AAC9B,cAAc,UAAU,CAAA;AACxB,cAAc,SAAS,CAAA;AACvB,cAAc,uBAAuB,CAAA;AACrC,cAAc,gBAAgB,CAAA;AAC9B,cAAc,eAAe,CAAA;AAC7B,cAAc,sBAAsB,CAAA;AACpC,cAAc,UAAU,CAAA;AACxB,cAAc,UAAU,CAAA;AACxB,cAAc,4BAA4B,CAAA;AAC1C,cAAc,gBAAgB,CAAA;AAC9B,cAAc,WAAW,CAAA;AACzB,cAAc,eAAe,CAAA;AAC7B,cAAc,QAAQ,CAAA;AACtB,cAAc,SAAS,CAAA;AACvB,cAAc,2BAA2B,CAAA;AACzC,cAAc,4BAA4B,CAAA;AAC1C,cAAc,4BAA4B,CAAA;AAC1C,cAAc,UAAU,CAAA;AACxB,cAAc,WAAW,CAAA;AACzB,cAAc,UAAU,CAAA;AACxB,cAAc,eAAe,CAAA;AAC7B,cAAc,sBAAsB,CAAA;AACpC,cAAc,QAAQ,CAAA;AACtB,cAAc,iBAAiB,CAAA;AAC/B,cAAc,wBAAwB,CAAA;AACtC,cAAc,iBAAiB,CAAA;AAC/B,cAAc,iCAAiC,CAAA;AAC/C,cAAc,iBAAiB,CAAA"}
|
|
@@ -23,6 +23,7 @@ export * from './text_button';
|
|
|
23
23
|
export * from './text_inline_button';
|
|
24
24
|
export * from './text';
|
|
25
25
|
export * from './toggle_button';
|
|
26
|
+
export * from './keyboard_scroll_view';
|
|
26
27
|
export * from './keyboard_view';
|
|
27
28
|
export * from './platform_modal_header_buttons';
|
|
28
29
|
export * from './pressable_row';
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.js","sourceRoot":"","sources":["../../../src/components/display/index.ts"],"names":[],"mappings":"AAAA,cAAc,gBAAgB,CAAA;AAC9B,cAAc,UAAU,CAAA;AACxB,cAAc,SAAS,CAAA;AACvB,cAAc,uBAAuB,CAAA;AACrC,cAAc,gBAAgB,CAAA;AAC9B,cAAc,eAAe,CAAA;AAC7B,cAAc,sBAAsB,CAAA;AACpC,cAAc,UAAU,CAAA;AACxB,cAAc,UAAU,CAAA;AACxB,cAAc,4BAA4B,CAAA;AAC1C,cAAc,gBAAgB,CAAA;AAC9B,cAAc,WAAW,CAAA;AACzB,cAAc,eAAe,CAAA;AAC7B,cAAc,QAAQ,CAAA;AACtB,cAAc,SAAS,CAAA;AACvB,cAAc,2BAA2B,CAAA;AACzC,cAAc,4BAA4B,CAAA;AAC1C,cAAc,4BAA4B,CAAA;AAC1C,cAAc,UAAU,CAAA;AACxB,cAAc,WAAW,CAAA;AACzB,cAAc,UAAU,CAAA;AACxB,cAAc,eAAe,CAAA;AAC7B,cAAc,sBAAsB,CAAA;AACpC,cAAc,QAAQ,CAAA;AACtB,cAAc,iBAAiB,CAAA;AAC/B,cAAc,iBAAiB,CAAA;AAC/B,cAAc,iCAAiC,CAAA;AAC/C,cAAc,iBAAiB,CAAA","sourcesContent":["export * from './avatar_group'\nexport * from './avatar'\nexport * from './badge'\nexport * from './conversation_avatar'\nexport * from './emoji_avatar'\nexport * from './icon_avatar'\nexport * from './banner_collapsible'\nexport * from './banner'\nexport * from './button'\nexport * from './adult_requirement_notice'\nexport * from './child_notice'\nexport * from './heading'\nexport * from './icon_button'\nexport * from './icon'\nexport * from './image'\nexport * from './file_attachment_preview'\nexport * from './image_attachment_preview'\nexport * from './video_attachment_preview'\nexport * from './person'\nexport * from './spinner'\nexport * from './switch'\nexport * from './text_button'\nexport * from './text_inline_button'\nexport * from './text'\nexport * from './toggle_button'\nexport * from './keyboard_view'\nexport * from './platform_modal_header_buttons'\nexport * from './pressable_row'\n"]}
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../../../src/components/display/index.ts"],"names":[],"mappings":"AAAA,cAAc,gBAAgB,CAAA;AAC9B,cAAc,UAAU,CAAA;AACxB,cAAc,SAAS,CAAA;AACvB,cAAc,uBAAuB,CAAA;AACrC,cAAc,gBAAgB,CAAA;AAC9B,cAAc,eAAe,CAAA;AAC7B,cAAc,sBAAsB,CAAA;AACpC,cAAc,UAAU,CAAA;AACxB,cAAc,UAAU,CAAA;AACxB,cAAc,4BAA4B,CAAA;AAC1C,cAAc,gBAAgB,CAAA;AAC9B,cAAc,WAAW,CAAA;AACzB,cAAc,eAAe,CAAA;AAC7B,cAAc,QAAQ,CAAA;AACtB,cAAc,SAAS,CAAA;AACvB,cAAc,2BAA2B,CAAA;AACzC,cAAc,4BAA4B,CAAA;AAC1C,cAAc,4BAA4B,CAAA;AAC1C,cAAc,UAAU,CAAA;AACxB,cAAc,WAAW,CAAA;AACzB,cAAc,UAAU,CAAA;AACxB,cAAc,eAAe,CAAA;AAC7B,cAAc,sBAAsB,CAAA;AACpC,cAAc,QAAQ,CAAA;AACtB,cAAc,iBAAiB,CAAA;AAC/B,cAAc,wBAAwB,CAAA;AACtC,cAAc,iBAAiB,CAAA;AAC/B,cAAc,iCAAiC,CAAA;AAC/C,cAAc,iBAAiB,CAAA","sourcesContent":["export * from './avatar_group'\nexport * from './avatar'\nexport * from './badge'\nexport * from './conversation_avatar'\nexport * from './emoji_avatar'\nexport * from './icon_avatar'\nexport * from './banner_collapsible'\nexport * from './banner'\nexport * from './button'\nexport * from './adult_requirement_notice'\nexport * from './child_notice'\nexport * from './heading'\nexport * from './icon_button'\nexport * from './icon'\nexport * from './image'\nexport * from './file_attachment_preview'\nexport * from './image_attachment_preview'\nexport * from './video_attachment_preview'\nexport * from './person'\nexport * from './spinner'\nexport * from './switch'\nexport * from './text_button'\nexport * from './text_inline_button'\nexport * from './text'\nexport * from './toggle_button'\nexport * from './keyboard_scroll_view'\nexport * from './keyboard_view'\nexport * from './platform_modal_header_buttons'\nexport * from './pressable_row'\n"]}
|
|
@@ -0,0 +1,5 @@
|
|
|
1
|
+
import { ScrollViewProps } from 'react-native';
|
|
2
|
+
type KeyboardScrollViewProps = Pick<ScrollViewProps, 'children' | 'contentContainerStyle'>;
|
|
3
|
+
export declare function KeyboardScrollView({ children, contentContainerStyle }: KeyboardScrollViewProps): import("react/jsx-runtime").JSX.Element;
|
|
4
|
+
export {};
|
|
5
|
+
//# sourceMappingURL=keyboard_scroll_view.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"keyboard_scroll_view.d.ts","sourceRoot":"","sources":["../../../src/components/display/keyboard_scroll_view.tsx"],"names":[],"mappings":"AACA,OAAO,EAAwB,eAAe,EAAa,MAAM,cAAc,CAAA;AAK/E,KAAK,uBAAuB,GAAG,IAAI,CAAC,eAAe,EAAE,UAAU,GAAG,uBAAuB,CAAC,CAAA;AAE1F,wBAAgB,kBAAkB,CAAC,EAAE,QAAQ,EAAE,qBAAqB,EAAE,EAAE,uBAAuB,2CA6C9F"}
|
|
@@ -0,0 +1,37 @@
|
|
|
1
|
+
import { jsx as _jsx } from "react/jsx-runtime";
|
|
2
|
+
import { useCallback, useRef } from 'react';
|
|
3
|
+
import { Keyboard, ScrollView, TextInput } from 'react-native';
|
|
4
|
+
import { KeyboardView } from './keyboard_view';
|
|
5
|
+
const FOCUSED_INPUT_BOTTOM_MARGIN = 32;
|
|
6
|
+
export function KeyboardScrollView({ children, contentContainerStyle }) {
|
|
7
|
+
const scrollViewRef = useRef(null);
|
|
8
|
+
const scrollFocusedInputIntoView = useCallback(() => {
|
|
9
|
+
const scrollView = scrollViewRef.current;
|
|
10
|
+
const input = TextInput.State.currentlyFocusedInput();
|
|
11
|
+
if (!scrollView || !input)
|
|
12
|
+
return;
|
|
13
|
+
const nativeScrollView = scrollView.getNativeScrollRef();
|
|
14
|
+
const innerView = scrollView.getInnerViewRef();
|
|
15
|
+
if (!nativeScrollView || !innerView)
|
|
16
|
+
return;
|
|
17
|
+
nativeScrollView.measureInWindow((_scrollX, scrollTop, _scrollWidth, scrollHeight) => {
|
|
18
|
+
const keyboardTop = Keyboard.metrics()?.screenY;
|
|
19
|
+
const scrollBottom = scrollTop + scrollHeight;
|
|
20
|
+
const visibleBottom = keyboardTop === undefined ? scrollBottom : Math.min(scrollBottom, keyboardTop);
|
|
21
|
+
const visibleHeight = visibleBottom - scrollTop;
|
|
22
|
+
input.measureInWindow((_inputX, inputTop, _inputWidth, inputHeight) => {
|
|
23
|
+
const inputBottom = inputTop + inputHeight + FOCUSED_INPUT_BOTTOM_MARGIN;
|
|
24
|
+
if (inputBottom <= visibleBottom)
|
|
25
|
+
return;
|
|
26
|
+
input.measureLayout(innerView, (_left, contentTop, _contentWidth, contentHeight) => {
|
|
27
|
+
scrollView.scrollTo({
|
|
28
|
+
y: contentTop + contentHeight + FOCUSED_INPUT_BOTTOM_MARGIN - visibleHeight,
|
|
29
|
+
animated: true,
|
|
30
|
+
});
|
|
31
|
+
});
|
|
32
|
+
});
|
|
33
|
+
});
|
|
34
|
+
}, []);
|
|
35
|
+
return (_jsx(KeyboardView, { children: _jsx(ScrollView, { ref: scrollViewRef, contentContainerStyle: contentContainerStyle, onLayout: scrollFocusedInputIntoView, onContentSizeChange: scrollFocusedInputIntoView, children: children }) }));
|
|
36
|
+
}
|
|
37
|
+
//# sourceMappingURL=keyboard_scroll_view.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"keyboard_scroll_view.js","sourceRoot":"","sources":["../../../src/components/display/keyboard_scroll_view.tsx"],"names":[],"mappings":";AAAA,OAAc,EAAE,WAAW,EAAE,MAAM,EAAE,MAAM,OAAO,CAAA;AAClD,OAAO,EAAE,QAAQ,EAAE,UAAU,EAAmB,SAAS,EAAE,MAAM,cAAc,CAAA;AAC/E,OAAO,EAAE,YAAY,EAAE,MAAM,iBAAiB,CAAA;AAE9C,MAAM,2BAA2B,GAAG,EAAE,CAAA;AAItC,MAAM,UAAU,kBAAkB,CAAC,EAAE,QAAQ,EAAE,qBAAqB,EAA2B;IAC7F,MAAM,aAAa,GAAG,MAAM,CAAa,IAAI,CAAC,CAAA;IAE9C,MAAM,0BAA0B,GAAG,WAAW,CAAC,GAAG,EAAE;QAClD,MAAM,UAAU,GAAG,aAAa,CAAC,OAAO,CAAA;QACxC,MAAM,KAAK,GAAG,SAAS,CAAC,KAAK,CAAC,qBAAqB,EAAE,CAAA;QACrD,IAAI,CAAC,UAAU,IAAI,CAAC,KAAK;YAAE,OAAM;QAEjC,MAAM,gBAAgB,GAAG,UAAU,CAAC,kBAAkB,EAAE,CAAA;QACxD,MAAM,SAAS,GAAG,UAAU,CAAC,eAAe,EAAE,CAAA;QAC9C,IAAI,CAAC,gBAAgB,IAAI,CAAC,SAAS;YAAE,OAAM;QAE3C,gBAAgB,CAAC,eAAe,CAAC,CAAC,QAAQ,EAAE,SAAS,EAAE,YAAY,EAAE,YAAY,EAAE,EAAE;YACnF,MAAM,WAAW,GAAG,QAAQ,CAAC,OAAO,EAAE,EAAE,OAAO,CAAA;YAC/C,MAAM,YAAY,GAAG,SAAS,GAAG,YAAY,CAAA;YAC7C,MAAM,aAAa,GACjB,WAAW,KAAK,SAAS,CAAC,CAAC,CAAC,YAAY,CAAC,CAAC,CAAC,IAAI,CAAC,GAAG,CAAC,YAAY,EAAE,WAAW,CAAC,CAAA;YAChF,MAAM,aAAa,GAAG,aAAa,GAAG,SAAS,CAAA;YAE/C,KAAK,CAAC,eAAe,CAAC,CAAC,OAAO,EAAE,QAAQ,EAAE,WAAW,EAAE,WAAW,EAAE,EAAE;gBACpE,MAAM,WAAW,GAAG,QAAQ,GAAG,WAAW,GAAG,2BAA2B,CAAA;gBACxE,IAAI,WAAW,IAAI,aAAa;oBAAE,OAAM;gBAExC,KAAK,CAAC,aAAa,CAAC,SAAS,EAAE,CAAC,KAAK,EAAE,UAAU,EAAE,aAAa,EAAE,aAAa,EAAE,EAAE;oBACjF,UAAU,CAAC,QAAQ,CAAC;wBAClB,CAAC,EAAE,UAAU,GAAG,aAAa,GAAG,2BAA2B,GAAG,aAAa;wBAC3E,QAAQ,EAAE,IAAI;qBACf,CAAC,CAAA;gBACJ,CAAC,CAAC,CAAA;YACJ,CAAC,CAAC,CAAA;QACJ,CAAC,CAAC,CAAA;IACJ,CAAC,EAAE,EAAE,CAAC,CAAA;IAEN,OAAO,CACL,KAAC,YAAY,cACX,KAAC,UAAU,IACT,GAAG,EAAE,aAAa,EAClB,qBAAqB,EAAE,qBAAqB,EAC5C,QAAQ,EAAE,0BAA0B,EACpC,mBAAmB,EAAE,0BAA0B,YAE9C,QAAQ,GACE,GACA,CAChB,CAAA;AACH,CAAC","sourcesContent":["import React, { useCallback, useRef } from 'react'\nimport { Keyboard, ScrollView, ScrollViewProps, TextInput } from 'react-native'\nimport { KeyboardView } from './keyboard_view'\n\nconst FOCUSED_INPUT_BOTTOM_MARGIN = 32\n\ntype KeyboardScrollViewProps = Pick<ScrollViewProps, 'children' | 'contentContainerStyle'>\n\nexport function KeyboardScrollView({ children, contentContainerStyle }: KeyboardScrollViewProps) {\n const scrollViewRef = useRef<ScrollView>(null)\n\n const scrollFocusedInputIntoView = useCallback(() => {\n const scrollView = scrollViewRef.current\n const input = TextInput.State.currentlyFocusedInput()\n if (!scrollView || !input) return\n\n const nativeScrollView = scrollView.getNativeScrollRef()\n const innerView = scrollView.getInnerViewRef()\n if (!nativeScrollView || !innerView) return\n\n nativeScrollView.measureInWindow((_scrollX, scrollTop, _scrollWidth, scrollHeight) => {\n const keyboardTop = Keyboard.metrics()?.screenY\n const scrollBottom = scrollTop + scrollHeight\n const visibleBottom =\n keyboardTop === undefined ? scrollBottom : Math.min(scrollBottom, keyboardTop)\n const visibleHeight = visibleBottom - scrollTop\n\n input.measureInWindow((_inputX, inputTop, _inputWidth, inputHeight) => {\n const inputBottom = inputTop + inputHeight + FOCUSED_INPUT_BOTTOM_MARGIN\n if (inputBottom <= visibleBottom) return\n\n input.measureLayout(innerView, (_left, contentTop, _contentWidth, contentHeight) => {\n scrollView.scrollTo({\n y: contentTop + contentHeight + FOCUSED_INPUT_BOTTOM_MARGIN - visibleHeight,\n animated: true,\n })\n })\n })\n })\n }, [])\n\n return (\n <KeyboardView>\n <ScrollView\n ref={scrollViewRef}\n contentContainerStyle={contentContainerStyle}\n onLayout={scrollFocusedInputIntoView}\n onContentSizeChange={scrollFocusedInputIntoView}\n >\n {children}\n </ScrollView>\n </KeyboardView>\n )\n}\n"]}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"bug_report_screen.d.ts","sourceRoot":"","sources":["../../src/screens/bug_report_screen.tsx"],"names":[],"mappings":"AACA,OAAO,KAAK,EACV,4BAA4B,EAC5B,sBAAsB,EACvB,MAAM,gCAAgC,CAAA;AAqDvC,eAAO,MAAM,sBAAsB,GAAI,iBAEpC,sBAAsB,CAAC,GAAG,CAAC,KAAG,4BAI9B,CAAA;AAoBH,wBAAgB,eAAe,
|
|
1
|
+
{"version":3,"file":"bug_report_screen.d.ts","sourceRoot":"","sources":["../../src/screens/bug_report_screen.tsx"],"names":[],"mappings":"AACA,OAAO,KAAK,EACV,4BAA4B,EAC5B,sBAAsB,EACvB,MAAM,gCAAgC,CAAA;AAqDvC,eAAO,MAAM,sBAAsB,GAAI,iBAEpC,sBAAsB,CAAC,GAAG,CAAC,KAAG,4BAI9B,CAAA;AAoBH,wBAAgB,eAAe,4CAmS9B"}
|
|
@@ -4,7 +4,7 @@ import { startsWith } from 'lodash';
|
|
|
4
4
|
import { useCallback, useState } from 'react';
|
|
5
5
|
import { View, StyleSheet, TextInput, Linking, ScrollView, TouchableOpacity, Platform, } from 'react-native';
|
|
6
6
|
import { useSafeAreaInsets } from 'react-native-safe-area-context';
|
|
7
|
-
import { Button, Spinner, Text, TextInlineButton, ImageAttachmentPreview, Icon,
|
|
7
|
+
import { Button, Spinner, Text, TextInlineButton, ImageAttachmentPreview, Icon, KeyboardScrollView, } from '../components';
|
|
8
8
|
import { composeOptions, HeaderDismissButton, useHeaderRight, withLeftClose, } from '../components/display/platform_modal_header_buttons';
|
|
9
9
|
import { VideoAttachmentPreview } from '../components/display/video_attachment_preview';
|
|
10
10
|
import { DefaultLoading } from '../components/page/loading';
|
|
@@ -126,10 +126,10 @@ export function BugReportScreen() {
|
|
|
126
126
|
if (status === 'error') {
|
|
127
127
|
return (_jsxs(View, { style: styles.container, children: [_jsxs(Text, { children: ["This is embarrassing, we can't submit your bug report right now. If you still need help or would like to submit this bug report another way please", ' ', _jsx(TextInlineButton, { accessibilityRole: "link", onPress: () => Linking.openURL('https://support.planningcenteronline.com/hc/en-us/requests/new'), children: "contact our help center" }), "."] }), _jsx(Button, { title: "Return to chat", onPress: navigation.goBack, variant: "fill", size: "lg" })] }));
|
|
128
128
|
}
|
|
129
|
-
return (
|
|
130
|
-
|
|
131
|
-
|
|
132
|
-
|
|
129
|
+
return (_jsxs(KeyboardScrollView, { contentContainerStyle: styles.container, children: [_jsxs(Text, { style: styles.description, children: ["Thanks for helping us improve ", DisplayableAppName[name], ". We won't be able to respond to your submission, but your feedback helps us improve the experience helps us improve the experience."] }), _jsxs(View, { style: styles.textInputContainer, children: [_jsxs(Text, { style: styles.fieldLabel, children: ["Where did you experience the issue? ", _jsx(Text, { style: styles.required, children: "*" })] }), _jsxs(TouchableOpacity, { style: styles.pickerButton, onPress: () => setShowBugTypePicker(true), children: [_jsx(Text, { style: [styles.pickerText, !bugType && styles.pickerPlaceholder], children: bugType }), _jsx(Icon, { name: "general.downChevron", style: styles.pickerArrow, accessibilityElementsHidden: true })] })] }), _jsx(SafeAreaModal, { visible: showBugTypePicker, animationType: "slide", presentationStyle: "pageSheet", onRequestClose: () => setShowBugTypePicker(false), children: _jsxs(View, { style: styles.modalContainer, children: [_jsxs(View, { style: styles.modalHeader, children: [_jsx(HeaderDismissButton, { title: "Cancel", onPress: () => setShowBugTypePicker(false) }), _jsx(Text, { style: styles.modalTitle, children: "Select Bug Type" }), _jsx(View, { style: styles.modalHeaderSpacer })] }), _jsx(ScrollView, { style: styles.modalContent, children: Object.values(BUG_TYPE_OPTIONS).map(option => (_jsxs(TouchableOpacity, { style: styles.modalOption, onPress: () => {
|
|
130
|
+
setBugType(option);
|
|
131
|
+
setShowBugTypePicker(false);
|
|
132
|
+
}, children: [_jsx(Text, { style: styles.modalOptionText, children: option }), bugType === option && (_jsx(Icon, { name: "general.check", style: styles.modalCheckmark, accessibilityElementsHidden: true }))] }, option))) })] }) }), _jsxs(View, { style: styles.textInputContainer, children: [_jsxs(Text, { style: styles.fieldLabel, children: ["What were you trying to do when you encountered the bug?", ' ', _jsx(Text, { style: styles.required, children: "*" })] }), _jsx(TextInput, { style: styles.textInput, multiline: true, placeholder: "Description", value: whatWereDoing, onChangeText: setWhatWereDoing, maxLength: MAX_DESCRIPTION_LENGTH }), whatWereDoing.length >= MAX_DESCRIPTION_LENGTH - 100 && (_jsxs(Text, { variant: "footnote", children: [whatWereDoing.length, "/", MAX_DESCRIPTION_LENGTH] }))] }), _jsxs(View, { style: styles.textInputContainer, children: [_jsxs(Text, { style: styles.fieldLabel, children: ["What did you expect to happen? Please describe what actually happened.", ' ', _jsx(Text, { style: styles.required, children: "*" })] }), _jsx(TextInput, { style: styles.textInput, multiline: true, placeholder: "Description", value: whatExpected, onChangeText: setWhatExpected, maxLength: MAX_DESCRIPTION_LENGTH }), whatExpected.length >= MAX_DESCRIPTION_LENGTH - 100 && (_jsxs(Text, { variant: "footnote", children: [whatExpected.length, "/", MAX_DESCRIPTION_LENGTH] }))] }), _jsxs(View, { style: styles.attachmentSection, children: [_jsxs(View, { style: styles.attachmentHeader, children: [_jsxs(Text, { style: styles.attachmentLabel, children: ["Attachment ", _jsx(Text, { style: styles.subLabel, children: "(optional)" })] }), uploading && _jsx(Spinner, {})] }), uploadError && _jsx(Text, { style: styles.attachmentErrorText, children: uploadError }), attachment ? (_jsx(View, { style: styles.attachmentPreviewContainer, children: isImageAttachment ? (_jsx(ImageAttachmentPreview, { uri: imagePreviewURI, fileName: attachment.name, onRemovePress: handleRemoveAttachment })) : (_jsx(VideoAttachmentPreview, { name: attachment.name, onRemovePress: handleRemoveAttachment })) })) : (_jsx(Button, { title: "Attach a screenshot or recording", accessibilityHint: "Opens your device's image gallery", iconNameLeft: "general.paperclip", onPress: pickImage, size: "sm", variant: "outline", style: styles.attachButton, disabled: uploading || Boolean(attachment) })), _jsxs(Text, { variant: "footnote", children: ["Screenshots and screen recordings help us reproduce and fix issues faster.", ' ', _jsx(TextInlineButton, { accessibilityRole: "link", variant: "footnote", onPress: () => Linking.openURL(VIDEO_RECORDING_HELP_URL), children: "How to record your screen" })] })] }), _jsx(View, { style: styles.footer, children: _jsxs(Text, { variant: "footnote", children: ["For details on how we process your data and ensure its security, please refer to our", ' ', _jsx(TextInlineButton, { accessibilityRole: "link", variant: "footnote", onPress: () => Linking.openURL('https://www.planningcenter.com/privacy'), children: "Privacy Policy" }), "."] }) })] }));
|
|
133
133
|
}
|
|
134
134
|
const VIDEO_RECORDING_HELP_URL = Platform.select({
|
|
135
135
|
android: 'https://support.google.com/android/answer/9075928?hl=en',
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"bug_report_screen.js","sourceRoot":"","sources":["../../src/screens/bug_report_screen.tsx"],"names":[],"mappings":"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","sourcesContent":["import { useNavigation } from '@react-navigation/native'\nimport type {\n NativeStackNavigationOptions,\n NativeStackScreenProps,\n} from '@react-navigation/native-stack'\nimport { startsWith } from 'lodash'\nimport React, { useCallback, useState } from 'react'\nimport {\n View,\n StyleSheet,\n TextInput,\n Linking,\n ScrollView,\n TouchableOpacity,\n Platform,\n} from 'react-native'\nimport { useSafeAreaInsets } from 'react-native-safe-area-context'\nimport {\n Button,\n Spinner,\n Text,\n TextInlineButton,\n ImageAttachmentPreview,\n Icon,\n KeyboardView,\n} from '../components'\nimport {\n composeOptions,\n HeaderDismissButton,\n useHeaderRight,\n withLeftClose,\n} from '../components/display/platform_modal_header_buttons'\nimport { VideoAttachmentPreview } from '../components/display/video_attachment_preview'\nimport { DefaultLoading } from '../components/page/loading'\nimport BlankState from '../components/primitive/blank_state_primitive'\nimport { SafeAreaModal } from '../components/safe_area_modal'\nimport { useTheme } from '../hooks'\nimport { useAppName } from '../hooks/use_app_name'\nimport { useReportBugAction } from '../hooks/use_report_bug_action'\nimport { useUploadClient } from '../hooks/use_upload_client'\nimport { ImagePicker, ImagePickerResult, platformFontWeightBold } from '../utils'\n\nconst MAX_DESCRIPTION_LENGTH = 2000\n\nenum BUG_TYPE_OPTIONS {\n Chat = 'Chat',\n FindMyChurch = 'Find my church',\n LoggingIn = 'Logging in',\n UsingGroups = 'Using groups (events, resources, members)',\n CheckingIn = 'Checking in',\n MakingADonation = 'Making a donation',\n RegisteringForAnEvent = 'Registering for an event',\n MyProfileAndSchedule = 'My profile and schedule',\n Directory = 'Directory',\n Other = 'Other',\n}\n\nexport const BugReportScreenOptions = ({\n navigation,\n}: NativeStackScreenProps<any>): NativeStackNavigationOptions =>\n composeOptions(\n { presentation: 'modal', title: 'Report a bug' },\n withLeftClose({ onPress: () => navigation.goBack() })\n )\n\ninterface Attachment {\n id: string\n name: string\n type: string\n}\n\nenum QualifiedMobileAppName {\n chat = 'Chat', // There is no app name for the mobile app\n churchcenter = 'Church Center App',\n services = 'Services Mobile',\n}\n\nenum DisplayableAppName {\n chat = 'Chat',\n churchcenter = 'Church Center',\n services = 'Services',\n}\n\nexport function BugReportScreen() {\n const styles = useStyles()\n const navigation = useNavigation()\n const name = useAppName()\n const appName = QualifiedMobileAppName[name]\n const [bugType, setBugType] = useState<BUG_TYPE_OPTIONS>(BUG_TYPE_OPTIONS.Chat)\n const [showBugTypePicker, setShowBugTypePicker] = useState(false)\n const [whatWereDoing, setWhatWereDoing] = useState('')\n const [whatExpected, setWhatExpected] = useState('')\n const uploadApi = useUploadClient()\n const [uploading, setUploading] = useState(false)\n const [attachment, setAttachment] = useState<Attachment | null>(null)\n const [uploadError, setUploadError] = useState<string | null>(null)\n const { mutate: createBugReport, status } = useReportBugAction()\n const formValid =\n bugType.trim().length > 0 &&\n whatWereDoing.trim().length > 0 &&\n whatExpected.trim().length > 0 &&\n status === 'idle' &&\n !uploading\n const [imagePreviewURI, setImagePreviewURI] = useState<string>('')\n const isImageAttachment = startsWith(attachment?.type, 'image/')\n\n const handleSubmit = useCallback(() => {\n const description = generateBugReportDescription(bugType, whatWereDoing, whatExpected)\n\n createBugReport({\n description,\n description_json: {\n bugType,\n whatWereDoing,\n whatExpected,\n appName: appName,\n },\n attachmentIds: attachment ? [attachment.id] : [],\n })\n }, [attachment, bugType, whatWereDoing, whatExpected, createBugReport, appName])\n\n const handleRemoveAttachment = useCallback(() => {\n setAttachment(null)\n setImagePreviewURI('')\n }, [])\n\n function uploadImagePickerResult(result: ImagePickerResult) {\n if (result.canceled || result.assets.length === 0) {\n setUploading(false)\n return\n }\n\n const asset = result.assets[0]\n\n uploadApi\n ?.uploadFile({\n uri: asset.uri,\n name: asset.fileName as string,\n type: asset.mimeType as string,\n })\n .then(uploadedResource => {\n setUploading(false)\n setImagePreviewURI(asset.uri)\n setAttachment({\n id: uploadedResource.id,\n name: asset.fileName || 'File',\n type: asset.mimeType as string,\n })\n })\n .catch(() => {\n setUploading(false)\n setUploadError(`Failed to upload attachment`)\n })\n }\n\n function pickImage() {\n setUploading(true)\n return ImagePicker.openImageLibraryAsync().then(result => uploadImagePickerResult(result))\n }\n\n useHeaderRight({\n icon: 'general.upArrow',\n accessibilityLabel: 'Submit',\n prominent: true,\n onPress: handleSubmit,\n disabled: !formValid,\n })\n\n if (status === 'pending') {\n return (\n <View style={[styles.container, styles.fullHeight]}>\n <DefaultLoading />\n </View>\n )\n }\n\n if (status === 'success') {\n return (\n <BlankState.Root>\n <BlankState.Imagery name=\"general.checkCircle\" style={styles.successIcon} />\n <BlankState.Content>\n <BlankState.Heading style={styles.successTitle}>Thank you!</BlankState.Heading>\n <BlankState.Text style={styles.successSubtitle}>\n We appreciate you taking the time to help improve {DisplayableAppName[name]}! We'll take\n a look at the issue you reported.\n </BlankState.Text>\n </BlankState.Content>\n <BlankState.Button\n title=\"Return to chat\"\n onPress={navigation.goBack}\n size=\"lg\"\n variant=\"fill\"\n />\n </BlankState.Root>\n )\n }\n\n if (status === 'error') {\n return (\n <View style={styles.container}>\n <Text>\n This is embarrassing, we can't submit your bug report right now. If you still need help or\n would like to submit this bug report another way please{' '}\n <TextInlineButton\n accessibilityRole=\"link\"\n onPress={() =>\n Linking.openURL('https://support.planningcenteronline.com/hc/en-us/requests/new')\n }\n >\n contact our help center\n </TextInlineButton>\n .\n </Text>\n <Button title=\"Return to chat\" onPress={navigation.goBack} variant=\"fill\" size=\"lg\" />\n </View>\n )\n }\n\n return (\n <KeyboardView>\n <ScrollView contentContainerStyle={styles.container}>\n <Text style={styles.description}>\n Thanks for helping us improve {DisplayableAppName[name]}. We won't be able to respond to\n your submission, but your feedback helps us improve the experience helps us improve the\n experience.\n </Text>\n\n <View style={styles.textInputContainer}>\n <Text style={styles.fieldLabel}>\n Where did you experience the issue? <Text style={styles.required}>*</Text>\n </Text>\n <TouchableOpacity style={styles.pickerButton} onPress={() => setShowBugTypePicker(true)}>\n <Text style={[styles.pickerText, !bugType && styles.pickerPlaceholder]}>{bugType}</Text>\n <Icon\n name=\"general.downChevron\"\n style={styles.pickerArrow}\n accessibilityElementsHidden\n />\n </TouchableOpacity>\n </View>\n\n <SafeAreaModal\n visible={showBugTypePicker}\n animationType=\"slide\"\n presentationStyle=\"pageSheet\"\n onRequestClose={() => setShowBugTypePicker(false)}\n >\n <View style={styles.modalContainer}>\n <View style={styles.modalHeader}>\n <HeaderDismissButton title=\"Cancel\" onPress={() => setShowBugTypePicker(false)} />\n <Text style={styles.modalTitle}>Select Bug Type</Text>\n <View style={styles.modalHeaderSpacer} />\n </View>\n <ScrollView style={styles.modalContent}>\n {Object.values(BUG_TYPE_OPTIONS).map(option => (\n <TouchableOpacity\n key={option}\n style={styles.modalOption}\n onPress={() => {\n setBugType(option)\n setShowBugTypePicker(false)\n }}\n >\n <Text style={styles.modalOptionText}>{option}</Text>\n {bugType === option && (\n <Icon\n name=\"general.check\"\n style={styles.modalCheckmark}\n accessibilityElementsHidden\n />\n )}\n </TouchableOpacity>\n ))}\n </ScrollView>\n </View>\n </SafeAreaModal>\n\n <View style={styles.textInputContainer}>\n <Text style={styles.fieldLabel}>\n What were you trying to do when you encountered the bug?{' '}\n <Text style={styles.required}>*</Text>\n </Text>\n <TextInput\n style={styles.textInput}\n multiline\n placeholder=\"Description\"\n value={whatWereDoing}\n onChangeText={setWhatWereDoing}\n maxLength={MAX_DESCRIPTION_LENGTH}\n />\n {whatWereDoing.length >= MAX_DESCRIPTION_LENGTH - 100 && (\n <Text variant=\"footnote\">\n {whatWereDoing.length}/{MAX_DESCRIPTION_LENGTH}\n </Text>\n )}\n </View>\n\n <View style={styles.textInputContainer}>\n <Text style={styles.fieldLabel}>\n What did you expect to happen? Please describe what actually happened.{' '}\n <Text style={styles.required}>*</Text>\n </Text>\n <TextInput\n style={styles.textInput}\n multiline\n placeholder=\"Description\"\n value={whatExpected}\n onChangeText={setWhatExpected}\n maxLength={MAX_DESCRIPTION_LENGTH}\n />\n {whatExpected.length >= MAX_DESCRIPTION_LENGTH - 100 && (\n <Text variant=\"footnote\">\n {whatExpected.length}/{MAX_DESCRIPTION_LENGTH}\n </Text>\n )}\n </View>\n\n <View style={styles.attachmentSection}>\n <View style={styles.attachmentHeader}>\n <Text style={styles.attachmentLabel}>\n Attachment <Text style={styles.subLabel}>(optional)</Text>\n </Text>\n {uploading && <Spinner />}\n </View>\n {uploadError && <Text style={styles.attachmentErrorText}>{uploadError}</Text>}\n {attachment ? (\n <View style={styles.attachmentPreviewContainer}>\n {isImageAttachment ? (\n <ImageAttachmentPreview\n uri={imagePreviewURI}\n fileName={attachment.name}\n onRemovePress={handleRemoveAttachment}\n />\n ) : (\n <VideoAttachmentPreview\n name={attachment.name}\n onRemovePress={handleRemoveAttachment}\n />\n )}\n </View>\n ) : (\n <Button\n title=\"Attach a screenshot or recording\"\n accessibilityHint=\"Opens your device's image gallery\"\n iconNameLeft=\"general.paperclip\"\n onPress={pickImage}\n size=\"sm\"\n variant=\"outline\"\n style={styles.attachButton}\n disabled={uploading || Boolean(attachment)}\n />\n )}\n <Text variant=\"footnote\">\n Screenshots and screen recordings help us reproduce and fix issues faster.{' '}\n <TextInlineButton\n accessibilityRole=\"link\"\n variant=\"footnote\"\n onPress={() => Linking.openURL(VIDEO_RECORDING_HELP_URL)}\n >\n How to record your screen\n </TextInlineButton>\n </Text>\n </View>\n\n <View style={styles.footer}>\n <Text variant=\"footnote\">\n For details on how we process your data and ensure its security, please refer to our{' '}\n <TextInlineButton\n accessibilityRole=\"link\"\n variant=\"footnote\"\n onPress={() => Linking.openURL('https://www.planningcenter.com/privacy')}\n >\n Privacy Policy\n </TextInlineButton>\n .\n </Text>\n </View>\n </ScrollView>\n </KeyboardView>\n )\n}\n\nconst VIDEO_RECORDING_HELP_URL = Platform.select({\n android: 'https://support.google.com/android/answer/9075928?hl=en',\n default: 'https://support.apple.com/en-us/102653',\n})\n\nconst generateBugReportDescription = (\n bugType: BUG_TYPE_OPTIONS,\n whatWereDoing: string,\n whatExpected: string\n) => {\n return `${whatWereDoing.substring(0, 100)}\n\n ## What kind of bug did you experience?\n${bugType}\n\n## What were you trying to do when you encountered the bug?\n${whatWereDoing}\n\n## What did you expect to happen? What actually happened?\n${whatExpected}\n`\n}\n\nconst useStyles = () => {\n const { bottom } = useSafeAreaInsets()\n const { colors } = useTheme()\n return StyleSheet.create({\n container: {\n padding: 16,\n paddingBottom: 16 + bottom,\n gap: 24,\n },\n fullHeight: {\n flex: 1,\n },\n description: {\n color: colors.textColorDefaultSecondary,\n },\n textInputContainer: {\n gap: 8,\n },\n fieldLabel: {\n fontSize: 16,\n fontWeight: platformFontWeightBold,\n color: colors.textColorDefaultPrimary,\n },\n required: {\n color: colors.statusErrorText,\n },\n pickerButton: {\n flexDirection: 'row',\n alignItems: 'center',\n justifyContent: 'space-between',\n borderWidth: 1,\n borderColor: colors.borderColorDefaultBase,\n borderRadius: 8,\n paddingHorizontal: 16,\n paddingVertical: 12,\n backgroundColor: colors.surfaceColor100,\n minHeight: 48,\n },\n pickerText: {\n fontSize: 16,\n color: colors.textColorDefaultPrimary,\n flex: 1,\n },\n pickerPlaceholder: {\n color: colors.textColorDefaultSecondary,\n },\n pickerArrow: {\n fontSize: 12,\n color: colors.iconColorDefaultSecondary,\n marginLeft: 8,\n },\n modalContainer: {\n flex: 1,\n backgroundColor: colors.surfaceColor100,\n },\n modalHeader: {\n flexDirection: 'row',\n alignItems: 'center',\n justifyContent: 'space-between',\n padding: 16,\n borderBottomWidth: 1,\n borderBottomColor: colors.borderColorDefaultBase,\n },\n modalTitle: {\n fontSize: 18,\n fontWeight: platformFontWeightBold,\n color: colors.textColorDefaultPrimary,\n },\n modalHeaderSpacer: {\n width: 50, // Same width as cancel button to center title\n },\n modalContent: {\n flex: 1,\n },\n modalOption: {\n flexDirection: 'row',\n alignItems: 'center',\n justifyContent: 'space-between',\n paddingHorizontal: 16,\n paddingVertical: 16,\n borderBottomWidth: 1,\n borderBottomColor: colors.borderColorDefaultBase,\n },\n modalOptionText: {\n fontSize: 16,\n color: colors.textColorDefaultPrimary,\n flex: 1,\n },\n modalCheckmark: {\n fontSize: 16,\n color: colors.statusSuccessIcon,\n },\n textInput: {\n color: colors.textColorDefaultPrimary,\n fontSize: 16,\n textAlignVertical: 'top',\n minHeight: 120,\n maxHeight: 200,\n borderWidth: 1,\n borderColor: colors.borderColorDefaultBase,\n borderRadius: 8,\n paddingHorizontal: 16,\n paddingVertical: 12,\n backgroundColor: colors.surfaceColor100,\n },\n attachmentSection: {\n gap: 8,\n },\n attachmentHeader: {\n flexDirection: 'row',\n gap: 4,\n alignItems: 'center',\n },\n attachmentLabel: { fontWeight: platformFontWeightBold },\n subLabel: { fontWeight: 'normal', color: colors.textColorDefaultSecondary },\n attachmentPreviewContainer: {\n gap: 4,\n },\n attachmentErrorText: {\n color: colors.statusErrorText,\n },\n attachButton: {\n alignSelf: 'flex-start',\n },\n footer: { gap: 8 },\n successIcon: {\n color: colors.statusSuccessIcon,\n fontSize: 48,\n },\n successTitle: {\n fontSize: 24,\n marginBottom: 4,\n },\n successSubtitle: {\n fontSize: 16,\n marginBottom: 4,\n },\n })\n}\n"]}
|
|
1
|
+
{"version":3,"file":"bug_report_screen.js","sourceRoot":"","sources":["../../src/screens/bug_report_screen.tsx"],"names":[],"mappings":";AAAA,OAAO,EAAE,aAAa,EAAE,MAAM,0BAA0B,CAAA;AAKxD,OAAO,EAAE,UAAU,EAAE,MAAM,QAAQ,CAAA;AACnC,OAAc,EAAE,WAAW,EAAE,QAAQ,EAAE,MAAM,OAAO,CAAA;AACpD,OAAO,EACL,IAAI,EACJ,UAAU,EACV,SAAS,EACT,OAAO,EACP,UAAU,EACV,gBAAgB,EAChB,QAAQ,GACT,MAAM,cAAc,CAAA;AACrB,OAAO,EAAE,iBAAiB,EAAE,MAAM,gCAAgC,CAAA;AAClE,OAAO,EACL,MAAM,EACN,OAAO,EACP,IAAI,EACJ,gBAAgB,EAChB,sBAAsB,EACtB,IAAI,EACJ,kBAAkB,GACnB,MAAM,eAAe,CAAA;AACtB,OAAO,EACL,cAAc,EACd,mBAAmB,EACnB,cAAc,EACd,aAAa,GACd,MAAM,qDAAqD,CAAA;AAC5D,OAAO,EAAE,sBAAsB,EAAE,MAAM,gDAAgD,CAAA;AACvF,OAAO,EAAE,cAAc,EAAE,MAAM,4BAA4B,CAAA;AAC3D,OAAO,UAAU,MAAM,+CAA+C,CAAA;AACtE,OAAO,EAAE,aAAa,EAAE,MAAM,+BAA+B,CAAA;AAC7D,OAAO,EAAE,QAAQ,EAAE,MAAM,UAAU,CAAA;AACnC,OAAO,EAAE,UAAU,EAAE,MAAM,uBAAuB,CAAA;AAClD,OAAO,EAAE,kBAAkB,EAAE,MAAM,gCAAgC,CAAA;AACnE,OAAO,EAAE,eAAe,EAAE,MAAM,4BAA4B,CAAA;AAC5D,OAAO,EAAE,WAAW,EAAqB,sBAAsB,EAAE,MAAM,UAAU,CAAA;AAEjF,MAAM,sBAAsB,GAAG,IAAI,CAAA;AAEnC,IAAK,gBAWJ;AAXD,WAAK,gBAAgB;IACnB,iCAAa,CAAA;IACb,mDAA+B,CAAA;IAC/B,4CAAwB,CAAA;IACxB,6EAAyD,CAAA;IACzD,8CAA0B,CAAA;IAC1B,yDAAqC,CAAA;IACrC,sEAAkD,CAAA;IAClD,oEAAgD,CAAA;IAChD,2CAAuB,CAAA;IACvB,mCAAe,CAAA;AACjB,CAAC,EAXI,gBAAgB,KAAhB,gBAAgB,QAWpB;AAED,MAAM,CAAC,MAAM,sBAAsB,GAAG,CAAC,EACrC,UAAU,GACkB,EAAgC,EAAE,CAC9D,cAAc,CACZ,EAAE,YAAY,EAAE,OAAO,EAAE,KAAK,EAAE,cAAc,EAAE,EAChD,aAAa,CAAC,EAAE,OAAO,EAAE,GAAG,EAAE,CAAC,UAAU,CAAC,MAAM,EAAE,EAAE,CAAC,CACtD,CAAA;AAQH,IAAK,sBAIJ;AAJD,WAAK,sBAAsB;IACzB,uCAAa,CAAA;IACb,4DAAkC,CAAA;IAClC,sDAA4B,CAAA;AAC9B,CAAC,EAJI,sBAAsB,KAAtB,sBAAsB,QAI1B;AAED,IAAK,kBAIJ;AAJD,WAAK,kBAAkB;IACrB,mCAAa,CAAA;IACb,oDAA8B,CAAA;IAC9B,2CAAqB,CAAA;AACvB,CAAC,EAJI,kBAAkB,KAAlB,kBAAkB,QAItB;AAED,MAAM,UAAU,eAAe;IAC7B,MAAM,MAAM,GAAG,SAAS,EAAE,CAAA;IAC1B,MAAM,UAAU,GAAG,aAAa,EAAE,CAAA;IAClC,MAAM,IAAI,GAAG,UAAU,EAAE,CAAA;IACzB,MAAM,OAAO,GAAG,sBAAsB,CAAC,IAAI,CAAC,CAAA;IAC5C,MAAM,CAAC,OAAO,EAAE,UAAU,CAAC,GAAG,QAAQ,CAAmB,gBAAgB,CAAC,IAAI,CAAC,CAAA;IAC/E,MAAM,CAAC,iBAAiB,EAAE,oBAAoB,CAAC,GAAG,QAAQ,CAAC,KAAK,CAAC,CAAA;IACjE,MAAM,CAAC,aAAa,EAAE,gBAAgB,CAAC,GAAG,QAAQ,CAAC,EAAE,CAAC,CAAA;IACtD,MAAM,CAAC,YAAY,EAAE,eAAe,CAAC,GAAG,QAAQ,CAAC,EAAE,CAAC,CAAA;IACpD,MAAM,SAAS,GAAG,eAAe,EAAE,CAAA;IACnC,MAAM,CAAC,SAAS,EAAE,YAAY,CAAC,GAAG,QAAQ,CAAC,KAAK,CAAC,CAAA;IACjD,MAAM,CAAC,UAAU,EAAE,aAAa,CAAC,GAAG,QAAQ,CAAoB,IAAI,CAAC,CAAA;IACrE,MAAM,CAAC,WAAW,EAAE,cAAc,CAAC,GAAG,QAAQ,CAAgB,IAAI,CAAC,CAAA;IACnE,MAAM,EAAE,MAAM,EAAE,eAAe,EAAE,MAAM,EAAE,GAAG,kBAAkB,EAAE,CAAA;IAChE,MAAM,SAAS,GACb,OAAO,CAAC,IAAI,EAAE,CAAC,MAAM,GAAG,CAAC;QACzB,aAAa,CAAC,IAAI,EAAE,CAAC,MAAM,GAAG,CAAC;QAC/B,YAAY,CAAC,IAAI,EAAE,CAAC,MAAM,GAAG,CAAC;QAC9B,MAAM,KAAK,MAAM;QACjB,CAAC,SAAS,CAAA;IACZ,MAAM,CAAC,eAAe,EAAE,kBAAkB,CAAC,GAAG,QAAQ,CAAS,EAAE,CAAC,CAAA;IAClE,MAAM,iBAAiB,GAAG,UAAU,CAAC,UAAU,EAAE,IAAI,EAAE,QAAQ,CAAC,CAAA;IAEhE,MAAM,YAAY,GAAG,WAAW,CAAC,GAAG,EAAE;QACpC,MAAM,WAAW,GAAG,4BAA4B,CAAC,OAAO,EAAE,aAAa,EAAE,YAAY,CAAC,CAAA;QAEtF,eAAe,CAAC;YACd,WAAW;YACX,gBAAgB,EAAE;gBAChB,OAAO;gBACP,aAAa;gBACb,YAAY;gBACZ,OAAO,EAAE,OAAO;aACjB;YACD,aAAa,EAAE,UAAU,CAAC,CAAC,CAAC,CAAC,UAAU,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,EAAE;SACjD,CAAC,CAAA;IACJ,CAAC,EAAE,CAAC,UAAU,EAAE,OAAO,EAAE,aAAa,EAAE,YAAY,EAAE,eAAe,EAAE,OAAO,CAAC,CAAC,CAAA;IAEhF,MAAM,sBAAsB,GAAG,WAAW,CAAC,GAAG,EAAE;QAC9C,aAAa,CAAC,IAAI,CAAC,CAAA;QACnB,kBAAkB,CAAC,EAAE,CAAC,CAAA;IACxB,CAAC,EAAE,EAAE,CAAC,CAAA;IAEN,SAAS,uBAAuB,CAAC,MAAyB;QACxD,IAAI,MAAM,CAAC,QAAQ,IAAI,MAAM,CAAC,MAAM,CAAC,MAAM,KAAK,CAAC,EAAE,CAAC;YAClD,YAAY,CAAC,KAAK,CAAC,CAAA;YACnB,OAAM;QACR,CAAC;QAED,MAAM,KAAK,GAAG,MAAM,CAAC,MAAM,CAAC,CAAC,CAAC,CAAA;QAE9B,SAAS;YACP,EAAE,UAAU,CAAC;YACX,GAAG,EAAE,KAAK,CAAC,GAAG;YACd,IAAI,EAAE,KAAK,CAAC,QAAkB;YAC9B,IAAI,EAAE,KAAK,CAAC,QAAkB;SAC/B,CAAC;aACD,IAAI,CAAC,gBAAgB,CAAC,EAAE;YACvB,YAAY,CAAC,KAAK,CAAC,CAAA;YACnB,kBAAkB,CAAC,KAAK,CAAC,GAAG,CAAC,CAAA;YAC7B,aAAa,CAAC;gBACZ,EAAE,EAAE,gBAAgB,CAAC,EAAE;gBACvB,IAAI,EAAE,KAAK,CAAC,QAAQ,IAAI,MAAM;gBAC9B,IAAI,EAAE,KAAK,CAAC,QAAkB;aAC/B,CAAC,CAAA;QACJ,CAAC,CAAC;aACD,KAAK,CAAC,GAAG,EAAE;YACV,YAAY,CAAC,KAAK,CAAC,CAAA;YACnB,cAAc,CAAC,6BAA6B,CAAC,CAAA;QAC/C,CAAC,CAAC,CAAA;IACN,CAAC;IAED,SAAS,SAAS;QAChB,YAAY,CAAC,IAAI,CAAC,CAAA;QAClB,OAAO,WAAW,CAAC,qBAAqB,EAAE,CAAC,IAAI,CAAC,MAAM,CAAC,EAAE,CAAC,uBAAuB,CAAC,MAAM,CAAC,CAAC,CAAA;IAC5F,CAAC;IAED,cAAc,CAAC;QACb,IAAI,EAAE,iBAAiB;QACvB,kBAAkB,EAAE,QAAQ;QAC5B,SAAS,EAAE,IAAI;QACf,OAAO,EAAE,YAAY;QACrB,QAAQ,EAAE,CAAC,SAAS;KACrB,CAAC,CAAA;IAEF,IAAI,MAAM,KAAK,SAAS,EAAE,CAAC;QACzB,OAAO,CACL,KAAC,IAAI,IAAC,KAAK,EAAE,CAAC,MAAM,CAAC,SAAS,EAAE,MAAM,CAAC,UAAU,CAAC,YAChD,KAAC,cAAc,KAAG,GACb,CACR,CAAA;IACH,CAAC;IAED,IAAI,MAAM,KAAK,SAAS,EAAE,CAAC;QACzB,OAAO,CACL,MAAC,UAAU,CAAC,IAAI,eACd,KAAC,UAAU,CAAC,OAAO,IAAC,IAAI,EAAC,qBAAqB,EAAC,KAAK,EAAE,MAAM,CAAC,WAAW,GAAI,EAC5E,MAAC,UAAU,CAAC,OAAO,eACjB,KAAC,UAAU,CAAC,OAAO,IAAC,KAAK,EAAE,MAAM,CAAC,YAAY,2BAAiC,EAC/E,MAAC,UAAU,CAAC,IAAI,IAAC,KAAK,EAAE,MAAM,CAAC,eAAe,mEACO,kBAAkB,CAAC,IAAI,CAAC,sDAE3D,IACC,EACrB,KAAC,UAAU,CAAC,MAAM,IAChB,KAAK,EAAC,gBAAgB,EACtB,OAAO,EAAE,UAAU,CAAC,MAAM,EAC1B,IAAI,EAAC,IAAI,EACT,OAAO,EAAC,MAAM,GACd,IACc,CACnB,CAAA;IACH,CAAC;IAED,IAAI,MAAM,KAAK,OAAO,EAAE,CAAC;QACvB,OAAO,CACL,MAAC,IAAI,IAAC,KAAK,EAAE,MAAM,CAAC,SAAS,aAC3B,MAAC,IAAI,qKAEqD,GAAG,EAC3D,KAAC,gBAAgB,IACf,iBAAiB,EAAC,MAAM,EACxB,OAAO,EAAE,GAAG,EAAE,CACZ,OAAO,CAAC,OAAO,CAAC,gEAAgE,CAAC,wCAIlE,SAEd,EACP,KAAC,MAAM,IAAC,KAAK,EAAC,gBAAgB,EAAC,OAAO,EAAE,UAAU,CAAC,MAAM,EAAE,OAAO,EAAC,MAAM,EAAC,IAAI,EAAC,IAAI,GAAG,IACjF,CACR,CAAA;IACH,CAAC;IAED,OAAO,CACL,MAAC,kBAAkB,IAAC,qBAAqB,EAAE,MAAM,CAAC,SAAS,aACzD,MAAC,IAAI,IAAC,KAAK,EAAE,MAAM,CAAC,WAAW,+CACE,kBAAkB,CAAC,IAAI,CAAC,4IAGlD,EAEP,MAAC,IAAI,IAAC,KAAK,EAAE,MAAM,CAAC,kBAAkB,aACpC,MAAC,IAAI,IAAC,KAAK,EAAE,MAAM,CAAC,UAAU,qDACQ,KAAC,IAAI,IAAC,KAAK,EAAE,MAAM,CAAC,QAAQ,kBAAU,IACrE,EACP,MAAC,gBAAgB,IAAC,KAAK,EAAE,MAAM,CAAC,YAAY,EAAE,OAAO,EAAE,GAAG,EAAE,CAAC,oBAAoB,CAAC,IAAI,CAAC,aACrF,KAAC,IAAI,IAAC,KAAK,EAAE,CAAC,MAAM,CAAC,UAAU,EAAE,CAAC,OAAO,IAAI,MAAM,CAAC,iBAAiB,CAAC,YAAG,OAAO,GAAQ,EACxF,KAAC,IAAI,IAAC,IAAI,EAAC,qBAAqB,EAAC,KAAK,EAAE,MAAM,CAAC,WAAW,EAAE,2BAA2B,SAAG,IACzE,IACd,EAEP,KAAC,aAAa,IACZ,OAAO,EAAE,iBAAiB,EAC1B,aAAa,EAAC,OAAO,EACrB,iBAAiB,EAAC,WAAW,EAC7B,cAAc,EAAE,GAAG,EAAE,CAAC,oBAAoB,CAAC,KAAK,CAAC,YAEjD,MAAC,IAAI,IAAC,KAAK,EAAE,MAAM,CAAC,cAAc,aAChC,MAAC,IAAI,IAAC,KAAK,EAAE,MAAM,CAAC,WAAW,aAC7B,KAAC,mBAAmB,IAAC,KAAK,EAAC,QAAQ,EAAC,OAAO,EAAE,GAAG,EAAE,CAAC,oBAAoB,CAAC,KAAK,CAAC,GAAI,EAClF,KAAC,IAAI,IAAC,KAAK,EAAE,MAAM,CAAC,UAAU,gCAAwB,EACtD,KAAC,IAAI,IAAC,KAAK,EAAE,MAAM,CAAC,iBAAiB,GAAI,IACpC,EACP,KAAC,UAAU,IAAC,KAAK,EAAE,MAAM,CAAC,YAAY,YACnC,MAAM,CAAC,MAAM,CAAC,gBAAgB,CAAC,CAAC,GAAG,CAAC,MAAM,CAAC,EAAE,CAAC,CAC7C,MAAC,gBAAgB,IAEf,KAAK,EAAE,MAAM,CAAC,WAAW,EACzB,OAAO,EAAE,GAAG,EAAE;oCACZ,UAAU,CAAC,MAAM,CAAC,CAAA;oCAClB,oBAAoB,CAAC,KAAK,CAAC,CAAA;gCAC7B,CAAC,aAED,KAAC,IAAI,IAAC,KAAK,EAAE,MAAM,CAAC,eAAe,YAAG,MAAM,GAAQ,EACnD,OAAO,KAAK,MAAM,IAAI,CACrB,KAAC,IAAI,IACH,IAAI,EAAC,eAAe,EACpB,KAAK,EAAE,MAAM,CAAC,cAAc,EAC5B,2BAA2B,SAC3B,CACH,KAdI,MAAM,CAeM,CACpB,CAAC,GACS,IACR,GACO,EAEhB,MAAC,IAAI,IAAC,KAAK,EAAE,MAAM,CAAC,kBAAkB,aACpC,MAAC,IAAI,IAAC,KAAK,EAAE,MAAM,CAAC,UAAU,yEAC6B,GAAG,EAC5D,KAAC,IAAI,IAAC,KAAK,EAAE,MAAM,CAAC,QAAQ,kBAAU,IACjC,EACP,KAAC,SAAS,IACR,KAAK,EAAE,MAAM,CAAC,SAAS,EACvB,SAAS,QACT,WAAW,EAAC,aAAa,EACzB,KAAK,EAAE,aAAa,EACpB,YAAY,EAAE,gBAAgB,EAC9B,SAAS,EAAE,sBAAsB,GACjC,EACD,aAAa,CAAC,MAAM,IAAI,sBAAsB,GAAG,GAAG,IAAI,CACvD,MAAC,IAAI,IAAC,OAAO,EAAC,UAAU,aACrB,aAAa,CAAC,MAAM,OAAG,sBAAsB,IACzC,CACR,IACI,EAEP,MAAC,IAAI,IAAC,KAAK,EAAE,MAAM,CAAC,kBAAkB,aACpC,MAAC,IAAI,IAAC,KAAK,EAAE,MAAM,CAAC,UAAU,uFAC2C,GAAG,EAC1E,KAAC,IAAI,IAAC,KAAK,EAAE,MAAM,CAAC,QAAQ,kBAAU,IACjC,EACP,KAAC,SAAS,IACR,KAAK,EAAE,MAAM,CAAC,SAAS,EACvB,SAAS,QACT,WAAW,EAAC,aAAa,EACzB,KAAK,EAAE,YAAY,EACnB,YAAY,EAAE,eAAe,EAC7B,SAAS,EAAE,sBAAsB,GACjC,EACD,YAAY,CAAC,MAAM,IAAI,sBAAsB,GAAG,GAAG,IAAI,CACtD,MAAC,IAAI,IAAC,OAAO,EAAC,UAAU,aACrB,YAAY,CAAC,MAAM,OAAG,sBAAsB,IACxC,CACR,IACI,EAEP,MAAC,IAAI,IAAC,KAAK,EAAE,MAAM,CAAC,iBAAiB,aACnC,MAAC,IAAI,IAAC,KAAK,EAAE,MAAM,CAAC,gBAAgB,aAClC,MAAC,IAAI,IAAC,KAAK,EAAE,MAAM,CAAC,eAAe,4BACtB,KAAC,IAAI,IAAC,KAAK,EAAE,MAAM,CAAC,QAAQ,2BAAmB,IACrD,EACN,SAAS,IAAI,KAAC,OAAO,KAAG,IACpB,EACN,WAAW,IAAI,KAAC,IAAI,IAAC,KAAK,EAAE,MAAM,CAAC,mBAAmB,YAAG,WAAW,GAAQ,EAC5E,UAAU,CAAC,CAAC,CAAC,CACZ,KAAC,IAAI,IAAC,KAAK,EAAE,MAAM,CAAC,0BAA0B,YAC3C,iBAAiB,CAAC,CAAC,CAAC,CACnB,KAAC,sBAAsB,IACrB,GAAG,EAAE,eAAe,EACpB,QAAQ,EAAE,UAAU,CAAC,IAAI,EACzB,aAAa,EAAE,sBAAsB,GACrC,CACH,CAAC,CAAC,CAAC,CACF,KAAC,sBAAsB,IACrB,IAAI,EAAE,UAAU,CAAC,IAAI,EACrB,aAAa,EAAE,sBAAsB,GACrC,CACH,GACI,CACR,CAAC,CAAC,CAAC,CACF,KAAC,MAAM,IACL,KAAK,EAAC,kCAAkC,EACxC,iBAAiB,EAAC,mCAAmC,EACrD,YAAY,EAAC,mBAAmB,EAChC,OAAO,EAAE,SAAS,EAClB,IAAI,EAAC,IAAI,EACT,OAAO,EAAC,SAAS,EACjB,KAAK,EAAE,MAAM,CAAC,YAAY,EAC1B,QAAQ,EAAE,SAAS,IAAI,OAAO,CAAC,UAAU,CAAC,GAC1C,CACH,EACD,MAAC,IAAI,IAAC,OAAO,EAAC,UAAU,2FACqD,GAAG,EAC9E,KAAC,gBAAgB,IACf,iBAAiB,EAAC,MAAM,EACxB,OAAO,EAAC,UAAU,EAClB,OAAO,EAAE,GAAG,EAAE,CAAC,OAAO,CAAC,OAAO,CAAC,wBAAwB,CAAC,0CAGvC,IACd,IACF,EAEP,KAAC,IAAI,IAAC,KAAK,EAAE,MAAM,CAAC,MAAM,YACxB,MAAC,IAAI,IAAC,OAAO,EAAC,UAAU,qGAC+D,GAAG,EACxF,KAAC,gBAAgB,IACf,iBAAiB,EAAC,MAAM,EACxB,OAAO,EAAC,UAAU,EAClB,OAAO,EAAE,GAAG,EAAE,CAAC,OAAO,CAAC,OAAO,CAAC,wCAAwC,CAAC,+BAGvD,SAEd,GACF,IACY,CACtB,CAAA;AACH,CAAC;AAED,MAAM,wBAAwB,GAAG,QAAQ,CAAC,MAAM,CAAC;IAC/C,OAAO,EAAE,yDAAyD;IAClE,OAAO,EAAE,wCAAwC;CAClD,CAAC,CAAA;AAEF,MAAM,4BAA4B,GAAG,CACnC,OAAyB,EACzB,aAAqB,EACrB,YAAoB,EACpB,EAAE;IACF,OAAO,GAAG,aAAa,CAAC,SAAS,CAAC,CAAC,EAAE,GAAG,CAAC;;;EAGzC,OAAO;;;EAGP,aAAa;;;EAGb,YAAY;CACb,CAAA;AACD,CAAC,CAAA;AAED,MAAM,SAAS,GAAG,GAAG,EAAE;IACrB,MAAM,EAAE,MAAM,EAAE,GAAG,iBAAiB,EAAE,CAAA;IACtC,MAAM,EAAE,MAAM,EAAE,GAAG,QAAQ,EAAE,CAAA;IAC7B,OAAO,UAAU,CAAC,MAAM,CAAC;QACvB,SAAS,EAAE;YACT,OAAO,EAAE,EAAE;YACX,aAAa,EAAE,EAAE,GAAG,MAAM;YAC1B,GAAG,EAAE,EAAE;SACR;QACD,UAAU,EAAE;YACV,IAAI,EAAE,CAAC;SACR;QACD,WAAW,EAAE;YACX,KAAK,EAAE,MAAM,CAAC,yBAAyB;SACxC;QACD,kBAAkB,EAAE;YAClB,GAAG,EAAE,CAAC;SACP;QACD,UAAU,EAAE;YACV,QAAQ,EAAE,EAAE;YACZ,UAAU,EAAE,sBAAsB;YAClC,KAAK,EAAE,MAAM,CAAC,uBAAuB;SACtC;QACD,QAAQ,EAAE;YACR,KAAK,EAAE,MAAM,CAAC,eAAe;SAC9B;QACD,YAAY,EAAE;YACZ,aAAa,EAAE,KAAK;YACpB,UAAU,EAAE,QAAQ;YACpB,cAAc,EAAE,eAAe;YAC/B,WAAW,EAAE,CAAC;YACd,WAAW,EAAE,MAAM,CAAC,sBAAsB;YAC1C,YAAY,EAAE,CAAC;YACf,iBAAiB,EAAE,EAAE;YACrB,eAAe,EAAE,EAAE;YACnB,eAAe,EAAE,MAAM,CAAC,eAAe;YACvC,SAAS,EAAE,EAAE;SACd;QACD,UAAU,EAAE;YACV,QAAQ,EAAE,EAAE;YACZ,KAAK,EAAE,MAAM,CAAC,uBAAuB;YACrC,IAAI,EAAE,CAAC;SACR;QACD,iBAAiB,EAAE;YACjB,KAAK,EAAE,MAAM,CAAC,yBAAyB;SACxC;QACD,WAAW,EAAE;YACX,QAAQ,EAAE,EAAE;YACZ,KAAK,EAAE,MAAM,CAAC,yBAAyB;YACvC,UAAU,EAAE,CAAC;SACd;QACD,cAAc,EAAE;YACd,IAAI,EAAE,CAAC;YACP,eAAe,EAAE,MAAM,CAAC,eAAe;SACxC;QACD,WAAW,EAAE;YACX,aAAa,EAAE,KAAK;YACpB,UAAU,EAAE,QAAQ;YACpB,cAAc,EAAE,eAAe;YAC/B,OAAO,EAAE,EAAE;YACX,iBAAiB,EAAE,CAAC;YACpB,iBAAiB,EAAE,MAAM,CAAC,sBAAsB;SACjD;QACD,UAAU,EAAE;YACV,QAAQ,EAAE,EAAE;YACZ,UAAU,EAAE,sBAAsB;YAClC,KAAK,EAAE,MAAM,CAAC,uBAAuB;SACtC;QACD,iBAAiB,EAAE;YACjB,KAAK,EAAE,EAAE,EAAE,8CAA8C;SAC1D;QACD,YAAY,EAAE;YACZ,IAAI,EAAE,CAAC;SACR;QACD,WAAW,EAAE;YACX,aAAa,EAAE,KAAK;YACpB,UAAU,EAAE,QAAQ;YACpB,cAAc,EAAE,eAAe;YAC/B,iBAAiB,EAAE,EAAE;YACrB,eAAe,EAAE,EAAE;YACnB,iBAAiB,EAAE,CAAC;YACpB,iBAAiB,EAAE,MAAM,CAAC,sBAAsB;SACjD;QACD,eAAe,EAAE;YACf,QAAQ,EAAE,EAAE;YACZ,KAAK,EAAE,MAAM,CAAC,uBAAuB;YACrC,IAAI,EAAE,CAAC;SACR;QACD,cAAc,EAAE;YACd,QAAQ,EAAE,EAAE;YACZ,KAAK,EAAE,MAAM,CAAC,iBAAiB;SAChC;QACD,SAAS,EAAE;YACT,KAAK,EAAE,MAAM,CAAC,uBAAuB;YACrC,QAAQ,EAAE,EAAE;YACZ,iBAAiB,EAAE,KAAK;YACxB,SAAS,EAAE,GAAG;YACd,SAAS,EAAE,GAAG;YACd,WAAW,EAAE,CAAC;YACd,WAAW,EAAE,MAAM,CAAC,sBAAsB;YAC1C,YAAY,EAAE,CAAC;YACf,iBAAiB,EAAE,EAAE;YACrB,eAAe,EAAE,EAAE;YACnB,eAAe,EAAE,MAAM,CAAC,eAAe;SACxC;QACD,iBAAiB,EAAE;YACjB,GAAG,EAAE,CAAC;SACP;QACD,gBAAgB,EAAE;YAChB,aAAa,EAAE,KAAK;YACpB,GAAG,EAAE,CAAC;YACN,UAAU,EAAE,QAAQ;SACrB;QACD,eAAe,EAAE,EAAE,UAAU,EAAE,sBAAsB,EAAE;QACvD,QAAQ,EAAE,EAAE,UAAU,EAAE,QAAQ,EAAE,KAAK,EAAE,MAAM,CAAC,yBAAyB,EAAE;QAC3E,0BAA0B,EAAE;YAC1B,GAAG,EAAE,CAAC;SACP;QACD,mBAAmB,EAAE;YACnB,KAAK,EAAE,MAAM,CAAC,eAAe;SAC9B;QACD,YAAY,EAAE;YACZ,SAAS,EAAE,YAAY;SACxB;QACD,MAAM,EAAE,EAAE,GAAG,EAAE,CAAC,EAAE;QAClB,WAAW,EAAE;YACX,KAAK,EAAE,MAAM,CAAC,iBAAiB;YAC/B,QAAQ,EAAE,EAAE;SACb;QACD,YAAY,EAAE;YACZ,QAAQ,EAAE,EAAE;YACZ,YAAY,EAAE,CAAC;SAChB;QACD,eAAe,EAAE;YACf,QAAQ,EAAE,EAAE;YACZ,YAAY,EAAE,CAAC;SAChB;KACF,CAAC,CAAA;AACJ,CAAC,CAAA","sourcesContent":["import { useNavigation } from '@react-navigation/native'\nimport type {\n NativeStackNavigationOptions,\n NativeStackScreenProps,\n} from '@react-navigation/native-stack'\nimport { startsWith } from 'lodash'\nimport React, { useCallback, useState } from 'react'\nimport {\n View,\n StyleSheet,\n TextInput,\n Linking,\n ScrollView,\n TouchableOpacity,\n Platform,\n} from 'react-native'\nimport { useSafeAreaInsets } from 'react-native-safe-area-context'\nimport {\n Button,\n Spinner,\n Text,\n TextInlineButton,\n ImageAttachmentPreview,\n Icon,\n KeyboardScrollView,\n} from '../components'\nimport {\n composeOptions,\n HeaderDismissButton,\n useHeaderRight,\n withLeftClose,\n} from '../components/display/platform_modal_header_buttons'\nimport { VideoAttachmentPreview } from '../components/display/video_attachment_preview'\nimport { DefaultLoading } from '../components/page/loading'\nimport BlankState from '../components/primitive/blank_state_primitive'\nimport { SafeAreaModal } from '../components/safe_area_modal'\nimport { useTheme } from '../hooks'\nimport { useAppName } from '../hooks/use_app_name'\nimport { useReportBugAction } from '../hooks/use_report_bug_action'\nimport { useUploadClient } from '../hooks/use_upload_client'\nimport { ImagePicker, ImagePickerResult, platformFontWeightBold } from '../utils'\n\nconst MAX_DESCRIPTION_LENGTH = 2000\n\nenum BUG_TYPE_OPTIONS {\n Chat = 'Chat',\n FindMyChurch = 'Find my church',\n LoggingIn = 'Logging in',\n UsingGroups = 'Using groups (events, resources, members)',\n CheckingIn = 'Checking in',\n MakingADonation = 'Making a donation',\n RegisteringForAnEvent = 'Registering for an event',\n MyProfileAndSchedule = 'My profile and schedule',\n Directory = 'Directory',\n Other = 'Other',\n}\n\nexport const BugReportScreenOptions = ({\n navigation,\n}: NativeStackScreenProps<any>): NativeStackNavigationOptions =>\n composeOptions(\n { presentation: 'modal', title: 'Report a bug' },\n withLeftClose({ onPress: () => navigation.goBack() })\n )\n\ninterface Attachment {\n id: string\n name: string\n type: string\n}\n\nenum QualifiedMobileAppName {\n chat = 'Chat', // There is no app name for the mobile app\n churchcenter = 'Church Center App',\n services = 'Services Mobile',\n}\n\nenum DisplayableAppName {\n chat = 'Chat',\n churchcenter = 'Church Center',\n services = 'Services',\n}\n\nexport function BugReportScreen() {\n const styles = useStyles()\n const navigation = useNavigation()\n const name = useAppName()\n const appName = QualifiedMobileAppName[name]\n const [bugType, setBugType] = useState<BUG_TYPE_OPTIONS>(BUG_TYPE_OPTIONS.Chat)\n const [showBugTypePicker, setShowBugTypePicker] = useState(false)\n const [whatWereDoing, setWhatWereDoing] = useState('')\n const [whatExpected, setWhatExpected] = useState('')\n const uploadApi = useUploadClient()\n const [uploading, setUploading] = useState(false)\n const [attachment, setAttachment] = useState<Attachment | null>(null)\n const [uploadError, setUploadError] = useState<string | null>(null)\n const { mutate: createBugReport, status } = useReportBugAction()\n const formValid =\n bugType.trim().length > 0 &&\n whatWereDoing.trim().length > 0 &&\n whatExpected.trim().length > 0 &&\n status === 'idle' &&\n !uploading\n const [imagePreviewURI, setImagePreviewURI] = useState<string>('')\n const isImageAttachment = startsWith(attachment?.type, 'image/')\n\n const handleSubmit = useCallback(() => {\n const description = generateBugReportDescription(bugType, whatWereDoing, whatExpected)\n\n createBugReport({\n description,\n description_json: {\n bugType,\n whatWereDoing,\n whatExpected,\n appName: appName,\n },\n attachmentIds: attachment ? [attachment.id] : [],\n })\n }, [attachment, bugType, whatWereDoing, whatExpected, createBugReport, appName])\n\n const handleRemoveAttachment = useCallback(() => {\n setAttachment(null)\n setImagePreviewURI('')\n }, [])\n\n function uploadImagePickerResult(result: ImagePickerResult) {\n if (result.canceled || result.assets.length === 0) {\n setUploading(false)\n return\n }\n\n const asset = result.assets[0]\n\n uploadApi\n ?.uploadFile({\n uri: asset.uri,\n name: asset.fileName as string,\n type: asset.mimeType as string,\n })\n .then(uploadedResource => {\n setUploading(false)\n setImagePreviewURI(asset.uri)\n setAttachment({\n id: uploadedResource.id,\n name: asset.fileName || 'File',\n type: asset.mimeType as string,\n })\n })\n .catch(() => {\n setUploading(false)\n setUploadError(`Failed to upload attachment`)\n })\n }\n\n function pickImage() {\n setUploading(true)\n return ImagePicker.openImageLibraryAsync().then(result => uploadImagePickerResult(result))\n }\n\n useHeaderRight({\n icon: 'general.upArrow',\n accessibilityLabel: 'Submit',\n prominent: true,\n onPress: handleSubmit,\n disabled: !formValid,\n })\n\n if (status === 'pending') {\n return (\n <View style={[styles.container, styles.fullHeight]}>\n <DefaultLoading />\n </View>\n )\n }\n\n if (status === 'success') {\n return (\n <BlankState.Root>\n <BlankState.Imagery name=\"general.checkCircle\" style={styles.successIcon} />\n <BlankState.Content>\n <BlankState.Heading style={styles.successTitle}>Thank you!</BlankState.Heading>\n <BlankState.Text style={styles.successSubtitle}>\n We appreciate you taking the time to help improve {DisplayableAppName[name]}! We'll take\n a look at the issue you reported.\n </BlankState.Text>\n </BlankState.Content>\n <BlankState.Button\n title=\"Return to chat\"\n onPress={navigation.goBack}\n size=\"lg\"\n variant=\"fill\"\n />\n </BlankState.Root>\n )\n }\n\n if (status === 'error') {\n return (\n <View style={styles.container}>\n <Text>\n This is embarrassing, we can't submit your bug report right now. If you still need help or\n would like to submit this bug report another way please{' '}\n <TextInlineButton\n accessibilityRole=\"link\"\n onPress={() =>\n Linking.openURL('https://support.planningcenteronline.com/hc/en-us/requests/new')\n }\n >\n contact our help center\n </TextInlineButton>\n .\n </Text>\n <Button title=\"Return to chat\" onPress={navigation.goBack} variant=\"fill\" size=\"lg\" />\n </View>\n )\n }\n\n return (\n <KeyboardScrollView contentContainerStyle={styles.container}>\n <Text style={styles.description}>\n Thanks for helping us improve {DisplayableAppName[name]}. We won't be able to respond to\n your submission, but your feedback helps us improve the experience helps us improve the\n experience.\n </Text>\n\n <View style={styles.textInputContainer}>\n <Text style={styles.fieldLabel}>\n Where did you experience the issue? <Text style={styles.required}>*</Text>\n </Text>\n <TouchableOpacity style={styles.pickerButton} onPress={() => setShowBugTypePicker(true)}>\n <Text style={[styles.pickerText, !bugType && styles.pickerPlaceholder]}>{bugType}</Text>\n <Icon name=\"general.downChevron\" style={styles.pickerArrow} accessibilityElementsHidden />\n </TouchableOpacity>\n </View>\n\n <SafeAreaModal\n visible={showBugTypePicker}\n animationType=\"slide\"\n presentationStyle=\"pageSheet\"\n onRequestClose={() => setShowBugTypePicker(false)}\n >\n <View style={styles.modalContainer}>\n <View style={styles.modalHeader}>\n <HeaderDismissButton title=\"Cancel\" onPress={() => setShowBugTypePicker(false)} />\n <Text style={styles.modalTitle}>Select Bug Type</Text>\n <View style={styles.modalHeaderSpacer} />\n </View>\n <ScrollView style={styles.modalContent}>\n {Object.values(BUG_TYPE_OPTIONS).map(option => (\n <TouchableOpacity\n key={option}\n style={styles.modalOption}\n onPress={() => {\n setBugType(option)\n setShowBugTypePicker(false)\n }}\n >\n <Text style={styles.modalOptionText}>{option}</Text>\n {bugType === option && (\n <Icon\n name=\"general.check\"\n style={styles.modalCheckmark}\n accessibilityElementsHidden\n />\n )}\n </TouchableOpacity>\n ))}\n </ScrollView>\n </View>\n </SafeAreaModal>\n\n <View style={styles.textInputContainer}>\n <Text style={styles.fieldLabel}>\n What were you trying to do when you encountered the bug?{' '}\n <Text style={styles.required}>*</Text>\n </Text>\n <TextInput\n style={styles.textInput}\n multiline\n placeholder=\"Description\"\n value={whatWereDoing}\n onChangeText={setWhatWereDoing}\n maxLength={MAX_DESCRIPTION_LENGTH}\n />\n {whatWereDoing.length >= MAX_DESCRIPTION_LENGTH - 100 && (\n <Text variant=\"footnote\">\n {whatWereDoing.length}/{MAX_DESCRIPTION_LENGTH}\n </Text>\n )}\n </View>\n\n <View style={styles.textInputContainer}>\n <Text style={styles.fieldLabel}>\n What did you expect to happen? Please describe what actually happened.{' '}\n <Text style={styles.required}>*</Text>\n </Text>\n <TextInput\n style={styles.textInput}\n multiline\n placeholder=\"Description\"\n value={whatExpected}\n onChangeText={setWhatExpected}\n maxLength={MAX_DESCRIPTION_LENGTH}\n />\n {whatExpected.length >= MAX_DESCRIPTION_LENGTH - 100 && (\n <Text variant=\"footnote\">\n {whatExpected.length}/{MAX_DESCRIPTION_LENGTH}\n </Text>\n )}\n </View>\n\n <View style={styles.attachmentSection}>\n <View style={styles.attachmentHeader}>\n <Text style={styles.attachmentLabel}>\n Attachment <Text style={styles.subLabel}>(optional)</Text>\n </Text>\n {uploading && <Spinner />}\n </View>\n {uploadError && <Text style={styles.attachmentErrorText}>{uploadError}</Text>}\n {attachment ? (\n <View style={styles.attachmentPreviewContainer}>\n {isImageAttachment ? (\n <ImageAttachmentPreview\n uri={imagePreviewURI}\n fileName={attachment.name}\n onRemovePress={handleRemoveAttachment}\n />\n ) : (\n <VideoAttachmentPreview\n name={attachment.name}\n onRemovePress={handleRemoveAttachment}\n />\n )}\n </View>\n ) : (\n <Button\n title=\"Attach a screenshot or recording\"\n accessibilityHint=\"Opens your device's image gallery\"\n iconNameLeft=\"general.paperclip\"\n onPress={pickImage}\n size=\"sm\"\n variant=\"outline\"\n style={styles.attachButton}\n disabled={uploading || Boolean(attachment)}\n />\n )}\n <Text variant=\"footnote\">\n Screenshots and screen recordings help us reproduce and fix issues faster.{' '}\n <TextInlineButton\n accessibilityRole=\"link\"\n variant=\"footnote\"\n onPress={() => Linking.openURL(VIDEO_RECORDING_HELP_URL)}\n >\n How to record your screen\n </TextInlineButton>\n </Text>\n </View>\n\n <View style={styles.footer}>\n <Text variant=\"footnote\">\n For details on how we process your data and ensure its security, please refer to our{' '}\n <TextInlineButton\n accessibilityRole=\"link\"\n variant=\"footnote\"\n onPress={() => Linking.openURL('https://www.planningcenter.com/privacy')}\n >\n Privacy Policy\n </TextInlineButton>\n .\n </Text>\n </View>\n </KeyboardScrollView>\n )\n}\n\nconst VIDEO_RECORDING_HELP_URL = Platform.select({\n android: 'https://support.google.com/android/answer/9075928?hl=en',\n default: 'https://support.apple.com/en-us/102653',\n})\n\nconst generateBugReportDescription = (\n bugType: BUG_TYPE_OPTIONS,\n whatWereDoing: string,\n whatExpected: string\n) => {\n return `${whatWereDoing.substring(0, 100)}\n\n ## What kind of bug did you experience?\n${bugType}\n\n## What were you trying to do when you encountered the bug?\n${whatWereDoing}\n\n## What did you expect to happen? What actually happened?\n${whatExpected}\n`\n}\n\nconst useStyles = () => {\n const { bottom } = useSafeAreaInsets()\n const { colors } = useTheme()\n return StyleSheet.create({\n container: {\n padding: 16,\n paddingBottom: 16 + bottom,\n gap: 24,\n },\n fullHeight: {\n flex: 1,\n },\n description: {\n color: colors.textColorDefaultSecondary,\n },\n textInputContainer: {\n gap: 8,\n },\n fieldLabel: {\n fontSize: 16,\n fontWeight: platformFontWeightBold,\n color: colors.textColorDefaultPrimary,\n },\n required: {\n color: colors.statusErrorText,\n },\n pickerButton: {\n flexDirection: 'row',\n alignItems: 'center',\n justifyContent: 'space-between',\n borderWidth: 1,\n borderColor: colors.borderColorDefaultBase,\n borderRadius: 8,\n paddingHorizontal: 16,\n paddingVertical: 12,\n backgroundColor: colors.surfaceColor100,\n minHeight: 48,\n },\n pickerText: {\n fontSize: 16,\n color: colors.textColorDefaultPrimary,\n flex: 1,\n },\n pickerPlaceholder: {\n color: colors.textColorDefaultSecondary,\n },\n pickerArrow: {\n fontSize: 12,\n color: colors.iconColorDefaultSecondary,\n marginLeft: 8,\n },\n modalContainer: {\n flex: 1,\n backgroundColor: colors.surfaceColor100,\n },\n modalHeader: {\n flexDirection: 'row',\n alignItems: 'center',\n justifyContent: 'space-between',\n padding: 16,\n borderBottomWidth: 1,\n borderBottomColor: colors.borderColorDefaultBase,\n },\n modalTitle: {\n fontSize: 18,\n fontWeight: platformFontWeightBold,\n color: colors.textColorDefaultPrimary,\n },\n modalHeaderSpacer: {\n width: 50, // Same width as cancel button to center title\n },\n modalContent: {\n flex: 1,\n },\n modalOption: {\n flexDirection: 'row',\n alignItems: 'center',\n justifyContent: 'space-between',\n paddingHorizontal: 16,\n paddingVertical: 16,\n borderBottomWidth: 1,\n borderBottomColor: colors.borderColorDefaultBase,\n },\n modalOptionText: {\n fontSize: 16,\n color: colors.textColorDefaultPrimary,\n flex: 1,\n },\n modalCheckmark: {\n fontSize: 16,\n color: colors.statusSuccessIcon,\n },\n textInput: {\n color: colors.textColorDefaultPrimary,\n fontSize: 16,\n textAlignVertical: 'top',\n minHeight: 120,\n maxHeight: 200,\n borderWidth: 1,\n borderColor: colors.borderColorDefaultBase,\n borderRadius: 8,\n paddingHorizontal: 16,\n paddingVertical: 12,\n backgroundColor: colors.surfaceColor100,\n },\n attachmentSection: {\n gap: 8,\n },\n attachmentHeader: {\n flexDirection: 'row',\n gap: 4,\n alignItems: 'center',\n },\n attachmentLabel: { fontWeight: platformFontWeightBold },\n subLabel: { fontWeight: 'normal', color: colors.textColorDefaultSecondary },\n attachmentPreviewContainer: {\n gap: 4,\n },\n attachmentErrorText: {\n color: colors.statusErrorText,\n },\n attachButton: {\n alignSelf: 'flex-start',\n },\n footer: { gap: 8 },\n successIcon: {\n color: colors.statusSuccessIcon,\n fontSize: 48,\n },\n successTitle: {\n fontSize: 24,\n marginBottom: 4,\n },\n successSubtitle: {\n fontSize: 16,\n marginBottom: 4,\n },\n })\n}\n"]}
|
|
@@ -1,9 +1,9 @@
|
|
|
1
1
|
import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
|
|
2
2
|
import { useNavigation, StackActions } from '@react-navigation/native';
|
|
3
3
|
import { useCallback, useLayoutEffect, useMemo, useState } from 'react';
|
|
4
|
-
import { View, StyleSheet, TextInput
|
|
4
|
+
import { View, StyleSheet, TextInput } from 'react-native';
|
|
5
5
|
import { useSafeAreaInsets } from 'react-native-safe-area-context';
|
|
6
|
-
import { Spinner, Text,
|
|
6
|
+
import { Spinner, Text, KeyboardScrollView } from '../components';
|
|
7
7
|
import { composeOptions, useHeaderRight, withLeftClose, } from '../components/display/platform_modal_header_buttons';
|
|
8
8
|
import BlankState from '../components/primitive/blank_state_primitive';
|
|
9
9
|
import { useTheme } from '../hooks';
|
|
@@ -81,7 +81,7 @@ function MessageReportScreenContent({ message, conversation_id, }) {
|
|
|
81
81
|
if (status === 'error') {
|
|
82
82
|
return (_jsxs(BlankState.Root, { children: [_jsx(BlankState.Imagery, { name: "general.exclamationTriangle" }), _jsxs(BlankState.Content, { children: [_jsx(BlankState.Heading, { children: "Unable to submit report" }), _jsx(BlankState.Text, { children: "We were unable to report this message. Please try again." })] }), _jsx(BlankState.Button, { title: "Close", onPress: handleClose, size: "lg", variant: "outline" })] }));
|
|
83
83
|
}
|
|
84
|
-
return (
|
|
84
|
+
return (_jsxs(KeyboardScrollView, { contentContainerStyle: styles.container, children: [_jsx(Text, { style: styles.warningText, maxFontSizeMultiplier: 1.5, children: "Reporting this message will notify a church leader. The person you are reporting will not receive a notification from Church Center. If someone is in immediate danger, call local emergency services. Don't wait." }), _jsx(MessagePreview, { message: message }), _jsxs(View, { style: styles.reasonSection, children: [_jsxs(Text, { style: styles.fieldLabel, children: ["What best describes the problem? ", _jsx(Text, { style: styles.required, children: "*" })] }), _jsx(View, { style: styles.reasonListContainer, children: _jsx(ReportReasonList, { selectedReason: selectedReason, onReasonChange: handleReasonChange }) })] }), selectedReason === 'other' && (_jsxs(View, { style: styles.detailSection, children: [_jsxs(Text, { style: styles.fieldLabel, children: ["Please provide more details ", _jsx(Text, { style: styles.required, children: "*" })] }), _jsx(TextInput, { style: styles.textInput, multiline: true, placeholder: "Describe the issue...", value: reasonDetail, onChangeText: setReasonDetail, maxLength: MAX_DETAIL_LENGTH, accessibilityLabel: "Additional details", accessibilityHint: "Provide more information about why you're reporting this message" }), reasonDetail.length >= MAX_DETAIL_LENGTH - 100 && (_jsxs(Text, { variant: "footnote", children: [reasonDetail.length, "/", MAX_DETAIL_LENGTH] }))] }))] }));
|
|
85
85
|
}
|
|
86
86
|
const useStyles = () => {
|
|
87
87
|
const { bottom } = useSafeAreaInsets();
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"message_report_screen.js","sourceRoot":"","sources":["../../src/screens/message_report_screen.tsx"],"names":[],"mappings":"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","sourcesContent":["import { StaticScreenProps, useNavigation, StackActions } from '@react-navigation/native'\nimport type {\n NativeStackNavigationOptions,\n NativeStackScreenProps,\n} from '@react-navigation/native-stack'\nimport React, { useCallback, useLayoutEffect, useMemo, useState } from 'react'\nimport { View, StyleSheet, TextInput, ScrollView } from 'react-native'\nimport { useSafeAreaInsets } from 'react-native-safe-area-context'\nimport { Spinner, Text, KeyboardView } from '../components'\nimport {\n composeOptions,\n useHeaderRight,\n withLeftClose,\n} from '../components/display/platform_modal_header_buttons'\nimport BlankState from '../components/primitive/blank_state_primitive'\nimport { useTheme } from '../hooks'\nimport { useConversationMessages } from '../hooks/use_conversation_messages'\nimport { useReportMessage } from '../hooks/use_report_message'\nimport { MessageResource } from '../types'\nimport { MessageReportReason } from '../types/resources/message_report'\nimport { platformFontWeightBold } from '../utils'\nimport { MessagePreview } from './message_report/components/message_preview'\nimport { ReportReasonList } from './message_report/components/report_reason_list'\n\nconst MAX_DETAIL_LENGTH = 500\n\nexport const MessageReportScreenOptions = ({\n navigation,\n route,\n}: NativeStackScreenProps<any>): NativeStackNavigationOptions => {\n const handleClose = () =>\n navigation.dispatch(\n StackActions.popTo(\n 'Conversation',\n { conversation_id: route.params?.conversation_id },\n { merge: true }\n )\n )\n\n return composeOptions(\n { presentation: 'modal', title: 'Report message' },\n withLeftClose({ onPress: handleClose })\n )\n}\n\nexport type MessageReportScreenProps = StaticScreenProps<{\n conversation_id: number\n message_id: string\n}>\n\nexport function MessageReportScreen({ route }: MessageReportScreenProps) {\n const { conversation_id, message_id } = route.params\n\n const { messages } = useConversationMessages({ conversation_id }, { refetchOnMount: false })\n const message = messages.find(m => m.id === message_id)\n\n if (!message) return null\n\n return <MessageReportScreenContent message={message} conversation_id={conversation_id} />\n}\n\nfunction MessageReportScreenContent({\n message,\n conversation_id,\n}: {\n message: MessageResource\n conversation_id: number\n}) {\n const styles = useStyles()\n const navigation = useNavigation()\n const [selectedReason, setSelectedReason] = useState<MessageReportReason | null>(null)\n const [reasonDetail, setReasonDetail] = useState('')\n const { mutate: submitReport, status } = useReportMessage(conversation_id, message.id)\n\n const handleReasonChange = useCallback((reason: MessageReportReason) => {\n setSelectedReason(reason)\n\n if (reason !== 'other') {\n setReasonDetail('')\n }\n }, [])\n\n const isFormValid = useMemo(() => {\n if (selectedReason === null) return false\n\n if (selectedReason === 'other' && reasonDetail.trim().length === 0) {\n return false\n }\n\n if (status === 'pending') return false\n\n return true\n }, [selectedReason, reasonDetail, status])\n\n const handleSubmit = useCallback(() => {\n if (!isFormValid || !selectedReason) return\n\n submitReport({\n reason: selectedReason,\n reasonDetail: selectedReason === 'other' ? reasonDetail : undefined,\n })\n }, [isFormValid, selectedReason, reasonDetail, submitReport])\n\n const handleClose = useCallback(() => {\n navigation.dispatch(StackActions.popTo('Conversation', { conversation_id }, { merge: true }))\n }, [navigation, conversation_id])\n\n const formVisible = status !== 'pending' && status !== 'success'\n\n useHeaderRight({\n icon: 'general.upArrow',\n accessibilityLabel: 'Submit',\n prominent: true,\n onPress: handleSubmit,\n disabled: !isFormValid,\n enabled: formVisible,\n })\n\n useLayoutEffect(() => {\n if (formVisible) {\n navigation.setOptions({ headerTitle: 'Report message' })\n }\n }, [formVisible, navigation])\n\n if (status === 'pending') {\n return (\n <View style={styles.fullScreenContainer}>\n <Spinner />\n <Text style={styles.loadingText}>Submitting report...</Text>\n </View>\n )\n }\n\n if (status === 'success') {\n return (\n <View style={styles.fullScreenContainer}>\n <BlankState.Root>\n <BlankState.Imagery name=\"general.checkCircle\" style={styles.successIcon} />\n <BlankState.Content>\n <BlankState.Heading style={styles.successTitle}>Message reported</BlankState.Heading>\n <BlankState.Text style={styles.successSubtitle}>\n The message has been reported and a church leader will be contacted.\n </BlankState.Text>\n </BlankState.Content>\n <BlankState.Button title=\"Close\" onPress={handleClose} size=\"lg\" variant=\"fill\" />\n </BlankState.Root>\n </View>\n )\n }\n\n if (status === 'error') {\n return (\n <BlankState.Root>\n <BlankState.Imagery name=\"general.exclamationTriangle\" />\n <BlankState.Content>\n <BlankState.Heading>Unable to submit report</BlankState.Heading>\n <BlankState.Text>\n We were unable to report this message. Please try again.\n </BlankState.Text>\n </BlankState.Content>\n <BlankState.Button title=\"Close\" onPress={handleClose} size=\"lg\" variant=\"outline\" />\n </BlankState.Root>\n )\n }\n\n return (\n <KeyboardView>\n <ScrollView contentContainerStyle={styles.container}>\n <Text style={styles.warningText} maxFontSizeMultiplier={1.5}>\n Reporting this message will notify a church leader. The person you are reporting will not\n receive a notification from Church Center. If someone is in immediate danger, call local\n emergency services. Don't wait.\n </Text>\n\n <MessagePreview message={message} />\n\n <View style={styles.reasonSection}>\n <Text style={styles.fieldLabel}>\n What best describes the problem? <Text style={styles.required}>*</Text>\n </Text>\n\n <View style={styles.reasonListContainer}>\n <ReportReasonList selectedReason={selectedReason} onReasonChange={handleReasonChange} />\n </View>\n </View>\n\n {selectedReason === 'other' && (\n <View style={styles.detailSection}>\n <Text style={styles.fieldLabel}>\n Please provide more details <Text style={styles.required}>*</Text>\n </Text>\n <TextInput\n style={styles.textInput}\n multiline\n placeholder=\"Describe the issue...\"\n value={reasonDetail}\n onChangeText={setReasonDetail}\n maxLength={MAX_DETAIL_LENGTH}\n accessibilityLabel=\"Additional details\"\n accessibilityHint=\"Provide more information about why you're reporting this message\"\n />\n {reasonDetail.length >= MAX_DETAIL_LENGTH - 100 && (\n <Text variant=\"footnote\">\n {reasonDetail.length}/{MAX_DETAIL_LENGTH}\n </Text>\n )}\n </View>\n )}\n </ScrollView>\n </KeyboardView>\n )\n}\n\nconst useStyles = () => {\n const { bottom } = useSafeAreaInsets()\n const { colors } = useTheme()\n\n return StyleSheet.create({\n container: {\n padding: 16,\n paddingBottom: 16 + bottom,\n gap: 24,\n },\n fullHeight: {\n flex: 1,\n justifyContent: 'center',\n alignItems: 'center',\n },\n fullScreenContainer: {\n flex: 1,\n justifyContent: 'center',\n alignItems: 'center',\n backgroundColor: colors.surfaceColor100,\n },\n loadingText: {\n marginTop: 16,\n fontSize: 16,\n fontWeight: '600',\n color: colors.textColorDefaultPrimary,\n },\n warningText: {\n fontSize: 14,\n lineHeight: 20,\n color: colors.textColorDefaultSecondary,\n },\n reasonSection: {\n gap: 8,\n },\n fieldLabel: {\n fontSize: 16,\n fontWeight: platformFontWeightBold,\n color: colors.textColorDefaultPrimary,\n },\n required: {\n color: colors.statusErrorText,\n },\n reasonListContainer: {\n backgroundColor: colors.surfaceColor100,\n },\n detailSection: {\n gap: 8,\n },\n textInput: {\n color: colors.textColorDefaultPrimary,\n fontSize: 16,\n textAlignVertical: 'top',\n minHeight: 120,\n maxHeight: 200,\n borderWidth: 1,\n borderColor: colors.borderColorDefaultBase,\n borderRadius: 8,\n paddingHorizontal: 16,\n paddingVertical: 12,\n backgroundColor: colors.surfaceColor100,\n },\n successIcon: {\n color: colors.statusSuccessIcon,\n fontSize: 48,\n },\n successTitle: {\n fontSize: 24,\n marginBottom: 4,\n },\n successSubtitle: {\n fontSize: 16,\n marginBottom: 4,\n },\n })\n}\n"]}
|
|
1
|
+
{"version":3,"file":"message_report_screen.js","sourceRoot":"","sources":["../../src/screens/message_report_screen.tsx"],"names":[],"mappings":"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","sourcesContent":["import { StaticScreenProps, useNavigation, StackActions } from '@react-navigation/native'\nimport type {\n NativeStackNavigationOptions,\n NativeStackScreenProps,\n} from '@react-navigation/native-stack'\nimport React, { useCallback, useLayoutEffect, useMemo, useState } from 'react'\nimport { View, StyleSheet, TextInput } from 'react-native'\nimport { useSafeAreaInsets } from 'react-native-safe-area-context'\nimport { Spinner, Text, KeyboardScrollView } from '../components'\nimport {\n composeOptions,\n useHeaderRight,\n withLeftClose,\n} from '../components/display/platform_modal_header_buttons'\nimport BlankState from '../components/primitive/blank_state_primitive'\nimport { useTheme } from '../hooks'\nimport { useConversationMessages } from '../hooks/use_conversation_messages'\nimport { useReportMessage } from '../hooks/use_report_message'\nimport { MessageResource } from '../types'\nimport { MessageReportReason } from '../types/resources/message_report'\nimport { platformFontWeightBold } from '../utils'\nimport { MessagePreview } from './message_report/components/message_preview'\nimport { ReportReasonList } from './message_report/components/report_reason_list'\n\nconst MAX_DETAIL_LENGTH = 500\n\nexport const MessageReportScreenOptions = ({\n navigation,\n route,\n}: NativeStackScreenProps<any>): NativeStackNavigationOptions => {\n const handleClose = () =>\n navigation.dispatch(\n StackActions.popTo(\n 'Conversation',\n { conversation_id: route.params?.conversation_id },\n { merge: true }\n )\n )\n\n return composeOptions(\n { presentation: 'modal', title: 'Report message' },\n withLeftClose({ onPress: handleClose })\n )\n}\n\nexport type MessageReportScreenProps = StaticScreenProps<{\n conversation_id: number\n message_id: string\n}>\n\nexport function MessageReportScreen({ route }: MessageReportScreenProps) {\n const { conversation_id, message_id } = route.params\n\n const { messages } = useConversationMessages({ conversation_id }, { refetchOnMount: false })\n const message = messages.find(m => m.id === message_id)\n\n if (!message) return null\n\n return <MessageReportScreenContent message={message} conversation_id={conversation_id} />\n}\n\nfunction MessageReportScreenContent({\n message,\n conversation_id,\n}: {\n message: MessageResource\n conversation_id: number\n}) {\n const styles = useStyles()\n const navigation = useNavigation()\n const [selectedReason, setSelectedReason] = useState<MessageReportReason | null>(null)\n const [reasonDetail, setReasonDetail] = useState('')\n const { mutate: submitReport, status } = useReportMessage(conversation_id, message.id)\n\n const handleReasonChange = useCallback((reason: MessageReportReason) => {\n setSelectedReason(reason)\n\n if (reason !== 'other') {\n setReasonDetail('')\n }\n }, [])\n\n const isFormValid = useMemo(() => {\n if (selectedReason === null) return false\n\n if (selectedReason === 'other' && reasonDetail.trim().length === 0) {\n return false\n }\n\n if (status === 'pending') return false\n\n return true\n }, [selectedReason, reasonDetail, status])\n\n const handleSubmit = useCallback(() => {\n if (!isFormValid || !selectedReason) return\n\n submitReport({\n reason: selectedReason,\n reasonDetail: selectedReason === 'other' ? reasonDetail : undefined,\n })\n }, [isFormValid, selectedReason, reasonDetail, submitReport])\n\n const handleClose = useCallback(() => {\n navigation.dispatch(StackActions.popTo('Conversation', { conversation_id }, { merge: true }))\n }, [navigation, conversation_id])\n\n const formVisible = status !== 'pending' && status !== 'success'\n\n useHeaderRight({\n icon: 'general.upArrow',\n accessibilityLabel: 'Submit',\n prominent: true,\n onPress: handleSubmit,\n disabled: !isFormValid,\n enabled: formVisible,\n })\n\n useLayoutEffect(() => {\n if (formVisible) {\n navigation.setOptions({ headerTitle: 'Report message' })\n }\n }, [formVisible, navigation])\n\n if (status === 'pending') {\n return (\n <View style={styles.fullScreenContainer}>\n <Spinner />\n <Text style={styles.loadingText}>Submitting report...</Text>\n </View>\n )\n }\n\n if (status === 'success') {\n return (\n <View style={styles.fullScreenContainer}>\n <BlankState.Root>\n <BlankState.Imagery name=\"general.checkCircle\" style={styles.successIcon} />\n <BlankState.Content>\n <BlankState.Heading style={styles.successTitle}>Message reported</BlankState.Heading>\n <BlankState.Text style={styles.successSubtitle}>\n The message has been reported and a church leader will be contacted.\n </BlankState.Text>\n </BlankState.Content>\n <BlankState.Button title=\"Close\" onPress={handleClose} size=\"lg\" variant=\"fill\" />\n </BlankState.Root>\n </View>\n )\n }\n\n if (status === 'error') {\n return (\n <BlankState.Root>\n <BlankState.Imagery name=\"general.exclamationTriangle\" />\n <BlankState.Content>\n <BlankState.Heading>Unable to submit report</BlankState.Heading>\n <BlankState.Text>\n We were unable to report this message. Please try again.\n </BlankState.Text>\n </BlankState.Content>\n <BlankState.Button title=\"Close\" onPress={handleClose} size=\"lg\" variant=\"outline\" />\n </BlankState.Root>\n )\n }\n\n return (\n <KeyboardScrollView contentContainerStyle={styles.container}>\n <Text style={styles.warningText} maxFontSizeMultiplier={1.5}>\n Reporting this message will notify a church leader. The person you are reporting will not\n receive a notification from Church Center. If someone is in immediate danger, call local\n emergency services. Don't wait.\n </Text>\n\n <MessagePreview message={message} />\n\n <View style={styles.reasonSection}>\n <Text style={styles.fieldLabel}>\n What best describes the problem? <Text style={styles.required}>*</Text>\n </Text>\n\n <View style={styles.reasonListContainer}>\n <ReportReasonList selectedReason={selectedReason} onReasonChange={handleReasonChange} />\n </View>\n </View>\n\n {selectedReason === 'other' && (\n <View style={styles.detailSection}>\n <Text style={styles.fieldLabel}>\n Please provide more details <Text style={styles.required}>*</Text>\n </Text>\n <TextInput\n style={styles.textInput}\n multiline\n placeholder=\"Describe the issue...\"\n value={reasonDetail}\n onChangeText={setReasonDetail}\n maxLength={MAX_DETAIL_LENGTH}\n accessibilityLabel=\"Additional details\"\n accessibilityHint=\"Provide more information about why you're reporting this message\"\n />\n {reasonDetail.length >= MAX_DETAIL_LENGTH - 100 && (\n <Text variant=\"footnote\">\n {reasonDetail.length}/{MAX_DETAIL_LENGTH}\n </Text>\n )}\n </View>\n )}\n </KeyboardScrollView>\n )\n}\n\nconst useStyles = () => {\n const { bottom } = useSafeAreaInsets()\n const { colors } = useTheme()\n\n return StyleSheet.create({\n container: {\n padding: 16,\n paddingBottom: 16 + bottom,\n gap: 24,\n },\n fullHeight: {\n flex: 1,\n justifyContent: 'center',\n alignItems: 'center',\n },\n fullScreenContainer: {\n flex: 1,\n justifyContent: 'center',\n alignItems: 'center',\n backgroundColor: colors.surfaceColor100,\n },\n loadingText: {\n marginTop: 16,\n fontSize: 16,\n fontWeight: '600',\n color: colors.textColorDefaultPrimary,\n },\n warningText: {\n fontSize: 14,\n lineHeight: 20,\n color: colors.textColorDefaultSecondary,\n },\n reasonSection: {\n gap: 8,\n },\n fieldLabel: {\n fontSize: 16,\n fontWeight: platformFontWeightBold,\n color: colors.textColorDefaultPrimary,\n },\n required: {\n color: colors.statusErrorText,\n },\n reasonListContainer: {\n backgroundColor: colors.surfaceColor100,\n },\n detailSection: {\n gap: 8,\n },\n textInput: {\n color: colors.textColorDefaultPrimary,\n fontSize: 16,\n textAlignVertical: 'top',\n minHeight: 120,\n maxHeight: 200,\n borderWidth: 1,\n borderColor: colors.borderColorDefaultBase,\n borderRadius: 8,\n paddingHorizontal: 16,\n paddingVertical: 12,\n backgroundColor: colors.surfaceColor100,\n },\n successIcon: {\n color: colors.statusSuccessIcon,\n fontSize: 48,\n },\n successTitle: {\n fontSize: 24,\n marginBottom: 4,\n },\n successSubtitle: {\n fontSize: 16,\n marginBottom: 4,\n },\n })\n}\n"]}
|
|
@@ -5,10 +5,7 @@ export interface VideoPlayerProps {
|
|
|
5
5
|
};
|
|
6
6
|
aspectRatio?: number;
|
|
7
7
|
style?: StyleProp<ViewStyle>;
|
|
8
|
-
|
|
9
|
-
onFullscreenPlayerDidPresent?: () => void;
|
|
10
|
-
onFullscreenPlayerWillDismiss?: () => void;
|
|
11
|
-
onFullscreenPlayerDidDismiss?: () => void;
|
|
8
|
+
onFullscreenDismiss: () => void;
|
|
12
9
|
}
|
|
13
10
|
export interface VideoPlayerHandle {
|
|
14
11
|
play: () => void;
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"video.d.ts","sourceRoot":"","sources":["../../../src/utils/native_adapters/video.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,SAAS,EAAE,SAAS,EAAE,MAAM,cAAc,CAAA;AAEnD,MAAM,WAAW,gBAAgB;IAC/B,MAAM,EAAE;QAAE,GAAG,EAAE,MAAM,CAAA;KAAE,CAAA;IACvB,WAAW,CAAC,EAAE,MAAM,CAAA;IACpB,KAAK,CAAC,EAAE,SAAS,CAAC,SAAS,CAAC,CAAA;IAC5B,
|
|
1
|
+
{"version":3,"file":"video.d.ts","sourceRoot":"","sources":["../../../src/utils/native_adapters/video.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,SAAS,EAAE,SAAS,EAAE,MAAM,cAAc,CAAA;AAEnD,MAAM,WAAW,gBAAgB;IAC/B,MAAM,EAAE;QAAE,GAAG,EAAE,MAAM,CAAA;KAAE,CAAA;IACvB,WAAW,CAAC,EAAE,MAAM,CAAA;IACpB,KAAK,CAAC,EAAE,SAAS,CAAC,SAAS,CAAC,CAAA;IAC5B,mBAAmB,EAAE,MAAM,IAAI,CAAA;CAChC;AAED,MAAM,WAAW,iBAAiB;IAChC,IAAI,EAAE,MAAM,IAAI,CAAA;IAChB,KAAK,EAAE,MAAM,IAAI,CAAA;IACjB,uBAAuB,EAAE,MAAM,IAAI,CAAA;IACnC,iBAAiB,EAAE,MAAM,IAAI,CAAA;CAC9B;AAED,KAAK,WAAW,GAAG,KAAK,CAAC,yBAAyB,CAChD,gBAAgB,GAAG,KAAK,CAAC,aAAa,CAAC,iBAAiB,CAAC,CAC1D,CAAA;AAED,qBAAa,YAAY;IACvB,MAAM,EAAE,WAAW,CAAA;gBAEP,OAAO,EAAE,YAAY;CAGlC"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"video.js","sourceRoot":"","sources":["../../../src/utils/native_adapters/video.ts"],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"video.js","sourceRoot":"","sources":["../../../src/utils/native_adapters/video.ts"],"names":[],"mappings":"AAoBA,MAAM,OAAO,YAAY;IACvB,MAAM,CAAa;IAEnB,YAAY,OAAqB;QAC/B,IAAI,CAAC,MAAM,GAAG,OAAO,CAAC,MAAM,CAAA;IAC9B,CAAC;CACF","sourcesContent":["import { StyleProp, ViewStyle } from 'react-native'\n\nexport interface VideoPlayerProps {\n source: { uri: string }\n aspectRatio?: number\n style?: StyleProp<ViewStyle>\n onFullscreenDismiss: () => void\n}\n\nexport interface VideoPlayerHandle {\n play: () => void\n pause: () => void\n presentFullscreenPlayer: () => void\n dismissFullscreen: () => void\n}\n\ntype VideoPlayer = React.ForwardRefExoticComponent<\n VideoPlayerProps & React.RefAttributes<VideoPlayerHandle>\n>\n\nexport class VideoAdapter {\n Player: VideoPlayer\n\n constructor(methods: VideoAdapter) {\n this.Player = methods.Player\n }\n}\n"]}
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@planningcenter/chat-react-native",
|
|
3
|
-
"version": "
|
|
3
|
+
"version": "4.0.0-rc.1",
|
|
4
4
|
"description": "",
|
|
5
5
|
"repository": {
|
|
6
6
|
"type": "git",
|
|
@@ -78,5 +78,5 @@
|
|
|
78
78
|
"sf-symbols-typescript": "^2.2.0",
|
|
79
79
|
"typescript": "~6.0.3"
|
|
80
80
|
},
|
|
81
|
-
"gitHead": "
|
|
81
|
+
"gitHead": "0acb61429b82088f4d7ce9638f2e18cec4cdbfb1"
|
|
82
82
|
}
|
|
@@ -96,19 +96,16 @@ describe('VideoAttachment', () => {
|
|
|
96
96
|
expect(handle.play).toHaveBeenCalledTimes(1)
|
|
97
97
|
})
|
|
98
98
|
|
|
99
|
-
it
|
|
100
|
-
|
|
101
|
-
|
|
102
|
-
const { getByLabelText } = renderAttachment()
|
|
103
|
-
fireEvent.press(getByLabelText('Play Video'))
|
|
99
|
+
it('pauses and can be reopened after the player dismisses fullscreen', () => {
|
|
100
|
+
const { getByLabelText } = renderAttachment()
|
|
101
|
+
fireEvent.press(getByLabelText('Play Video'))
|
|
104
102
|
|
|
105
|
-
|
|
103
|
+
act(() => latestPlayerProps()?.onFullscreenDismiss())
|
|
106
104
|
|
|
107
|
-
|
|
105
|
+
expect(handle.pause).toHaveBeenCalledTimes(1)
|
|
108
106
|
|
|
109
|
-
|
|
107
|
+
fireEvent.press(getByLabelText('Play Video'))
|
|
110
108
|
|
|
111
|
-
|
|
112
|
-
|
|
113
|
-
)
|
|
109
|
+
expect(handle.presentFullscreenPlayer).toHaveBeenCalledTimes(2)
|
|
110
|
+
})
|
|
114
111
|
})
|
|
@@ -60,8 +60,7 @@ export function VideoAttachment({
|
|
|
60
60
|
source={{ uri: url }}
|
|
61
61
|
aspectRatio={width / height}
|
|
62
62
|
style={styles.video}
|
|
63
|
-
|
|
64
|
-
onFullscreenPlayerDidDismiss={closeVideo}
|
|
63
|
+
onFullscreenDismiss={closeVideo}
|
|
65
64
|
/>
|
|
66
65
|
{!isOpen && !isDeleting && (
|
|
67
66
|
<View style={styles.playContainer}>
|
|
@@ -23,6 +23,7 @@ export * from './text_button'
|
|
|
23
23
|
export * from './text_inline_button'
|
|
24
24
|
export * from './text'
|
|
25
25
|
export * from './toggle_button'
|
|
26
|
+
export * from './keyboard_scroll_view'
|
|
26
27
|
export * from './keyboard_view'
|
|
27
28
|
export * from './platform_modal_header_buttons'
|
|
28
29
|
export * from './pressable_row'
|
|
@@ -0,0 +1,54 @@
|
|
|
1
|
+
import React, { useCallback, useRef } from 'react'
|
|
2
|
+
import { Keyboard, ScrollView, ScrollViewProps, TextInput } from 'react-native'
|
|
3
|
+
import { KeyboardView } from './keyboard_view'
|
|
4
|
+
|
|
5
|
+
const FOCUSED_INPUT_BOTTOM_MARGIN = 32
|
|
6
|
+
|
|
7
|
+
type KeyboardScrollViewProps = Pick<ScrollViewProps, 'children' | 'contentContainerStyle'>
|
|
8
|
+
|
|
9
|
+
export function KeyboardScrollView({ children, contentContainerStyle }: KeyboardScrollViewProps) {
|
|
10
|
+
const scrollViewRef = useRef<ScrollView>(null)
|
|
11
|
+
|
|
12
|
+
const scrollFocusedInputIntoView = useCallback(() => {
|
|
13
|
+
const scrollView = scrollViewRef.current
|
|
14
|
+
const input = TextInput.State.currentlyFocusedInput()
|
|
15
|
+
if (!scrollView || !input) return
|
|
16
|
+
|
|
17
|
+
const nativeScrollView = scrollView.getNativeScrollRef()
|
|
18
|
+
const innerView = scrollView.getInnerViewRef()
|
|
19
|
+
if (!nativeScrollView || !innerView) return
|
|
20
|
+
|
|
21
|
+
nativeScrollView.measureInWindow((_scrollX, scrollTop, _scrollWidth, scrollHeight) => {
|
|
22
|
+
const keyboardTop = Keyboard.metrics()?.screenY
|
|
23
|
+
const scrollBottom = scrollTop + scrollHeight
|
|
24
|
+
const visibleBottom =
|
|
25
|
+
keyboardTop === undefined ? scrollBottom : Math.min(scrollBottom, keyboardTop)
|
|
26
|
+
const visibleHeight = visibleBottom - scrollTop
|
|
27
|
+
|
|
28
|
+
input.measureInWindow((_inputX, inputTop, _inputWidth, inputHeight) => {
|
|
29
|
+
const inputBottom = inputTop + inputHeight + FOCUSED_INPUT_BOTTOM_MARGIN
|
|
30
|
+
if (inputBottom <= visibleBottom) return
|
|
31
|
+
|
|
32
|
+
input.measureLayout(innerView, (_left, contentTop, _contentWidth, contentHeight) => {
|
|
33
|
+
scrollView.scrollTo({
|
|
34
|
+
y: contentTop + contentHeight + FOCUSED_INPUT_BOTTOM_MARGIN - visibleHeight,
|
|
35
|
+
animated: true,
|
|
36
|
+
})
|
|
37
|
+
})
|
|
38
|
+
})
|
|
39
|
+
})
|
|
40
|
+
}, [])
|
|
41
|
+
|
|
42
|
+
return (
|
|
43
|
+
<KeyboardView>
|
|
44
|
+
<ScrollView
|
|
45
|
+
ref={scrollViewRef}
|
|
46
|
+
contentContainerStyle={contentContainerStyle}
|
|
47
|
+
onLayout={scrollFocusedInputIntoView}
|
|
48
|
+
onContentSizeChange={scrollFocusedInputIntoView}
|
|
49
|
+
>
|
|
50
|
+
{children}
|
|
51
|
+
</ScrollView>
|
|
52
|
+
</KeyboardView>
|
|
53
|
+
)
|
|
54
|
+
}
|
|
@@ -22,7 +22,7 @@ import {
|
|
|
22
22
|
TextInlineButton,
|
|
23
23
|
ImageAttachmentPreview,
|
|
24
24
|
Icon,
|
|
25
|
-
|
|
25
|
+
KeyboardScrollView,
|
|
26
26
|
} from '../components'
|
|
27
27
|
import {
|
|
28
28
|
composeOptions,
|
|
@@ -217,166 +217,160 @@ export function BugReportScreen() {
|
|
|
217
217
|
}
|
|
218
218
|
|
|
219
219
|
return (
|
|
220
|
-
<
|
|
221
|
-
<
|
|
222
|
-
|
|
223
|
-
|
|
224
|
-
|
|
225
|
-
|
|
226
|
-
</Text>
|
|
220
|
+
<KeyboardScrollView contentContainerStyle={styles.container}>
|
|
221
|
+
<Text style={styles.description}>
|
|
222
|
+
Thanks for helping us improve {DisplayableAppName[name]}. We won't be able to respond to
|
|
223
|
+
your submission, but your feedback helps us improve the experience helps us improve the
|
|
224
|
+
experience.
|
|
225
|
+
</Text>
|
|
227
226
|
|
|
228
|
-
|
|
229
|
-
|
|
230
|
-
|
|
231
|
-
|
|
232
|
-
|
|
233
|
-
|
|
234
|
-
|
|
235
|
-
|
|
236
|
-
|
|
237
|
-
accessibilityElementsHidden
|
|
238
|
-
/>
|
|
239
|
-
</TouchableOpacity>
|
|
240
|
-
</View>
|
|
227
|
+
<View style={styles.textInputContainer}>
|
|
228
|
+
<Text style={styles.fieldLabel}>
|
|
229
|
+
Where did you experience the issue? <Text style={styles.required}>*</Text>
|
|
230
|
+
</Text>
|
|
231
|
+
<TouchableOpacity style={styles.pickerButton} onPress={() => setShowBugTypePicker(true)}>
|
|
232
|
+
<Text style={[styles.pickerText, !bugType && styles.pickerPlaceholder]}>{bugType}</Text>
|
|
233
|
+
<Icon name="general.downChevron" style={styles.pickerArrow} accessibilityElementsHidden />
|
|
234
|
+
</TouchableOpacity>
|
|
235
|
+
</View>
|
|
241
236
|
|
|
242
|
-
|
|
243
|
-
|
|
244
|
-
|
|
245
|
-
|
|
246
|
-
|
|
247
|
-
|
|
248
|
-
|
|
249
|
-
|
|
250
|
-
|
|
251
|
-
|
|
252
|
-
|
|
253
|
-
</View>
|
|
254
|
-
<ScrollView style={styles.modalContent}>
|
|
255
|
-
{Object.values(BUG_TYPE_OPTIONS).map(option => (
|
|
256
|
-
<TouchableOpacity
|
|
257
|
-
key={option}
|
|
258
|
-
style={styles.modalOption}
|
|
259
|
-
onPress={() => {
|
|
260
|
-
setBugType(option)
|
|
261
|
-
setShowBugTypePicker(false)
|
|
262
|
-
}}
|
|
263
|
-
>
|
|
264
|
-
<Text style={styles.modalOptionText}>{option}</Text>
|
|
265
|
-
{bugType === option && (
|
|
266
|
-
<Icon
|
|
267
|
-
name="general.check"
|
|
268
|
-
style={styles.modalCheckmark}
|
|
269
|
-
accessibilityElementsHidden
|
|
270
|
-
/>
|
|
271
|
-
)}
|
|
272
|
-
</TouchableOpacity>
|
|
273
|
-
))}
|
|
274
|
-
</ScrollView>
|
|
237
|
+
<SafeAreaModal
|
|
238
|
+
visible={showBugTypePicker}
|
|
239
|
+
animationType="slide"
|
|
240
|
+
presentationStyle="pageSheet"
|
|
241
|
+
onRequestClose={() => setShowBugTypePicker(false)}
|
|
242
|
+
>
|
|
243
|
+
<View style={styles.modalContainer}>
|
|
244
|
+
<View style={styles.modalHeader}>
|
|
245
|
+
<HeaderDismissButton title="Cancel" onPress={() => setShowBugTypePicker(false)} />
|
|
246
|
+
<Text style={styles.modalTitle}>Select Bug Type</Text>
|
|
247
|
+
<View style={styles.modalHeaderSpacer} />
|
|
275
248
|
</View>
|
|
276
|
-
|
|
277
|
-
|
|
278
|
-
|
|
279
|
-
|
|
280
|
-
|
|
281
|
-
|
|
282
|
-
|
|
283
|
-
|
|
284
|
-
|
|
285
|
-
|
|
286
|
-
|
|
287
|
-
|
|
288
|
-
|
|
289
|
-
|
|
290
|
-
|
|
291
|
-
|
|
292
|
-
|
|
293
|
-
|
|
294
|
-
|
|
295
|
-
|
|
249
|
+
<ScrollView style={styles.modalContent}>
|
|
250
|
+
{Object.values(BUG_TYPE_OPTIONS).map(option => (
|
|
251
|
+
<TouchableOpacity
|
|
252
|
+
key={option}
|
|
253
|
+
style={styles.modalOption}
|
|
254
|
+
onPress={() => {
|
|
255
|
+
setBugType(option)
|
|
256
|
+
setShowBugTypePicker(false)
|
|
257
|
+
}}
|
|
258
|
+
>
|
|
259
|
+
<Text style={styles.modalOptionText}>{option}</Text>
|
|
260
|
+
{bugType === option && (
|
|
261
|
+
<Icon
|
|
262
|
+
name="general.check"
|
|
263
|
+
style={styles.modalCheckmark}
|
|
264
|
+
accessibilityElementsHidden
|
|
265
|
+
/>
|
|
266
|
+
)}
|
|
267
|
+
</TouchableOpacity>
|
|
268
|
+
))}
|
|
269
|
+
</ScrollView>
|
|
296
270
|
</View>
|
|
271
|
+
</SafeAreaModal>
|
|
297
272
|
|
|
298
|
-
|
|
299
|
-
|
|
300
|
-
|
|
301
|
-
|
|
273
|
+
<View style={styles.textInputContainer}>
|
|
274
|
+
<Text style={styles.fieldLabel}>
|
|
275
|
+
What were you trying to do when you encountered the bug?{' '}
|
|
276
|
+
<Text style={styles.required}>*</Text>
|
|
277
|
+
</Text>
|
|
278
|
+
<TextInput
|
|
279
|
+
style={styles.textInput}
|
|
280
|
+
multiline
|
|
281
|
+
placeholder="Description"
|
|
282
|
+
value={whatWereDoing}
|
|
283
|
+
onChangeText={setWhatWereDoing}
|
|
284
|
+
maxLength={MAX_DESCRIPTION_LENGTH}
|
|
285
|
+
/>
|
|
286
|
+
{whatWereDoing.length >= MAX_DESCRIPTION_LENGTH - 100 && (
|
|
287
|
+
<Text variant="footnote">
|
|
288
|
+
{whatWereDoing.length}/{MAX_DESCRIPTION_LENGTH}
|
|
302
289
|
</Text>
|
|
303
|
-
|
|
304
|
-
|
|
305
|
-
multiline
|
|
306
|
-
placeholder="Description"
|
|
307
|
-
value={whatExpected}
|
|
308
|
-
onChangeText={setWhatExpected}
|
|
309
|
-
maxLength={MAX_DESCRIPTION_LENGTH}
|
|
310
|
-
/>
|
|
311
|
-
{whatExpected.length >= MAX_DESCRIPTION_LENGTH - 100 && (
|
|
312
|
-
<Text variant="footnote">
|
|
313
|
-
{whatExpected.length}/{MAX_DESCRIPTION_LENGTH}
|
|
314
|
-
</Text>
|
|
315
|
-
)}
|
|
316
|
-
</View>
|
|
290
|
+
)}
|
|
291
|
+
</View>
|
|
317
292
|
|
|
318
|
-
|
|
319
|
-
|
|
320
|
-
|
|
321
|
-
|
|
322
|
-
|
|
323
|
-
|
|
324
|
-
|
|
325
|
-
|
|
326
|
-
|
|
327
|
-
|
|
328
|
-
|
|
329
|
-
|
|
330
|
-
|
|
331
|
-
|
|
332
|
-
onRemovePress={handleRemoveAttachment}
|
|
333
|
-
/>
|
|
334
|
-
) : (
|
|
335
|
-
<VideoAttachmentPreview
|
|
336
|
-
name={attachment.name}
|
|
337
|
-
onRemovePress={handleRemoveAttachment}
|
|
338
|
-
/>
|
|
339
|
-
)}
|
|
340
|
-
</View>
|
|
341
|
-
) : (
|
|
342
|
-
<Button
|
|
343
|
-
title="Attach a screenshot or recording"
|
|
344
|
-
accessibilityHint="Opens your device's image gallery"
|
|
345
|
-
iconNameLeft="general.paperclip"
|
|
346
|
-
onPress={pickImage}
|
|
347
|
-
size="sm"
|
|
348
|
-
variant="outline"
|
|
349
|
-
style={styles.attachButton}
|
|
350
|
-
disabled={uploading || Boolean(attachment)}
|
|
351
|
-
/>
|
|
352
|
-
)}
|
|
293
|
+
<View style={styles.textInputContainer}>
|
|
294
|
+
<Text style={styles.fieldLabel}>
|
|
295
|
+
What did you expect to happen? Please describe what actually happened.{' '}
|
|
296
|
+
<Text style={styles.required}>*</Text>
|
|
297
|
+
</Text>
|
|
298
|
+
<TextInput
|
|
299
|
+
style={styles.textInput}
|
|
300
|
+
multiline
|
|
301
|
+
placeholder="Description"
|
|
302
|
+
value={whatExpected}
|
|
303
|
+
onChangeText={setWhatExpected}
|
|
304
|
+
maxLength={MAX_DESCRIPTION_LENGTH}
|
|
305
|
+
/>
|
|
306
|
+
{whatExpected.length >= MAX_DESCRIPTION_LENGTH - 100 && (
|
|
353
307
|
<Text variant="footnote">
|
|
354
|
-
|
|
355
|
-
<TextInlineButton
|
|
356
|
-
accessibilityRole="link"
|
|
357
|
-
variant="footnote"
|
|
358
|
-
onPress={() => Linking.openURL(VIDEO_RECORDING_HELP_URL)}
|
|
359
|
-
>
|
|
360
|
-
How to record your screen
|
|
361
|
-
</TextInlineButton>
|
|
308
|
+
{whatExpected.length}/{MAX_DESCRIPTION_LENGTH}
|
|
362
309
|
</Text>
|
|
363
|
-
|
|
310
|
+
)}
|
|
311
|
+
</View>
|
|
364
312
|
|
|
365
|
-
|
|
366
|
-
|
|
367
|
-
|
|
368
|
-
<
|
|
369
|
-
accessibilityRole="link"
|
|
370
|
-
variant="footnote"
|
|
371
|
-
onPress={() => Linking.openURL('https://www.planningcenter.com/privacy')}
|
|
372
|
-
>
|
|
373
|
-
Privacy Policy
|
|
374
|
-
</TextInlineButton>
|
|
375
|
-
.
|
|
313
|
+
<View style={styles.attachmentSection}>
|
|
314
|
+
<View style={styles.attachmentHeader}>
|
|
315
|
+
<Text style={styles.attachmentLabel}>
|
|
316
|
+
Attachment <Text style={styles.subLabel}>(optional)</Text>
|
|
376
317
|
</Text>
|
|
318
|
+
{uploading && <Spinner />}
|
|
377
319
|
</View>
|
|
378
|
-
|
|
379
|
-
|
|
320
|
+
{uploadError && <Text style={styles.attachmentErrorText}>{uploadError}</Text>}
|
|
321
|
+
{attachment ? (
|
|
322
|
+
<View style={styles.attachmentPreviewContainer}>
|
|
323
|
+
{isImageAttachment ? (
|
|
324
|
+
<ImageAttachmentPreview
|
|
325
|
+
uri={imagePreviewURI}
|
|
326
|
+
fileName={attachment.name}
|
|
327
|
+
onRemovePress={handleRemoveAttachment}
|
|
328
|
+
/>
|
|
329
|
+
) : (
|
|
330
|
+
<VideoAttachmentPreview
|
|
331
|
+
name={attachment.name}
|
|
332
|
+
onRemovePress={handleRemoveAttachment}
|
|
333
|
+
/>
|
|
334
|
+
)}
|
|
335
|
+
</View>
|
|
336
|
+
) : (
|
|
337
|
+
<Button
|
|
338
|
+
title="Attach a screenshot or recording"
|
|
339
|
+
accessibilityHint="Opens your device's image gallery"
|
|
340
|
+
iconNameLeft="general.paperclip"
|
|
341
|
+
onPress={pickImage}
|
|
342
|
+
size="sm"
|
|
343
|
+
variant="outline"
|
|
344
|
+
style={styles.attachButton}
|
|
345
|
+
disabled={uploading || Boolean(attachment)}
|
|
346
|
+
/>
|
|
347
|
+
)}
|
|
348
|
+
<Text variant="footnote">
|
|
349
|
+
Screenshots and screen recordings help us reproduce and fix issues faster.{' '}
|
|
350
|
+
<TextInlineButton
|
|
351
|
+
accessibilityRole="link"
|
|
352
|
+
variant="footnote"
|
|
353
|
+
onPress={() => Linking.openURL(VIDEO_RECORDING_HELP_URL)}
|
|
354
|
+
>
|
|
355
|
+
How to record your screen
|
|
356
|
+
</TextInlineButton>
|
|
357
|
+
</Text>
|
|
358
|
+
</View>
|
|
359
|
+
|
|
360
|
+
<View style={styles.footer}>
|
|
361
|
+
<Text variant="footnote">
|
|
362
|
+
For details on how we process your data and ensure its security, please refer to our{' '}
|
|
363
|
+
<TextInlineButton
|
|
364
|
+
accessibilityRole="link"
|
|
365
|
+
variant="footnote"
|
|
366
|
+
onPress={() => Linking.openURL('https://www.planningcenter.com/privacy')}
|
|
367
|
+
>
|
|
368
|
+
Privacy Policy
|
|
369
|
+
</TextInlineButton>
|
|
370
|
+
.
|
|
371
|
+
</Text>
|
|
372
|
+
</View>
|
|
373
|
+
</KeyboardScrollView>
|
|
380
374
|
)
|
|
381
375
|
}
|
|
382
376
|
|
|
@@ -4,9 +4,9 @@ import type {
|
|
|
4
4
|
NativeStackScreenProps,
|
|
5
5
|
} from '@react-navigation/native-stack'
|
|
6
6
|
import React, { useCallback, useLayoutEffect, useMemo, useState } from 'react'
|
|
7
|
-
import { View, StyleSheet, TextInput
|
|
7
|
+
import { View, StyleSheet, TextInput } from 'react-native'
|
|
8
8
|
import { useSafeAreaInsets } from 'react-native-safe-area-context'
|
|
9
|
-
import { Spinner, Text,
|
|
9
|
+
import { Spinner, Text, KeyboardScrollView } from '../components'
|
|
10
10
|
import {
|
|
11
11
|
composeOptions,
|
|
12
12
|
useHeaderRight,
|
|
@@ -164,50 +164,48 @@ function MessageReportScreenContent({
|
|
|
164
164
|
}
|
|
165
165
|
|
|
166
166
|
return (
|
|
167
|
-
<
|
|
168
|
-
<
|
|
169
|
-
|
|
170
|
-
|
|
171
|
-
|
|
172
|
-
|
|
173
|
-
</Text>
|
|
167
|
+
<KeyboardScrollView contentContainerStyle={styles.container}>
|
|
168
|
+
<Text style={styles.warningText} maxFontSizeMultiplier={1.5}>
|
|
169
|
+
Reporting this message will notify a church leader. The person you are reporting will not
|
|
170
|
+
receive a notification from Church Center. If someone is in immediate danger, call local
|
|
171
|
+
emergency services. Don't wait.
|
|
172
|
+
</Text>
|
|
174
173
|
|
|
175
|
-
|
|
174
|
+
<MessagePreview message={message} />
|
|
176
175
|
|
|
177
|
-
|
|
178
|
-
|
|
179
|
-
|
|
180
|
-
|
|
176
|
+
<View style={styles.reasonSection}>
|
|
177
|
+
<Text style={styles.fieldLabel}>
|
|
178
|
+
What best describes the problem? <Text style={styles.required}>*</Text>
|
|
179
|
+
</Text>
|
|
181
180
|
|
|
182
|
-
|
|
183
|
-
|
|
184
|
-
</View>
|
|
181
|
+
<View style={styles.reasonListContainer}>
|
|
182
|
+
<ReportReasonList selectedReason={selectedReason} onReasonChange={handleReasonChange} />
|
|
185
183
|
</View>
|
|
184
|
+
</View>
|
|
186
185
|
|
|
187
|
-
|
|
188
|
-
|
|
189
|
-
|
|
190
|
-
|
|
186
|
+
{selectedReason === 'other' && (
|
|
187
|
+
<View style={styles.detailSection}>
|
|
188
|
+
<Text style={styles.fieldLabel}>
|
|
189
|
+
Please provide more details <Text style={styles.required}>*</Text>
|
|
190
|
+
</Text>
|
|
191
|
+
<TextInput
|
|
192
|
+
style={styles.textInput}
|
|
193
|
+
multiline
|
|
194
|
+
placeholder="Describe the issue..."
|
|
195
|
+
value={reasonDetail}
|
|
196
|
+
onChangeText={setReasonDetail}
|
|
197
|
+
maxLength={MAX_DETAIL_LENGTH}
|
|
198
|
+
accessibilityLabel="Additional details"
|
|
199
|
+
accessibilityHint="Provide more information about why you're reporting this message"
|
|
200
|
+
/>
|
|
201
|
+
{reasonDetail.length >= MAX_DETAIL_LENGTH - 100 && (
|
|
202
|
+
<Text variant="footnote">
|
|
203
|
+
{reasonDetail.length}/{MAX_DETAIL_LENGTH}
|
|
191
204
|
</Text>
|
|
192
|
-
|
|
193
|
-
|
|
194
|
-
|
|
195
|
-
|
|
196
|
-
value={reasonDetail}
|
|
197
|
-
onChangeText={setReasonDetail}
|
|
198
|
-
maxLength={MAX_DETAIL_LENGTH}
|
|
199
|
-
accessibilityLabel="Additional details"
|
|
200
|
-
accessibilityHint="Provide more information about why you're reporting this message"
|
|
201
|
-
/>
|
|
202
|
-
{reasonDetail.length >= MAX_DETAIL_LENGTH - 100 && (
|
|
203
|
-
<Text variant="footnote">
|
|
204
|
-
{reasonDetail.length}/{MAX_DETAIL_LENGTH}
|
|
205
|
-
</Text>
|
|
206
|
-
)}
|
|
207
|
-
</View>
|
|
208
|
-
)}
|
|
209
|
-
</ScrollView>
|
|
210
|
-
</KeyboardView>
|
|
205
|
+
)}
|
|
206
|
+
</View>
|
|
207
|
+
)}
|
|
208
|
+
</KeyboardScrollView>
|
|
211
209
|
)
|
|
212
210
|
}
|
|
213
211
|
|
|
@@ -4,10 +4,7 @@ export interface VideoPlayerProps {
|
|
|
4
4
|
source: { uri: string }
|
|
5
5
|
aspectRatio?: number
|
|
6
6
|
style?: StyleProp<ViewStyle>
|
|
7
|
-
|
|
8
|
-
onFullscreenPlayerDidPresent?: () => void
|
|
9
|
-
onFullscreenPlayerWillDismiss?: () => void
|
|
10
|
-
onFullscreenPlayerDidDismiss?: () => void
|
|
7
|
+
onFullscreenDismiss: () => void
|
|
11
8
|
}
|
|
12
9
|
|
|
13
10
|
export interface VideoPlayerHandle {
|