@planningcenter/chat-react-native 4.4.1-qa-staging.15 → 4.4.1-qa-staging.17
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/build/components/conversation/reply_shadow_message.js +120 -104
- package/build/components/conversation/reply_shadow_message.js.map +1 -1
- package/build/components/conversations/conversations.d.ts.map +1 -1
- package/build/components/conversations/conversations.js +55 -39
- package/build/components/conversations/conversations.js.map +1 -1
- package/build/components/conversations/conversations_blank_state.d.ts.map +1 -1
- package/build/components/conversations/conversations_blank_state.js +55 -12
- package/build/components/conversations/conversations_blank_state.js.map +1 -1
- package/build/components/conversations/filtered_results_footer.d.ts +2 -0
- package/build/components/conversations/filtered_results_footer.d.ts.map +1 -0
- package/build/components/conversations/filtered_results_footer.js +77 -0
- package/build/components/conversations/filtered_results_footer.js.map +1 -0
- package/build/hooks/use_clear_conversation_filters.d.ts +2 -0
- package/build/hooks/use_clear_conversation_filters.d.ts.map +1 -0
- package/build/hooks/use_clear_conversation_filters.js +24 -0
- package/build/hooks/use_clear_conversation_filters.js.map +1 -0
- package/build/hooks/use_reduce_motion.d.ts.map +1 -1
- package/build/hooks/use_reduce_motion.js +2 -1
- package/build/hooks/use_reduce_motion.js.map +1 -1
- package/build/screens/conversation_filters/components/conversation_filters.d.ts.map +1 -1
- package/build/screens/conversation_filters/components/conversation_filters.js +8 -5
- package/build/screens/conversation_filters/components/conversation_filters.js.map +1 -1
- package/build/screens/conversation_filters_screen.d.ts.map +1 -1
- package/build/screens/conversation_filters_screen.js +47 -42
- package/build/screens/conversation_filters_screen.js.map +1 -1
- package/package.json +3 -3
- package/src/__tests__/screens/conversation_filters/components/conversation_filters.test.tsx +129 -0
- package/src/__tests__/screens/conversation_new/components/services_form.test.tsx +1 -0
- package/src/components/conversation/reply_shadow_message.tsx +1 -2
- package/src/components/conversations/__tests__/conversations_blank_state.test.tsx +72 -0
- package/src/components/conversations/conversations.tsx +13 -2
- package/src/components/conversations/conversations_blank_state.tsx +21 -0
- package/src/components/conversations/filtered_results_footer.tsx +38 -0
- package/src/hooks/__tests__/use_reduce_motion.test.tsx +13 -1
- package/src/hooks/use_clear_conversation_filters.ts +15 -0
- package/src/hooks/use_reduce_motion.ts +2 -1
- package/src/screens/conversation_filters/components/conversation_filters.tsx +8 -5
- package/src/screens/conversation_filters_screen.tsx +5 -1
|
@@ -7,6 +7,7 @@ import React, { useCallback } from 'react';
|
|
|
7
7
|
import { Platform, StyleSheet, useWindowDimensions, View } from 'react-native';
|
|
8
8
|
import { useSafeAreaInsets } from 'react-native-safe-area-context';
|
|
9
9
|
import FormSheet, { getFormSheetScreenOptions } from '../components/primitive/form_sheet';
|
|
10
|
+
import { useFilterDropdownEnabled } from '../hooks/use_filter_dropdown_enabled';
|
|
10
11
|
import { ConversationFilters } from './conversation_filters/components/conversation_filters';
|
|
11
12
|
import { FilterProvider, useFilterContext } from './conversation_filters/context/conversation_filter_context';
|
|
12
13
|
import { GroupFilters } from './conversation_filters/group_filters';
|
|
@@ -100,13 +101,14 @@ export const ConversationFiltersScreen = _props => {
|
|
|
100
101
|
return t2;
|
|
101
102
|
};
|
|
102
103
|
const FormSheetHeaderWithContext = () => {
|
|
103
|
-
const $ = _c(
|
|
104
|
+
const $ = _c(19);
|
|
104
105
|
const {
|
|
105
106
|
resetFilter,
|
|
106
107
|
applyFilters,
|
|
107
108
|
setFormSheetHeaderHeight
|
|
108
109
|
} = useFilterContext();
|
|
109
110
|
const route = useRoute();
|
|
111
|
+
const filterDropdownEnabled = useFilterDropdownEnabled();
|
|
110
112
|
const styles = useStyles();
|
|
111
113
|
let t0;
|
|
112
114
|
if ($[0] !== setFormSheetHeaderHeight) {
|
|
@@ -119,74 +121,77 @@ const FormSheetHeaderWithContext = () => {
|
|
|
119
121
|
t0 = $[1];
|
|
120
122
|
}
|
|
121
123
|
const handleFormSheetHeaderLayout = t0;
|
|
122
|
-
|
|
123
|
-
|
|
124
|
-
|
|
125
|
-
|
|
124
|
+
const t1 = filterDropdownEnabled ? "More filters" : "Filters";
|
|
125
|
+
let t2;
|
|
126
|
+
if ($[2] !== t1) {
|
|
127
|
+
t2 = /*#__PURE__*/_jsx(FormSheet.HeaderTitle, {
|
|
128
|
+
children: t1
|
|
126
129
|
});
|
|
127
130
|
$[2] = t1;
|
|
131
|
+
$[3] = t2;
|
|
128
132
|
} else {
|
|
129
|
-
|
|
133
|
+
t2 = $[3];
|
|
130
134
|
}
|
|
131
|
-
let
|
|
132
|
-
if ($[
|
|
133
|
-
|
|
135
|
+
let t3;
|
|
136
|
+
if ($[4] !== resetFilter) {
|
|
137
|
+
t3 = /*#__PURE__*/_jsx(FormSheet.HeaderTextButton, {
|
|
134
138
|
onPress: resetFilter,
|
|
135
139
|
children: "Reset"
|
|
136
140
|
});
|
|
137
|
-
$[
|
|
138
|
-
$[
|
|
141
|
+
$[4] = resetFilter;
|
|
142
|
+
$[5] = t3;
|
|
139
143
|
} else {
|
|
140
|
-
|
|
144
|
+
t3 = $[5];
|
|
141
145
|
}
|
|
142
|
-
let
|
|
143
|
-
if ($[
|
|
144
|
-
|
|
146
|
+
let t4;
|
|
147
|
+
if ($[6] !== applyFilters || $[7] !== route.params) {
|
|
148
|
+
t4 = /*#__PURE__*/_jsx(FormSheet.HeaderButton, {
|
|
145
149
|
title: "Apply",
|
|
146
150
|
onPress: () => applyFilters(route.params)
|
|
147
151
|
});
|
|
148
|
-
$[
|
|
149
|
-
$[
|
|
150
|
-
$[
|
|
152
|
+
$[6] = applyFilters;
|
|
153
|
+
$[7] = route.params;
|
|
154
|
+
$[8] = t4;
|
|
151
155
|
} else {
|
|
152
|
-
|
|
156
|
+
t4 = $[8];
|
|
153
157
|
}
|
|
154
|
-
let
|
|
155
|
-
if ($[
|
|
156
|
-
|
|
157
|
-
children: [
|
|
158
|
+
let t5;
|
|
159
|
+
if ($[9] !== t3 || $[10] !== t4) {
|
|
160
|
+
t5 = /*#__PURE__*/_jsxs(FormSheet.HeaderActions, {
|
|
161
|
+
children: [t3, t4]
|
|
158
162
|
});
|
|
159
|
-
$[8] = t2;
|
|
160
163
|
$[9] = t3;
|
|
161
164
|
$[10] = t4;
|
|
165
|
+
$[11] = t5;
|
|
162
166
|
} else {
|
|
163
|
-
|
|
167
|
+
t5 = $[11];
|
|
164
168
|
}
|
|
165
|
-
let
|
|
166
|
-
if ($[
|
|
167
|
-
|
|
169
|
+
let t6;
|
|
170
|
+
if ($[12] !== styles.header || $[13] !== t2 || $[14] !== t5) {
|
|
171
|
+
t6 = /*#__PURE__*/_jsxs(FormSheet.Header, {
|
|
168
172
|
style: styles.header,
|
|
169
|
-
children: [
|
|
173
|
+
children: [t2, t5]
|
|
170
174
|
});
|
|
171
|
-
$[
|
|
172
|
-
$[
|
|
173
|
-
$[
|
|
175
|
+
$[12] = styles.header;
|
|
176
|
+
$[13] = t2;
|
|
177
|
+
$[14] = t5;
|
|
178
|
+
$[15] = t6;
|
|
174
179
|
} else {
|
|
175
|
-
|
|
180
|
+
t6 = $[15];
|
|
176
181
|
}
|
|
177
|
-
let
|
|
178
|
-
if ($[
|
|
179
|
-
|
|
182
|
+
let t7;
|
|
183
|
+
if ($[16] !== handleFormSheetHeaderLayout || $[17] !== t6) {
|
|
184
|
+
t7 = /*#__PURE__*/_jsx(View, {
|
|
180
185
|
onLayout: handleFormSheetHeaderLayout,
|
|
181
|
-
children:
|
|
186
|
+
children: t6
|
|
182
187
|
});
|
|
183
|
-
$[
|
|
184
|
-
$[
|
|
185
|
-
$[
|
|
188
|
+
$[16] = handleFormSheetHeaderLayout;
|
|
189
|
+
$[17] = t6;
|
|
190
|
+
$[18] = t7;
|
|
186
191
|
} else {
|
|
187
|
-
|
|
192
|
+
t7 = $[18];
|
|
188
193
|
}
|
|
189
|
-
return
|
|
194
|
+
return t7;
|
|
190
195
|
};
|
|
191
196
|
const useStyles = () => {
|
|
192
197
|
const $ = _c(4);
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"conversation_filters_screen.js","names":["useHeaderHeight","ReactNavigationNative","useRoute","createNativeStackNavigator","React","useCallback","Platform","StyleSheet","useWindowDimensions","View","useSafeAreaInsets","FormSheet","getFormSheetScreenOptions","ConversationFilters","FilterProvider","useFilterContext","GroupFilters","TeamFilters","jsx","_jsx","jsxs","_jsxs","ConversationFiltersScreenOptions","presentation","select","android","ios","sheetAllowedDetents","default","headerTitle","FilterNavigator","initialRouteName","screens","Filters","screen","options","headerShown","headerBackTitle","createStaticNavigationComponent","tree","name","getComponent","createComponentForStaticNavigation","ConversationFiltersScreen","_props","$","_c","styles","useStyles","t0","t1","Symbol","for","FormSheetHeaderWithContext","t2","contentContainer","children","Root","contentStyle","showAndroidSheetGrabber","resetFilter","applyFilters","setFormSheetHeaderHeight","route","event","nativeEvent","layout","height","handleFormSheetHeaderLayout","HeaderTitle","HeaderTextButton","t3","params","HeaderButton","title","onPress","t4","HeaderActions","t5","header","Header","style","t6","top","headerHeight","containerHeight","create","paddingTop","borderBottomWidth"],"sources":["../../src/screens/conversation_filters_screen.tsx"],"sourcesContent":["import { useHeaderHeight } from '@react-navigation/elements'\nimport * as ReactNavigationNative from '@react-navigation/native'\nimport { RouteProp, useRoute } from '@react-navigation/native'\nimport { createNativeStackNavigator } from '@react-navigation/native-stack'\nimport React, { useCallback } from 'react'\nimport { LayoutChangeEvent, Platform, StyleSheet, useWindowDimensions, View } from 'react-native'\nimport { useSafeAreaInsets } from 'react-native-safe-area-context'\nimport FormSheet, { getFormSheetScreenOptions } from '../components/primitive/form_sheet'\nimport { ConversationFilters } from './conversation_filters/components/conversation_filters'\nimport {\n FilterProvider,\n useFilterContext,\n} from './conversation_filters/context/conversation_filter_context'\nimport { GroupFilters } from './conversation_filters/group_filters'\nimport {\n ConversationFiltersScreenProps,\n ConversationFilterStackParamList,\n} from './conversation_filters/screen_props'\nimport { TeamFilters } from './conversation_filters/team_filters'\n\nexport const ConversationFiltersScreenOptions = getFormSheetScreenOptions({\n presentation: Platform.select({ android: 'modal', ios: 'formSheet' }),\n sheetAllowedDetents: Platform.select({\n ios: [0.75, 1],\n default: [1],\n }),\n headerTitle: 'Filters',\n})\n\nconst FilterNavigator = createNativeStackNavigator<ConversationFilterStackParamList>({\n initialRouteName: 'Filters',\n screens: {\n Filters: {\n screen: ConversationFilters,\n options: {\n headerShown: false,\n },\n },\n GroupFilters: {\n screen: GroupFilters,\n options: {\n headerTitle: Platform.select({\n android: 'Groups',\n ios: '',\n }),\n headerBackTitle: 'Groups',\n },\n },\n TeamFilters: {\n screen: TeamFilters,\n options: {\n headerTitle: Platform.select({\n android: 'Teams',\n ios: '',\n }),\n headerBackTitle: 'Teams',\n },\n },\n },\n})\n\n// tree.getComponent() doesn't exist on every host's installed\n// react-navigation/core — hosts on an older version would throw here.\n// Where it does exist, it's the real implementation (the \"deprecated\"\n// createComponentForStaticNavigation is just a console.warn wrapper around\n// the same call on current versions), so prefer it and only reach for the\n// old function on cores where getComponent() genuinely isn't there yet.\nfunction createStaticNavigationComponent<P extends object>(\n tree: { getComponent?: () => React.ComponentType<P> },\n name: string\n): React.ComponentType<P> {\n if (typeof tree.getComponent === 'function') return tree.getComponent()\n\n const { createComponentForStaticNavigation } = ReactNavigationNative as {\n createComponentForStaticNavigation: (tree: unknown, name: string) => React.ComponentType<P>\n }\n\n return createComponentForStaticNavigation(tree, name)\n}\n\nconst Filters = createStaticNavigationComponent(FilterNavigator, 'Filters')\n\nexport const ConversationFiltersScreen = (_props: ConversationFiltersScreenProps) => {\n const styles = useStyles()\n\n return (\n <FilterProvider>\n <FormSheet.Root contentStyle={styles.contentContainer} showAndroidSheetGrabber={false}>\n <FormSheetHeaderWithContext />\n <Filters />\n </FormSheet.Root>\n </FilterProvider>\n )\n}\n\nconst FormSheetHeaderWithContext = () => {\n const { resetFilter, applyFilters, setFormSheetHeaderHeight } = useFilterContext()\n const route = useRoute<RouteProp<ConversationFiltersScreenProps['route']>>()\n const styles = useStyles()\n\n const handleFormSheetHeaderLayout = useCallback(\n (event: LayoutChangeEvent) => {\n setFormSheetHeaderHeight(event.nativeEvent.layout.height)\n },\n [setFormSheetHeaderHeight]\n )\n\n return (\n <View onLayout={handleFormSheetHeaderLayout}>\n <FormSheet.Header style={styles.header}>\n <FormSheet.HeaderTitle>Filters</FormSheet.HeaderTitle>\n <FormSheet.HeaderActions>\n <FormSheet.HeaderTextButton onPress={resetFilter}>Reset</FormSheet.HeaderTextButton>\n <FormSheet.HeaderButton title=\"Apply\" onPress={() => applyFilters(route.params)} />\n </FormSheet.HeaderActions>\n </FormSheet.Header>\n </View>\n )\n}\n\nconst useStyles = () => {\n const { top } = useSafeAreaInsets()\n const { height } = useWindowDimensions()\n const headerHeight = useHeaderHeight()\n\n const containerHeight = Platform.select({\n android: height,\n ios: height - top - headerHeight,\n })\n\n return StyleSheet.create({\n contentContainer: {\n height: containerHeight,\n },\n header: {\n paddingTop: Platform.select({\n ios: 20,\n android: 20 + top,\n }),\n // The filter list scrolls under it, so the sheet header doesn't need a\n // separator the way the non-scrolling reaction sheet does.\n borderBottomWidth: 0,\n },\n })\n}\n"],"mappings":"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","ignoreList":[]}
|
|
1
|
+
{"version":3,"file":"conversation_filters_screen.js","names":["useHeaderHeight","ReactNavigationNative","useRoute","createNativeStackNavigator","React","useCallback","Platform","StyleSheet","useWindowDimensions","View","useSafeAreaInsets","FormSheet","getFormSheetScreenOptions","useFilterDropdownEnabled","ConversationFilters","FilterProvider","useFilterContext","GroupFilters","TeamFilters","jsx","_jsx","jsxs","_jsxs","ConversationFiltersScreenOptions","presentation","select","android","ios","sheetAllowedDetents","default","headerTitle","FilterNavigator","initialRouteName","screens","Filters","screen","options","headerShown","headerBackTitle","createStaticNavigationComponent","tree","name","getComponent","createComponentForStaticNavigation","ConversationFiltersScreen","_props","$","_c","styles","useStyles","t0","t1","Symbol","for","FormSheetHeaderWithContext","t2","contentContainer","children","Root","contentStyle","showAndroidSheetGrabber","resetFilter","applyFilters","setFormSheetHeaderHeight","route","filterDropdownEnabled","event","nativeEvent","layout","height","handleFormSheetHeaderLayout","HeaderTitle","t3","HeaderTextButton","t4","params","HeaderButton","title","onPress","t5","HeaderActions","t6","header","Header","style","t7","top","headerHeight","containerHeight","create","paddingTop","borderBottomWidth"],"sources":["../../src/screens/conversation_filters_screen.tsx"],"sourcesContent":["import { useHeaderHeight } from '@react-navigation/elements'\nimport * as ReactNavigationNative from '@react-navigation/native'\nimport { RouteProp, useRoute } from '@react-navigation/native'\nimport { createNativeStackNavigator } from '@react-navigation/native-stack'\nimport React, { useCallback } from 'react'\nimport { LayoutChangeEvent, Platform, StyleSheet, useWindowDimensions, View } from 'react-native'\nimport { useSafeAreaInsets } from 'react-native-safe-area-context'\nimport FormSheet, { getFormSheetScreenOptions } from '../components/primitive/form_sheet'\nimport { useFilterDropdownEnabled } from '../hooks/use_filter_dropdown_enabled'\nimport { ConversationFilters } from './conversation_filters/components/conversation_filters'\nimport {\n FilterProvider,\n useFilterContext,\n} from './conversation_filters/context/conversation_filter_context'\nimport { GroupFilters } from './conversation_filters/group_filters'\nimport {\n ConversationFiltersScreenProps,\n ConversationFilterStackParamList,\n} from './conversation_filters/screen_props'\nimport { TeamFilters } from './conversation_filters/team_filters'\n\nexport const ConversationFiltersScreenOptions = getFormSheetScreenOptions({\n presentation: Platform.select({ android: 'modal', ios: 'formSheet' }),\n sheetAllowedDetents: Platform.select({\n ios: [0.75, 1],\n default: [1],\n }),\n headerTitle: 'Filters',\n})\n\nconst FilterNavigator = createNativeStackNavigator<ConversationFilterStackParamList>({\n initialRouteName: 'Filters',\n screens: {\n Filters: {\n screen: ConversationFilters,\n options: {\n headerShown: false,\n },\n },\n GroupFilters: {\n screen: GroupFilters,\n options: {\n headerTitle: Platform.select({\n android: 'Groups',\n ios: '',\n }),\n headerBackTitle: 'Groups',\n },\n },\n TeamFilters: {\n screen: TeamFilters,\n options: {\n headerTitle: Platform.select({\n android: 'Teams',\n ios: '',\n }),\n headerBackTitle: 'Teams',\n },\n },\n },\n})\n\n// tree.getComponent() doesn't exist on every host's installed\n// react-navigation/core — hosts on an older version would throw here.\n// Where it does exist, it's the real implementation (the \"deprecated\"\n// createComponentForStaticNavigation is just a console.warn wrapper around\n// the same call on current versions), so prefer it and only reach for the\n// old function on cores where getComponent() genuinely isn't there yet.\nfunction createStaticNavigationComponent<P extends object>(\n tree: { getComponent?: () => React.ComponentType<P> },\n name: string\n): React.ComponentType<P> {\n if (typeof tree.getComponent === 'function') return tree.getComponent()\n\n const { createComponentForStaticNavigation } = ReactNavigationNative as {\n createComponentForStaticNavigation: (tree: unknown, name: string) => React.ComponentType<P>\n }\n\n return createComponentForStaticNavigation(tree, name)\n}\n\nconst Filters = createStaticNavigationComponent(FilterNavigator, 'Filters')\n\nexport const ConversationFiltersScreen = (_props: ConversationFiltersScreenProps) => {\n const styles = useStyles()\n\n return (\n <FilterProvider>\n <FormSheet.Root contentStyle={styles.contentContainer} showAndroidSheetGrabber={false}>\n <FormSheetHeaderWithContext />\n <Filters />\n </FormSheet.Root>\n </FilterProvider>\n )\n}\n\nconst FormSheetHeaderWithContext = () => {\n const { resetFilter, applyFilters, setFormSheetHeaderHeight } = useFilterContext()\n const route = useRoute<RouteProp<ConversationFiltersScreenProps['route']>>()\n const filterDropdownEnabled = useFilterDropdownEnabled()\n const styles = useStyles()\n\n const handleFormSheetHeaderLayout = useCallback(\n (event: LayoutChangeEvent) => {\n setFormSheetHeaderHeight(event.nativeEvent.layout.height)\n },\n [setFormSheetHeaderHeight]\n )\n\n return (\n <View onLayout={handleFormSheetHeaderLayout}>\n <FormSheet.Header style={styles.header}>\n <FormSheet.HeaderTitle>\n {filterDropdownEnabled ? 'More filters' : 'Filters'}\n </FormSheet.HeaderTitle>\n <FormSheet.HeaderActions>\n <FormSheet.HeaderTextButton onPress={resetFilter}>Reset</FormSheet.HeaderTextButton>\n <FormSheet.HeaderButton title=\"Apply\" onPress={() => applyFilters(route.params)} />\n </FormSheet.HeaderActions>\n </FormSheet.Header>\n </View>\n )\n}\n\nconst useStyles = () => {\n const { top } = useSafeAreaInsets()\n const { height } = useWindowDimensions()\n const headerHeight = useHeaderHeight()\n\n const containerHeight = Platform.select({\n android: height,\n ios: height - top - headerHeight,\n })\n\n return StyleSheet.create({\n contentContainer: {\n height: containerHeight,\n },\n header: {\n paddingTop: Platform.select({\n ios: 20,\n android: 20 + top,\n }),\n // The filter list scrolls under it, so the sheet header doesn't need a\n // separator the way the non-scrolling reaction sheet does.\n borderBottomWidth: 0,\n },\n })\n}\n"],"mappings":"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","ignoreList":[]}
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@planningcenter/chat-react-native",
|
|
3
|
-
"version": "4.4.1-qa-staging.
|
|
3
|
+
"version": "4.4.1-qa-staging.17",
|
|
4
4
|
"description": "",
|
|
5
5
|
"repository": {
|
|
6
6
|
"type": "git",
|
|
@@ -33,7 +33,7 @@
|
|
|
33
33
|
"dependencies": {
|
|
34
34
|
"@fortawesome/fontawesome-svg-core": "^7.2.0",
|
|
35
35
|
"@fortawesome/react-native-fontawesome": "^0.3.2",
|
|
36
|
-
"@planningcenter/emoji-keyboard": "4.4.1-qa-staging.
|
|
36
|
+
"@planningcenter/emoji-keyboard": "4.4.1-qa-staging.17",
|
|
37
37
|
"lodash-inflection": "^1.5.0"
|
|
38
38
|
},
|
|
39
39
|
"peerDependencies": {
|
|
@@ -84,5 +84,5 @@
|
|
|
84
84
|
"sf-symbols-typescript": "^2.2.0",
|
|
85
85
|
"typescript": "~6.0.3"
|
|
86
86
|
},
|
|
87
|
-
"gitHead": "
|
|
87
|
+
"gitHead": "3f42f16e64f443ba3e1b2c24298954ecc380b52a"
|
|
88
88
|
}
|
|
@@ -0,0 +1,129 @@
|
|
|
1
|
+
import { DefaultTheme, ThemeProvider } from '@react-navigation/native'
|
|
2
|
+
import { render } from '@testing-library/react-native'
|
|
3
|
+
import React from 'react'
|
|
4
|
+
import { SafeAreaProvider } from 'react-native-safe-area-context'
|
|
5
|
+
import { useFilterDropdownEnabled } from '../../../../hooks/use_filter_dropdown_enabled'
|
|
6
|
+
import { ConversationFilters } from '../../../../screens/conversation_filters/components/conversation_filters'
|
|
7
|
+
import { FilterContext } from '../../../../screens/conversation_filters/context/conversation_filter_context'
|
|
8
|
+
import { FilterTypes } from '../../../../screens/conversation_filters/filter_types'
|
|
9
|
+
import { GroupResource } from '../../../../types/resources/group_resource'
|
|
10
|
+
|
|
11
|
+
jest.mock('react-native-gesture-handler', () => {
|
|
12
|
+
const { FlatList } = jest.requireActual('react-native')
|
|
13
|
+
const ReactActual = jest.requireActual('react')
|
|
14
|
+
|
|
15
|
+
return {
|
|
16
|
+
FlatList: (props: object) =>
|
|
17
|
+
ReactActual.createElement(FlatList, { ...props, initialNumToRender: 50 }),
|
|
18
|
+
}
|
|
19
|
+
})
|
|
20
|
+
jest.mock('@react-navigation/native', () => ({
|
|
21
|
+
...jest.requireActual('@react-navigation/native'),
|
|
22
|
+
useNavigation: () => ({ navigate: jest.fn(), dispatch: jest.fn(), setParams: jest.fn() }),
|
|
23
|
+
}))
|
|
24
|
+
jest.mock('../../../../hooks/use_api_client', () => ({ useApiClient: () => ({}) }))
|
|
25
|
+
jest.mock('../../../../hooks/use_filter_dropdown_enabled', () => ({
|
|
26
|
+
useFilterDropdownEnabled: jest.fn(() => false),
|
|
27
|
+
}))
|
|
28
|
+
jest.mock('../../../../hooks/use_direct_messages_eligible', () => ({
|
|
29
|
+
useDirectMessagesEligible: () => true,
|
|
30
|
+
}))
|
|
31
|
+
jest.mock('../../../../hooks/use_has_direct_messages', () => ({
|
|
32
|
+
useHasDirectMessages: () => true,
|
|
33
|
+
}))
|
|
34
|
+
jest.mock('../../../../hooks/services/use_services_team', () => ({
|
|
35
|
+
useServicesTeamsMap: () => ({}),
|
|
36
|
+
}))
|
|
37
|
+
jest.mock('../../../../screens/conversation_filters/hooks/filters', () => ({
|
|
38
|
+
useGroupsToFilter: () => ({ groups: mockGroups }),
|
|
39
|
+
useTeamsToFilter: () => ({ teams: mockTeams }),
|
|
40
|
+
}))
|
|
41
|
+
|
|
42
|
+
const buildGroup = (id: number, name: string): GroupResource => ({
|
|
43
|
+
id: `Groups-Group-${id}`,
|
|
44
|
+
type: 'Group',
|
|
45
|
+
links: { self: '' },
|
|
46
|
+
name,
|
|
47
|
+
sourceAppName: 'Groups',
|
|
48
|
+
sourceType: 'Group',
|
|
49
|
+
})
|
|
50
|
+
|
|
51
|
+
const buildTeam = (id: number, name: string): GroupResource => ({
|
|
52
|
+
id: `Services-Team-${id}`,
|
|
53
|
+
type: 'Group',
|
|
54
|
+
links: { self: '' },
|
|
55
|
+
name,
|
|
56
|
+
sourceAppName: 'Services',
|
|
57
|
+
sourceType: 'Team',
|
|
58
|
+
})
|
|
59
|
+
|
|
60
|
+
const mockGroups = Array.from({ length: 6 }, (_, i) => buildGroup(i + 1, `Group ${i + 1}`))
|
|
61
|
+
const mockTeams = [buildTeam(1, 'Worship Team')]
|
|
62
|
+
|
|
63
|
+
const mockedFilterDropdownEnabled = jest.mocked(useFilterDropdownEnabled)
|
|
64
|
+
|
|
65
|
+
const safeAreaMetrics = {
|
|
66
|
+
frame: { x: 0, y: 0, width: 390, height: 844 },
|
|
67
|
+
insets: { top: 0, right: 0, bottom: 0, left: 0 },
|
|
68
|
+
}
|
|
69
|
+
|
|
70
|
+
const renderFilters = () =>
|
|
71
|
+
render(
|
|
72
|
+
<SafeAreaProvider initialMetrics={safeAreaMetrics}>
|
|
73
|
+
<ThemeProvider value={DefaultTheme}>
|
|
74
|
+
<FilterContext.Provider
|
|
75
|
+
value={{
|
|
76
|
+
params: {},
|
|
77
|
+
scrollOffset: 0,
|
|
78
|
+
setScrollOffset: jest.fn(),
|
|
79
|
+
setFormSheetHeaderHeight: jest.fn(),
|
|
80
|
+
resetFilter: jest.fn(),
|
|
81
|
+
setGroupFilter: jest.fn(),
|
|
82
|
+
setAppFilter: jest.fn(),
|
|
83
|
+
applyFilters: jest.fn(),
|
|
84
|
+
platformListPaddingBottom: 0,
|
|
85
|
+
}}
|
|
86
|
+
>
|
|
87
|
+
<ConversationFilters />
|
|
88
|
+
</FilterContext.Provider>
|
|
89
|
+
</ThemeProvider>
|
|
90
|
+
</SafeAreaProvider>
|
|
91
|
+
)
|
|
92
|
+
|
|
93
|
+
const generalFilterLabels = [
|
|
94
|
+
'General Filters',
|
|
95
|
+
FilterTypes.All,
|
|
96
|
+
FilterTypes.Groups,
|
|
97
|
+
FilterTypes.Teams,
|
|
98
|
+
FilterTypes.DirectMessages,
|
|
99
|
+
]
|
|
100
|
+
|
|
101
|
+
describe('ConversationFilters', () => {
|
|
102
|
+
beforeEach(() => {
|
|
103
|
+
jest.clearAllMocks()
|
|
104
|
+
})
|
|
105
|
+
|
|
106
|
+
it('renders the General Filters section when the filter dropdown is off', () => {
|
|
107
|
+
mockedFilterDropdownEnabled.mockReturnValue(false)
|
|
108
|
+
|
|
109
|
+
const { getByText } = renderFilters()
|
|
110
|
+
|
|
111
|
+
generalFilterLabels.forEach(label => expect(getByText(label)).toBeTruthy())
|
|
112
|
+
expect(getByText('Groups')).toBeTruthy()
|
|
113
|
+
expect(getByText('Teams')).toBeTruthy()
|
|
114
|
+
})
|
|
115
|
+
|
|
116
|
+
it('hides the General Filters section but keeps Groups and Teams when the filter dropdown is on', () => {
|
|
117
|
+
mockedFilterDropdownEnabled.mockReturnValue(true)
|
|
118
|
+
|
|
119
|
+
const { getByText, queryByText, getAllByText } = renderFilters()
|
|
120
|
+
|
|
121
|
+
generalFilterLabels.forEach(label => expect(queryByText(label)).toBeNull())
|
|
122
|
+
expect(getByText('Groups')).toBeTruthy()
|
|
123
|
+
expect(getByText('Teams')).toBeTruthy()
|
|
124
|
+
expect(getByText('Group 1')).toBeTruthy()
|
|
125
|
+
expect(queryByText('Group 6')).toBeNull()
|
|
126
|
+
expect(getByText('Worship Team')).toBeTruthy()
|
|
127
|
+
expect(getAllByText('View more')).toHaveLength(1)
|
|
128
|
+
})
|
|
129
|
+
})
|
|
@@ -9,6 +9,7 @@ import { ServicesForm } from '../../../../screens/conversation_new/components/se
|
|
|
9
9
|
jest.mock('react-native-reanimated', () => ({
|
|
10
10
|
...jest.requireActual('react-native-reanimated/mock'),
|
|
11
11
|
LayoutAnimationConfig: ({ children }: { children: React.ReactNode }) => children,
|
|
12
|
+
useReducedMotion: () => false,
|
|
12
13
|
}))
|
|
13
14
|
jest.mock('@react-navigation/native', () => ({
|
|
14
15
|
...jest.requireActual('@react-navigation/native'),
|
|
@@ -110,7 +110,7 @@ function ShadowMessageContent({ conversation_id, ...message }: ShadowMessageCont
|
|
|
110
110
|
accessibilityRole="link"
|
|
111
111
|
>
|
|
112
112
|
<Animated.View style={[StyleSheet.absoluteFill, animatedBackgroundColor]} />
|
|
113
|
-
<View style={styles.message}>
|
|
113
|
+
<View style={[styles.message, { marginBottom: -SPACE_BELOW_PRESSABLE }]}>
|
|
114
114
|
{!message.mine && (
|
|
115
115
|
<View>
|
|
116
116
|
<View style={[styles.avatarWrapper, !isDeleted && styles.avatarOpacity]}>
|
|
@@ -297,7 +297,6 @@ const useStyles = ({ mine, imageWidth = 32, imageHeight = 32 }: StylesProps = {}
|
|
|
297
297
|
gap: 8,
|
|
298
298
|
flexDirection: mine ? 'row-reverse' : 'row',
|
|
299
299
|
paddingHorizontal: CONVERSATION_MESSAGE_LIST_PADDING_HORIZONTAL,
|
|
300
|
-
marginBottom: -SPACE_BELOW_PRESSABLE,
|
|
301
300
|
},
|
|
302
301
|
messageContent: {
|
|
303
302
|
flex: 1,
|
|
@@ -0,0 +1,72 @@
|
|
|
1
|
+
import { fireEvent, render } from '@testing-library/react-native'
|
|
2
|
+
import React from 'react'
|
|
3
|
+
import { ConversationsBlankState } from '../conversations_blank_state'
|
|
4
|
+
|
|
5
|
+
const mockSetParams = jest.fn()
|
|
6
|
+
const mockUseFilterDropdownEnabled = jest.fn()
|
|
7
|
+
|
|
8
|
+
jest.mock('@react-navigation/native', () => ({
|
|
9
|
+
...jest.requireActual('@react-navigation/native'),
|
|
10
|
+
useNavigation: () => ({ setParams: mockSetParams }),
|
|
11
|
+
}))
|
|
12
|
+
|
|
13
|
+
jest.mock('../../../hooks/use_filter_dropdown_enabled', () => ({
|
|
14
|
+
useFilterDropdownEnabled: () => mockUseFilterDropdownEnabled(),
|
|
15
|
+
}))
|
|
16
|
+
|
|
17
|
+
describe('ConversationsBlankState', () => {
|
|
18
|
+
beforeEach(() => {
|
|
19
|
+
mockSetParams.mockClear()
|
|
20
|
+
})
|
|
21
|
+
|
|
22
|
+
describe('with the filter dropdown on', () => {
|
|
23
|
+
beforeEach(() => {
|
|
24
|
+
mockUseFilterDropdownEnabled.mockReturnValue(true)
|
|
25
|
+
})
|
|
26
|
+
|
|
27
|
+
it('offers to view all conversations when a filter is applied', () => {
|
|
28
|
+
const view = render(
|
|
29
|
+
<ConversationsBlankState isFilterApplied={true} canCreateConversations={true} />
|
|
30
|
+
)
|
|
31
|
+
|
|
32
|
+
expect(view.getByText('No matches')).toBeTruthy()
|
|
33
|
+
expect(view.queryByText('No conversations yet.')).toBeNull()
|
|
34
|
+
|
|
35
|
+
fireEvent.press(view.getByText('View all conversations'))
|
|
36
|
+
|
|
37
|
+
expect(mockSetParams).toHaveBeenCalledTimes(1)
|
|
38
|
+
expect(mockSetParams.mock.calls[0][0]).toStrictEqual({
|
|
39
|
+
title: undefined,
|
|
40
|
+
chat_group_graph_id: undefined,
|
|
41
|
+
group_source_app_name: undefined,
|
|
42
|
+
show_direct_messages: undefined,
|
|
43
|
+
})
|
|
44
|
+
})
|
|
45
|
+
|
|
46
|
+
it('keeps the compose prompt when no filter is applied', () => {
|
|
47
|
+
const view = render(
|
|
48
|
+
<ConversationsBlankState isFilterApplied={false} canCreateConversations={true} />
|
|
49
|
+
)
|
|
50
|
+
|
|
51
|
+
expect(view.getByText('No conversations yet.')).toBeTruthy()
|
|
52
|
+
expect(view.getByText('Tap the compose button to get started.')).toBeTruthy()
|
|
53
|
+
expect(view.queryByText('View all conversations')).toBeNull()
|
|
54
|
+
})
|
|
55
|
+
})
|
|
56
|
+
|
|
57
|
+
describe('with the filter dropdown off', () => {
|
|
58
|
+
beforeEach(() => {
|
|
59
|
+
mockUseFilterDropdownEnabled.mockReturnValue(false)
|
|
60
|
+
})
|
|
61
|
+
|
|
62
|
+
it('keeps the adjust-your-filters copy when a filter is applied', () => {
|
|
63
|
+
const view = render(
|
|
64
|
+
<ConversationsBlankState isFilterApplied={true} canCreateConversations={true} />
|
|
65
|
+
)
|
|
66
|
+
|
|
67
|
+
expect(view.getByText('No conversations yet.')).toBeTruthy()
|
|
68
|
+
expect(view.getByText('Adjust your filters to find conversations.')).toBeTruthy()
|
|
69
|
+
expect(view.queryByText('View all conversations')).toBeNull()
|
|
70
|
+
})
|
|
71
|
+
})
|
|
72
|
+
})
|
|
@@ -5,9 +5,11 @@ import { useConversationsContext } from '../../contexts/conversations_context'
|
|
|
5
5
|
import { useTheme } from '../../hooks'
|
|
6
6
|
import { useCanCreateConversations } from '../../hooks/use_chat_permissions'
|
|
7
7
|
import { useConversationsJoltEvents } from '../../hooks/use_conversations_jolt_events'
|
|
8
|
+
import { useFilterDropdownEnabled } from '../../hooks/use_filter_dropdown_enabled'
|
|
8
9
|
import { ConversationResource } from '../../types'
|
|
9
10
|
import { ConversationPreview, ConversationPreviewSkeleton } from './conversation_preview'
|
|
10
11
|
import { ConversationsBlankState } from './conversations_blank_state'
|
|
12
|
+
import { FilteredResultsFooter } from './filtered_results_footer'
|
|
11
13
|
|
|
12
14
|
interface ConversationsProps {
|
|
13
15
|
ListHeaderComponent?:
|
|
@@ -26,11 +28,19 @@ export const Conversations = ({ ListHeaderComponent }: ConversationsProps) => {
|
|
|
26
28
|
refetch,
|
|
27
29
|
isRefetching,
|
|
28
30
|
isFetched,
|
|
29
|
-
|
|
31
|
+
hasNextPage,
|
|
32
|
+
args: { chat_group_graph_id, group_source_app_name, show_direct_messages },
|
|
30
33
|
} = useConversationsContext()
|
|
31
34
|
const navigation = useNavigation()
|
|
32
35
|
const canCreateConversations = useCanCreateConversations()
|
|
33
|
-
const
|
|
36
|
+
const filterDropdownEnabled = useFilterDropdownEnabled()
|
|
37
|
+
const isFilterApplied = !!chat_group_graph_id || !!group_source_app_name || !!show_direct_messages
|
|
38
|
+
const showFilteredResultsFooter =
|
|
39
|
+
filterDropdownEnabled &&
|
|
40
|
+
isFilterApplied &&
|
|
41
|
+
!hasNextPage &&
|
|
42
|
+
!isLoading &&
|
|
43
|
+
conversations.length > 0
|
|
34
44
|
|
|
35
45
|
const showBadges = !chat_group_graph_id
|
|
36
46
|
|
|
@@ -62,6 +72,7 @@ export const Conversations = ({ ListHeaderComponent }: ConversationsProps) => {
|
|
|
62
72
|
canCreateConversations={canCreateConversations}
|
|
63
73
|
/>
|
|
64
74
|
}
|
|
75
|
+
ListFooterComponent={showFilteredResultsFooter ? <FilteredResultsFooter /> : null}
|
|
65
76
|
renderItem={({ item }) => {
|
|
66
77
|
if (item.type === 'loading') {
|
|
67
78
|
return <ConversationPreviewSkeleton />
|
|
@@ -1,5 +1,7 @@
|
|
|
1
1
|
import React from 'react'
|
|
2
2
|
import { StyleSheet, View } from 'react-native'
|
|
3
|
+
import { useClearConversationFilters } from '../../hooks/use_clear_conversation_filters'
|
|
4
|
+
import { useFilterDropdownEnabled } from '../../hooks/use_filter_dropdown_enabled'
|
|
3
5
|
import BlankState from '../primitive/blank_state_primitive'
|
|
4
6
|
|
|
5
7
|
interface ConversationsBlankStateProps {
|
|
@@ -11,6 +13,25 @@ export function ConversationsBlankState({
|
|
|
11
13
|
isFilterApplied,
|
|
12
14
|
canCreateConversations,
|
|
13
15
|
}: ConversationsBlankStateProps) {
|
|
16
|
+
const filterDropdownEnabled = useFilterDropdownEnabled()
|
|
17
|
+
const clearFilters = useClearConversationFilters()
|
|
18
|
+
|
|
19
|
+
if (filterDropdownEnabled && isFilterApplied) {
|
|
20
|
+
return (
|
|
21
|
+
<View style={styles.container}>
|
|
22
|
+
<BlankState.Root>
|
|
23
|
+
<BlankState.Imagery name="general.outlinedTextMessage" />
|
|
24
|
+
<BlankState.Content>
|
|
25
|
+
<BlankState.Heading>No matches</BlankState.Heading>
|
|
26
|
+
</BlankState.Content>
|
|
27
|
+
<BlankState.TextButton onPress={clearFilters}>
|
|
28
|
+
View all conversations
|
|
29
|
+
</BlankState.TextButton>
|
|
30
|
+
</BlankState.Root>
|
|
31
|
+
</View>
|
|
32
|
+
)
|
|
33
|
+
}
|
|
34
|
+
|
|
14
35
|
return (
|
|
15
36
|
<View style={styles.container}>
|
|
16
37
|
<BlankState.Root>
|
|
@@ -0,0 +1,38 @@
|
|
|
1
|
+
import React from 'react'
|
|
2
|
+
import { StyleSheet, View } from 'react-native'
|
|
3
|
+
import { useTheme } from '../../hooks'
|
|
4
|
+
import { useClearConversationFilters } from '../../hooks/use_clear_conversation_filters'
|
|
5
|
+
import { Text, TextButton } from '../display'
|
|
6
|
+
|
|
7
|
+
export function FilteredResultsFooter() {
|
|
8
|
+
const styles = useStyles()
|
|
9
|
+
const clearFilters = useClearConversationFilters()
|
|
10
|
+
|
|
11
|
+
return (
|
|
12
|
+
<View style={styles.container}>
|
|
13
|
+
<Text variant="tertiary" style={styles.text}>
|
|
14
|
+
You’re viewing filtered results
|
|
15
|
+
</Text>
|
|
16
|
+
<TextButton variant="tertiary" onPress={clearFilters}>
|
|
17
|
+
View all conversations
|
|
18
|
+
</TextButton>
|
|
19
|
+
</View>
|
|
20
|
+
)
|
|
21
|
+
}
|
|
22
|
+
|
|
23
|
+
const useStyles = () => {
|
|
24
|
+
const { colors } = useTheme()
|
|
25
|
+
|
|
26
|
+
return StyleSheet.create({
|
|
27
|
+
container: {
|
|
28
|
+
alignItems: 'center',
|
|
29
|
+
gap: 8,
|
|
30
|
+
paddingHorizontal: 16,
|
|
31
|
+
paddingVertical: 24,
|
|
32
|
+
},
|
|
33
|
+
text: {
|
|
34
|
+
textAlign: 'center',
|
|
35
|
+
color: colors.textColorDefaultSecondary,
|
|
36
|
+
},
|
|
37
|
+
})
|
|
38
|
+
}
|
|
@@ -1,5 +1,6 @@
|
|
|
1
1
|
import { act, renderHook, waitFor } from '@testing-library/react-native'
|
|
2
2
|
import { AccessibilityInfo, EmitterSubscription } from 'react-native'
|
|
3
|
+
import * as Reanimated from 'react-native-reanimated'
|
|
3
4
|
import { useReduceMotion } from '../use_reduce_motion'
|
|
4
5
|
|
|
5
6
|
type ReduceMotionListener = (enabled: boolean) => void
|
|
@@ -11,6 +12,7 @@ describe('useReduceMotion', () => {
|
|
|
11
12
|
beforeEach(() => {
|
|
12
13
|
listener = undefined
|
|
13
14
|
remove.mockClear()
|
|
15
|
+
jest.spyOn(Reanimated, 'useReducedMotion').mockReturnValue(false)
|
|
14
16
|
jest.spyOn(AccessibilityInfo, 'isReduceMotionEnabled').mockResolvedValue(true)
|
|
15
17
|
const addEventListener: typeof AccessibilityInfo.addEventListener = (_event, handler) => {
|
|
16
18
|
listener = handler as ReduceMotionListener
|
|
@@ -21,7 +23,17 @@ describe('useReduceMotion', () => {
|
|
|
21
23
|
|
|
22
24
|
afterEach(() => jest.restoreAllMocks())
|
|
23
25
|
|
|
24
|
-
it('seeds from the
|
|
26
|
+
it('seeds synchronously from the launch-time setting', async () => {
|
|
27
|
+
jest.spyOn(Reanimated, 'useReducedMotion').mockReturnValue(true)
|
|
28
|
+
jest.mocked(AccessibilityInfo.isReduceMotionEnabled).mockResolvedValue(false)
|
|
29
|
+
|
|
30
|
+
const { result } = renderHook(() => useReduceMotion())
|
|
31
|
+
|
|
32
|
+
expect(result.current).toBe(true)
|
|
33
|
+
await waitFor(() => expect(result.current).toBe(false))
|
|
34
|
+
})
|
|
35
|
+
|
|
36
|
+
it('updates to the live setting once it resolves', async () => {
|
|
25
37
|
const { result } = renderHook(() => useReduceMotion())
|
|
26
38
|
|
|
27
39
|
expect(result.current).toBe(false)
|
|
@@ -0,0 +1,15 @@
|
|
|
1
|
+
import { useNavigation } from '@react-navigation/native'
|
|
2
|
+
import { useCallback } from 'react'
|
|
3
|
+
|
|
4
|
+
export function useClearConversationFilters() {
|
|
5
|
+
const navigation = useNavigation()
|
|
6
|
+
|
|
7
|
+
return useCallback(() => {
|
|
8
|
+
navigation.setParams({
|
|
9
|
+
title: undefined,
|
|
10
|
+
chat_group_graph_id: undefined,
|
|
11
|
+
group_source_app_name: undefined,
|
|
12
|
+
show_direct_messages: undefined,
|
|
13
|
+
})
|
|
14
|
+
}, [navigation])
|
|
15
|
+
}
|
|
@@ -1,8 +1,9 @@
|
|
|
1
1
|
import { useEffect, useState } from 'react'
|
|
2
2
|
import { AccessibilityInfo } from 'react-native'
|
|
3
|
+
import { useReducedMotion } from 'react-native-reanimated'
|
|
3
4
|
|
|
4
5
|
export const useReduceMotion = () => {
|
|
5
|
-
const [reduceMotion, setReduceMotion] = useState(
|
|
6
|
+
const [reduceMotion, setReduceMotion] = useState(useReducedMotion())
|
|
6
7
|
|
|
7
8
|
useEffect(() => {
|
|
8
9
|
AccessibilityInfo.isReduceMotionEnabled().then(setReduceMotion)
|