2020-04-26 16:15:59 +05:00
|
|
|
import React, {createRef, useState} from 'react';
|
2020-04-20 10:54:58 +05:00
|
|
|
import {
|
|
|
|
|
FlatList,
|
|
|
|
|
Platform,
|
|
|
|
|
RefreshControl,
|
2020-04-26 16:36:51 +05:00
|
|
|
SectionList,
|
2020-04-20 10:54:58 +05:00
|
|
|
Text,
|
|
|
|
|
View,
|
|
|
|
|
} from 'react-native';
|
2020-09-09 14:55:59 +05:00
|
|
|
import * as Animatable from 'react-native-animatable';
|
2020-04-26 16:36:51 +05:00
|
|
|
import {useSafeArea} from 'react-native-safe-area-context';
|
2020-09-09 14:55:59 +05:00
|
|
|
import Icon from 'react-native-vector-icons/MaterialCommunityIcons';
|
|
|
|
|
import {SIZE, WEIGHT} from '../../common/common';
|
2020-04-20 09:16:01 +05:00
|
|
|
import {useTracked} from '../../provider';
|
|
|
|
|
import {ACTIONS} from '../../provider/actions';
|
|
|
|
|
import {eSendEvent} from '../../services/eventManager';
|
2020-08-16 18:59:07 +05:00
|
|
|
import {
|
|
|
|
|
eClearSearch,
|
|
|
|
|
eOpenLoginDialog,
|
2020-09-09 14:55:59 +05:00
|
|
|
eScrollEvent,
|
2020-08-16 18:59:07 +05:00
|
|
|
} from '../../services/events';
|
2020-05-14 14:52:56 +05:00
|
|
|
import NavigationService from '../../services/NavigationService';
|
2020-09-09 14:55:59 +05:00
|
|
|
import {db, DDS, ToastEvent} from '../../utils/utils';
|
|
|
|
|
import {PressableButton} from '../PressableButton';
|
|
|
|
|
import {PinnedItemList} from './PinnedItemList';
|
2020-04-20 10:54:58 +05:00
|
|
|
const sectionListRef = createRef();
|
2020-05-10 22:19:23 +05:00
|
|
|
|
|
|
|
|
const AnimatedFlatlist = Animatable.createAnimatableComponent(FlatList);
|
|
|
|
|
const AnimatedSectionList = Animatable.createAnimatableComponent(SectionList);
|
2020-03-09 20:06:55 +05:00
|
|
|
const SimpleList = ({
|
|
|
|
|
data,
|
|
|
|
|
type,
|
|
|
|
|
placeholder,
|
2020-05-10 22:19:23 +05:00
|
|
|
RenderItem,
|
2020-03-09 20:06:55 +05:00
|
|
|
focused,
|
|
|
|
|
placeholderText,
|
2020-03-09 20:15:00 +05:00
|
|
|
pinned = null,
|
2020-04-26 16:36:51 +05:00
|
|
|
customRefresh,
|
|
|
|
|
customRefreshing,
|
2020-03-17 10:02:34 +05:00
|
|
|
isMove,
|
|
|
|
|
hideMore,
|
|
|
|
|
noteToMove,
|
2020-04-20 10:54:58 +05:00
|
|
|
isHome = false,
|
2020-03-09 20:06:55 +05:00
|
|
|
}) => {
|
|
|
|
|
const [state, dispatch] = useTracked();
|
2020-05-14 14:52:56 +05:00
|
|
|
const {colors, selectionMode, user} = state;
|
2020-04-20 09:16:01 +05:00
|
|
|
const searchResults = {...state.searchResults};
|
2020-04-26 16:15:59 +05:00
|
|
|
const [refreshing, setRefreshing] = useState(false);
|
2020-04-16 13:57:51 +05:00
|
|
|
const insets = useSafeArea();
|
2020-09-07 19:19:54 +05:00
|
|
|
const _onScroll = (event) => {
|
2020-03-09 20:06:55 +05:00
|
|
|
if (!event) return;
|
|
|
|
|
let y = event.nativeEvent.contentOffset.y;
|
|
|
|
|
eSendEvent(eScrollEvent, y);
|
|
|
|
|
};
|
|
|
|
|
|
|
|
|
|
const _ListFooterComponent = data[0] ? (
|
|
|
|
|
<View
|
|
|
|
|
style={{
|
|
|
|
|
height: 150,
|
|
|
|
|
alignItems: 'center',
|
|
|
|
|
justifyContent: 'center',
|
|
|
|
|
}}>
|
|
|
|
|
<Text
|
|
|
|
|
style={{
|
2020-09-07 21:23:38 +05:00
|
|
|
color: colors.nav,
|
2020-03-09 20:06:55 +05:00
|
|
|
fontSize: SIZE.sm,
|
|
|
|
|
fontFamily: WEIGHT.regular,
|
|
|
|
|
}}>
|
|
|
|
|
- End -
|
|
|
|
|
</Text>
|
|
|
|
|
</View>
|
|
|
|
|
) : null;
|
|
|
|
|
|
2020-04-20 10:54:58 +05:00
|
|
|
const _renderSectionHeader = ({section: {title}}) => (
|
|
|
|
|
<Text
|
|
|
|
|
style={{
|
|
|
|
|
fontFamily: WEIGHT.bold,
|
|
|
|
|
fontSize: SIZE.xs + 1,
|
|
|
|
|
color: colors.accent,
|
|
|
|
|
paddingHorizontal: 12,
|
|
|
|
|
width: '100%',
|
|
|
|
|
alignSelf: 'center',
|
|
|
|
|
marginTop: 15,
|
|
|
|
|
paddingBottom: 5,
|
|
|
|
|
}}>
|
|
|
|
|
{title}
|
|
|
|
|
</Text>
|
|
|
|
|
);
|
|
|
|
|
|
2020-04-26 16:15:59 +05:00
|
|
|
const _onRefresh = async () => {
|
|
|
|
|
if (Platform.OS === 'ios') {
|
|
|
|
|
dispatch({
|
|
|
|
|
type: ACTIONS.SYNCING,
|
|
|
|
|
syncing: true,
|
|
|
|
|
});
|
|
|
|
|
} else {
|
|
|
|
|
setRefreshing(true);
|
|
|
|
|
}
|
|
|
|
|
try {
|
|
|
|
|
let user = await db.user.get();
|
|
|
|
|
dispatch({type: ACTIONS.USER, user: user});
|
|
|
|
|
await db.sync();
|
|
|
|
|
if (Platform.OS === 'ios') {
|
|
|
|
|
dispatch({
|
|
|
|
|
type: ACTIONS.SYNCING,
|
|
|
|
|
syncing: false,
|
|
|
|
|
});
|
|
|
|
|
} else {
|
|
|
|
|
setRefreshing(false);
|
|
|
|
|
}
|
|
|
|
|
ToastEvent.show('Sync Complete', 'success');
|
|
|
|
|
} catch (e) {
|
|
|
|
|
if (Platform.OS === 'ios') {
|
|
|
|
|
dispatch({
|
|
|
|
|
type: ACTIONS.SYNCING,
|
|
|
|
|
syncing: false,
|
|
|
|
|
});
|
|
|
|
|
} else {
|
|
|
|
|
setRefreshing(false);
|
|
|
|
|
}
|
2020-09-14 09:42:46 +05:00
|
|
|
ToastEvent.show(
|
|
|
|
|
e.message,
|
|
|
|
|
'error',
|
|
|
|
|
'global',
|
|
|
|
|
5000,
|
|
|
|
|
() => {
|
|
|
|
|
NavigationService.navigate('Login', {
|
|
|
|
|
root: true,
|
|
|
|
|
});
|
|
|
|
|
},
|
|
|
|
|
'Login',
|
|
|
|
|
);
|
2020-04-26 16:15:59 +05:00
|
|
|
}
|
|
|
|
|
dispatch({type: ACTIONS.ALL});
|
|
|
|
|
};
|
|
|
|
|
|
2020-03-09 20:06:55 +05:00
|
|
|
const _ListHeaderComponent_S =
|
|
|
|
|
searchResults.type === type && searchResults.results.length > 0 ? (
|
|
|
|
|
<View
|
|
|
|
|
style={{
|
|
|
|
|
marginTop:
|
|
|
|
|
Platform.OS == 'ios'
|
|
|
|
|
? data[0] && !selectionMode
|
2020-04-26 16:08:50 +05:00
|
|
|
? 115
|
|
|
|
|
: 115 - 60
|
2020-03-09 20:06:55 +05:00
|
|
|
: data[0] && !selectionMode
|
2020-04-20 10:54:58 +05:00
|
|
|
? 155 - insets.top
|
|
|
|
|
: 155 - insets.top - 60,
|
2020-03-09 20:06:55 +05:00
|
|
|
flexDirection: 'row',
|
|
|
|
|
alignItems: 'center',
|
|
|
|
|
justifyContent: 'space-between',
|
|
|
|
|
paddingHorizontal: 12,
|
|
|
|
|
}}>
|
|
|
|
|
<Text
|
|
|
|
|
style={{
|
|
|
|
|
fontFamily: WEIGHT.bold,
|
|
|
|
|
color: colors.accent,
|
|
|
|
|
fontSize: SIZE.xs,
|
|
|
|
|
}}>
|
2020-04-25 11:28:20 +05:00
|
|
|
Showing Results for {searchResults.keyword}
|
2020-03-09 20:06:55 +05:00
|
|
|
</Text>
|
|
|
|
|
<Text
|
|
|
|
|
onPress={() => {
|
2020-03-17 10:18:10 +05:00
|
|
|
eSendEvent(eClearSearch);
|
2020-03-09 20:06:55 +05:00
|
|
|
}}
|
|
|
|
|
style={{
|
|
|
|
|
fontFamily: WEIGHT.regular,
|
|
|
|
|
color: colors.errorText,
|
|
|
|
|
fontSize: SIZE.xs,
|
|
|
|
|
}}>
|
|
|
|
|
Clear
|
|
|
|
|
</Text>
|
|
|
|
|
</View>
|
|
|
|
|
) : (
|
2020-04-20 09:16:01 +05:00
|
|
|
<View
|
|
|
|
|
style={{
|
|
|
|
|
marginTop:
|
|
|
|
|
Platform.OS == 'ios'
|
|
|
|
|
? data[0] && !selectionMode
|
2020-04-28 18:12:46 +05:00
|
|
|
? 135
|
|
|
|
|
: 135 - 60
|
2020-04-20 09:16:01 +05:00
|
|
|
: data[0] && !selectionMode
|
2020-04-20 10:54:58 +05:00
|
|
|
? 155 - insets.top
|
|
|
|
|
: 155 - 60 - insets.top,
|
2020-04-20 09:16:01 +05:00
|
|
|
}}>
|
2020-08-16 18:59:07 +05:00
|
|
|
{user || !data[0] || selectionMode ? null : (
|
2020-09-08 22:23:44 +05:00
|
|
|
<PressableButton
|
2020-05-14 14:52:56 +05:00
|
|
|
onPress={() => {
|
|
|
|
|
DDS.isTab
|
|
|
|
|
? eSendEvent(eOpenLoginDialog)
|
|
|
|
|
: NavigationService.navigate('Login', {
|
|
|
|
|
root: true,
|
|
|
|
|
});
|
|
|
|
|
}}
|
2020-09-08 22:23:44 +05:00
|
|
|
color={colors.shade}
|
|
|
|
|
selectedColor={colors.accent}
|
|
|
|
|
alpha={!colors.night ? -0.02 : 0.1}
|
|
|
|
|
opacity={0.12}
|
|
|
|
|
customStyle={{
|
2020-08-16 18:59:07 +05:00
|
|
|
paddingVertical: 6,
|
2020-05-14 14:52:56 +05:00
|
|
|
width: '100%',
|
|
|
|
|
flexDirection: 'row',
|
|
|
|
|
alignItems: 'center',
|
|
|
|
|
justifyContent: 'flex-start',
|
|
|
|
|
paddingHorizontal: 12,
|
2020-08-16 18:59:07 +05:00
|
|
|
alignSelf: 'center',
|
2020-05-14 14:52:56 +05:00
|
|
|
}}>
|
|
|
|
|
<View
|
|
|
|
|
style={{
|
|
|
|
|
width: 25,
|
|
|
|
|
backgroundColor: colors.accent,
|
|
|
|
|
height: 25,
|
|
|
|
|
borderRadius: 100,
|
|
|
|
|
alignItems: 'center',
|
|
|
|
|
justifyContent: 'center',
|
|
|
|
|
}}>
|
|
|
|
|
<Icon
|
|
|
|
|
style={{
|
|
|
|
|
textAlign: 'center',
|
|
|
|
|
textAlignVertical: 'center',
|
|
|
|
|
}}
|
|
|
|
|
name="account-outline"
|
|
|
|
|
color="white"
|
|
|
|
|
size={SIZE.xs}
|
|
|
|
|
/>
|
|
|
|
|
</View>
|
|
|
|
|
<View
|
|
|
|
|
style={{
|
|
|
|
|
marginLeft: 10,
|
|
|
|
|
}}>
|
|
|
|
|
<Text
|
|
|
|
|
style={{
|
|
|
|
|
fontFamily: WEIGHT.regular,
|
|
|
|
|
color: colors.icon,
|
|
|
|
|
fontSize: SIZE.xxs - 1,
|
|
|
|
|
}}>
|
|
|
|
|
You are not logged in
|
|
|
|
|
</Text>
|
|
|
|
|
<Text
|
|
|
|
|
style={{
|
|
|
|
|
color: colors.accent,
|
|
|
|
|
fontSize: SIZE.xxs,
|
|
|
|
|
}}>
|
|
|
|
|
Login to sync your {type}.
|
|
|
|
|
</Text>
|
|
|
|
|
</View>
|
2020-09-08 22:23:44 +05:00
|
|
|
</PressableButton>
|
2020-05-14 14:52:56 +05:00
|
|
|
)}
|
|
|
|
|
{pinned ? <PinnedItemList type={type} /> : null}
|
2020-04-20 09:16:01 +05:00
|
|
|
</View>
|
|
|
|
|
);
|
2020-03-09 20:06:55 +05:00
|
|
|
|
|
|
|
|
const _ListEmptyComponent = (
|
|
|
|
|
<View
|
|
|
|
|
style={{
|
|
|
|
|
height: '80%',
|
|
|
|
|
width: '100%',
|
|
|
|
|
alignItems: 'center',
|
|
|
|
|
alignSelf: 'center',
|
|
|
|
|
justifyContent: 'center',
|
2020-03-19 11:04:47 +05:00
|
|
|
opacity: 1,
|
2020-03-09 20:06:55 +05:00
|
|
|
}}>
|
2020-08-16 18:59:07 +05:00
|
|
|
<>{placeholder}</>
|
2020-03-09 20:06:55 +05:00
|
|
|
</View>
|
|
|
|
|
);
|
|
|
|
|
|
|
|
|
|
const _listKeyExtractor = (item, index) =>
|
2020-03-22 12:39:35 +05:00
|
|
|
item.id.toString() + index.toString();
|
2020-03-09 20:06:55 +05:00
|
|
|
|
2020-04-20 10:54:58 +05:00
|
|
|
return isHome && searchResults.type !== 'notes' ? (
|
2020-05-10 22:19:23 +05:00
|
|
|
<AnimatedSectionList
|
|
|
|
|
transition="backgroundColor"
|
|
|
|
|
duration={300}
|
2020-04-20 10:54:58 +05:00
|
|
|
ref={sectionListRef}
|
|
|
|
|
sections={data}
|
|
|
|
|
refreshControl={
|
|
|
|
|
<RefreshControl
|
|
|
|
|
tintColor={colors.accent}
|
|
|
|
|
colors={[colors.accent]}
|
2020-04-26 16:08:50 +05:00
|
|
|
progressViewOffset={150}
|
2020-04-26 16:15:59 +05:00
|
|
|
onRefresh={_onRefresh}
|
2020-04-26 16:27:54 +05:00
|
|
|
refreshing={refreshing}
|
2020-04-20 10:54:58 +05:00
|
|
|
/>
|
|
|
|
|
}
|
|
|
|
|
keyExtractor={_listKeyExtractor}
|
|
|
|
|
renderSectionHeader={_renderSectionHeader}
|
|
|
|
|
onScroll={_onScroll}
|
2020-04-26 16:08:50 +05:00
|
|
|
stickySectionHeadersEnabled={false}
|
2020-04-20 10:54:58 +05:00
|
|
|
ListEmptyComponent={_ListEmptyComponent}
|
|
|
|
|
ListHeaderComponent={_ListHeaderComponent_S}
|
|
|
|
|
contentContainerStyle={{
|
|
|
|
|
width: '100%',
|
|
|
|
|
alignSelf: 'center',
|
|
|
|
|
minHeight: '100%',
|
|
|
|
|
}}
|
|
|
|
|
style={{
|
|
|
|
|
height: '100%',
|
2020-05-10 22:19:23 +05:00
|
|
|
backgroundColor: colors.bg,
|
2020-04-20 10:54:58 +05:00
|
|
|
}}
|
|
|
|
|
removeClippedSubviews={true}
|
|
|
|
|
ListFooterComponent={_ListFooterComponent}
|
2020-05-10 22:19:23 +05:00
|
|
|
renderItem={({item, index}) => <RenderItem item={item} index={index} />}
|
2020-04-20 10:54:58 +05:00
|
|
|
/>
|
|
|
|
|
) : (
|
2020-05-10 22:19:23 +05:00
|
|
|
<AnimatedFlatlist
|
|
|
|
|
transition="backgroundColor"
|
|
|
|
|
duration={300}
|
2020-03-09 20:06:55 +05:00
|
|
|
data={
|
|
|
|
|
searchResults.type === type &&
|
2020-04-20 09:16:01 +05:00
|
|
|
focused &&
|
|
|
|
|
searchResults.results.length > 0
|
2020-03-09 20:06:55 +05:00
|
|
|
? searchResults.results
|
|
|
|
|
: data
|
|
|
|
|
}
|
|
|
|
|
refreshControl={
|
|
|
|
|
<RefreshControl
|
|
|
|
|
tintColor={colors.accent}
|
|
|
|
|
colors={[colors.accent]}
|
2020-04-26 16:36:51 +05:00
|
|
|
progressViewOffset={150}
|
|
|
|
|
onRefresh={customRefresh ? customRefresh : _onRefresh}
|
|
|
|
|
refreshing={customRefresh ? customRefreshing : refreshing}
|
2020-03-09 20:06:55 +05:00
|
|
|
/>
|
|
|
|
|
}
|
|
|
|
|
keyExtractor={_listKeyExtractor}
|
|
|
|
|
ListFooterComponent={_ListFooterComponent}
|
|
|
|
|
onScroll={_onScroll}
|
|
|
|
|
ListHeaderComponent={_ListHeaderComponent_S}
|
|
|
|
|
ListEmptyComponent={_ListEmptyComponent}
|
|
|
|
|
contentContainerStyle={{
|
|
|
|
|
width: '100%',
|
|
|
|
|
alignSelf: 'center',
|
|
|
|
|
minHeight: '100%',
|
|
|
|
|
}}
|
|
|
|
|
style={{
|
|
|
|
|
height: '100%',
|
2020-05-10 22:19:23 +05:00
|
|
|
backgroundColor: colors.bg,
|
2020-03-09 20:06:55 +05:00
|
|
|
}}
|
2020-05-10 22:19:23 +05:00
|
|
|
renderItem={({item, index}) => <RenderItem item={item} index={index} />}
|
2020-03-09 20:06:55 +05:00
|
|
|
/>
|
|
|
|
|
);
|
|
|
|
|
};
|
|
|
|
|
|
|
|
|
|
export default SimpleList;
|