[MM-48225] Reduce Padding/Margins from Files Tab and moving the Search Results to the FlatList (#7430)

* feat: reducing the padding/margins of tabs and filter icons on the Search Page

* feat: adds the results text inside the post_results and file_results

* feat: changes search results to use translation

* feat: updates text on search results to use FormattedText

* feat: removing text wrapper

* feat: removing margins and using an ItemSeparator to separate the rows of the file results

* feat: refactor spacing on post results and unnecessary top

* review: externalizing Separator on the file_results

* feat: add marginTop in all File components used inside the <Files> component
This commit is contained in:
Lucas Reis 2023-07-25 05:11:37 -03:00 committed by GitHub
parent aeba5ed6d2
commit 722871d165
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
10 changed files with 90 additions and 46 deletions

View file

@ -44,7 +44,6 @@ const getStyleSheet = makeStyleSheetFromTheme((theme: Theme) => {
flex: 1,
flexDirection: 'row',
alignItems: 'center',
marginTop: 10,
borderWidth: 1,
borderColor: changeOpacity(theme.centerChannelColor, 0.24),
borderRadius: 4,

View file

@ -43,6 +43,9 @@ const styles = StyleSheet.create({
failed: {
opacity: 0.5,
},
marginTop: {
marginTop: 10,
},
});
const Files = ({canDownloadFiles, failed, filesInfo, isReplyPost, layoutWidth, location, postId, publicLinkEnabled}: FilesProps) => {
@ -86,7 +89,7 @@ const Files = ({canDownloadFiles, failed, filesInfo, isReplyPost, layoutWidth, l
}
return (
<View
style={container}
style={[container, styles.marginTop]}
key={file.id}
>
<File

View file

@ -2,10 +2,11 @@
// See LICENSE.txt for license information.
import React, {useCallback, useMemo, useState} from 'react';
import {FlatList, type ListRenderItemInfo, type StyleProp, type ViewStyle} from 'react-native';
import {FlatList, type ListRenderItemInfo, type StyleProp, type ViewStyle, View} from 'react-native';
import {useSafeAreaInsets} from 'react-native-safe-area-context';
import NoResults from '@components/files_search/no_results';
import FormattedText from '@components/formatted_text';
import NoResultsWithTerm from '@components/no_results_with_term';
import {useTheme} from '@context/theme';
import {useIsTablet} from '@hooks/device';
@ -20,6 +21,8 @@ import {
import {openGalleryAtIndex} from '@utils/gallery';
import {TabTypes} from '@utils/search';
import {preventDoubleTap} from '@utils/tap';
import {makeStyleSheetFromTheme} from '@utils/theme';
import {typography} from '@utils/typography';
import {showMobileOptionsBottomSheet} from './file_options/mobile_options';
import Toasts from './file_options/toasts';
@ -28,6 +31,14 @@ import FileResult from './file_result';
import type ChannelModel from '@typings/database/models/servers/channel';
import type {GalleryAction} from '@typings/screens/gallery';
const getStyles = makeStyleSheetFromTheme((theme: Theme) => ({
resultsNumber: {
...typography('Heading', 300),
padding: 20,
color: theme.centerChannelColor,
},
}));
type Props = {
canDownloadFiles: boolean;
fileChannels: ChannelModel[];
@ -41,6 +52,9 @@ type Props = {
const galleryIdentifier = 'search-files-location';
const separatorStyle = {height: 10};
const Separator = () => <View style={separatorStyle}/>;
const FileResults = ({
canDownloadFiles,
fileChannels,
@ -52,13 +66,14 @@ const FileResults = ({
isFilterEnabled,
}: Props) => {
const theme = useTheme();
const styles = getStyles(theme);
const insets = useSafeAreaInsets();
const isTablet = useIsTablet();
const [action, setAction] = useState<GalleryAction>('none');
const [lastViewedFileInfo, setLastViewedFileInfo] = useState<FileInfo | undefined>(undefined);
const containerStyle = useMemo(() => ([paddingTop, {top: fileInfos.length ? 8 : 0, flexGrow: 1}]), [fileInfos, paddingTop]);
const containerStyle = useMemo(() => ([paddingTop, {flexGrow: 1}]), [paddingTop]);
const numOptions = getNumberFileMenuOptions(canDownloadFiles, publicLinkEnabled);
const {images: imageAttachments, nonImages: nonImageAttachments} = useImageAttachments(fileInfos, publicLinkEnabled);
@ -141,6 +156,15 @@ const FileResults = ({
return (
<>
<FlatList
ListHeaderComponent={
<FormattedText
style={styles.resultsNumber}
id='mobile.search.results'
defaultMessage='{count} search {count, plural, one {result} other {results}}'
values={{count: orderedFileInfos.length}}
/>
}
ItemSeparatorComponent={Separator}
ListEmptyComponent={noResults}
contentContainerStyle={containerStyle}
data={orderedFileInfos}

View file

@ -27,8 +27,6 @@ type Props = {
onFilterChanged: (filter: FileFilter) => void;
selectedTab: TabType;
selectedFilter: FileFilter;
numberMessages: number;
numberFiles: number;
setTeamId: (id: string) => void;
teamId: string;
teams: TeamModel[];
@ -65,8 +63,6 @@ const Header = ({
setTeamId,
onTabSelect,
onFilterChanged,
numberMessages,
numberFiles,
selectedTab,
selectedFilter,
teams,
@ -122,7 +118,7 @@ const Header = ({
});
}, [onFilterChanged, selectedFilter]);
const filterStyle = useMemo(() => ({marginRight: teams.length > 1 ? 0 : 10}), [teams.length > 1]);
const filterStyle = useMemo(() => ({marginRight: teams.length > 1 ? 0 : 8}), [teams.length > 1]);
return (
<View style={styles.container}>
@ -130,39 +126,42 @@ const Header = ({
<SelectButton
selected={selectedTab === TabTypes.MESSAGES}
onPress={handleMessagesPress}
text={`${messagesText} (${numberMessages})`}
text={messagesText}
/>
<SelectButton
selected={selectedTab === TabTypes.FILES}
onPress={handleFilesPress}
text={`${filesText} (${numberFiles})`}
text={filesText}
/>
<View style={styles.iconsContainer}>
{showFilterIcon &&
<View style={filterStyle}>
<CompassIcon
name={'filter-variant'}
size={24}
color={changeOpacity(theme.centerChannelColor, 0.56)}
onPress={handleFilterPress}
{showFilterIcon && (
<View style={filterStyle}>
<CompassIcon
name={'filter-variant'}
size={24}
color={changeOpacity(
theme.centerChannelColor,
0.56,
)}
onPress={handleFilterPress}
/>
<Badge
style={styles.badge}
visible={hasFilters}
testID={'search.filters.badge'}
value={-1}
/>
</View>
)}
{teams.length > 1 && (
<TeamPickerIcon
size={32}
divider={true}
setTeamId={setTeamId}
teamId={teamId}
teams={teams}
/>
<Badge
style={styles.badge}
visible={hasFilters}
testID={'search.filters.badge'}
value={-1}
/>
</View>
}
{teams.length > 1 &&
<TeamPickerIcon
size={32}
divider={true}
setTeamId={setTeamId}
teamId={teamId}
teams={teams}
/>
}
)}
</View>
</View>
</View>
@ -170,4 +169,3 @@ const Header = ({
};
export default Header;

View file

@ -16,7 +16,7 @@ const getStyleFromTheme = makeStyleSheetFromTheme((theme) => {
borderRadius: 4,
},
text: {
paddingHorizontal: 16,
paddingHorizontal: 12,
paddingVertical: 8,
...typography('Body', 200, 'SemiBold'),
},

View file

@ -4,18 +4,30 @@
import React, {useCallback, useMemo} from 'react';
import {FlatList, type ListRenderItemInfo, type StyleProp, type ViewStyle} from 'react-native';
import FormattedText from '@components/formatted_text';
import NoResultsWithTerm from '@components/no_results_with_term';
import DateSeparator from '@components/post_list/date_separator';
import PostWithChannelInfo from '@components/post_with_channel_info';
import {Screens} from '@constants';
import {useTheme} from '@context/theme';
import {convertSearchTermToRegex, parseSearchTerms} from '@utils/markdown';
import {getDateForDateLine, selectOrderedPosts} from '@utils/post_list';
import {TabTypes} from '@utils/search';
import {makeStyleSheetFromTheme} from '@utils/theme';
import {typography} from '@utils/typography';
import type {PostListItem, PostListOtherItem} from '@typings/components/post_list';
import type PostModel from '@typings/database/models/servers/post';
import type {SearchPattern} from '@typings/global/markdown';
const getStyles = makeStyleSheetFromTheme((theme: Theme) => ({
resultsNumber: {
...typography('Heading', 300),
padding: 20,
color: theme.centerChannelColor,
},
}));
type Props = {
appsEnabled: boolean;
customEmojiNames: string[];
@ -37,8 +49,10 @@ const PostResults = ({
paddingTop,
searchValue,
}: Props) => {
const theme = useTheme();
const styles = getStyles(theme);
const orderedPosts = useMemo(() => selectOrderedPosts(posts, 0, false, '', '', false, isTimezoneEnabled, currentTimezone, false).reverse(), [posts]);
const containerStyle = useMemo(() => ({top: posts.length ? 4 : 8, flexGrow: 1}), [posts]);
const containerStyle = useMemo(() => ([paddingTop, {flexGrow: 1}]), [paddingTop]);
const renderItem = useCallback(({item}: ListRenderItemInfo<PostListItem | PostListOtherItem>) => {
switch (item.type) {
@ -88,8 +102,16 @@ const PostResults = ({
return (
<FlatList
ListHeaderComponent={
<FormattedText
style={styles.resultsNumber}
id='mobile.search.results'
defaultMessage='{count} search {count, plural, one {result} other {results}}'
values={{count: posts.length}}
/>
}
ListEmptyComponent={noResults}
contentContainerStyle={[paddingTop, containerStyle]}
contentContainerStyle={containerStyle}
data={orderedPosts}
indicatorStyle='black'
initialNumToRender={5}
@ -104,7 +126,6 @@ const PostResults = ({
scrollEventThrottle={16}
scrollToOverflowEnabled={true}
showsVerticalScrollIndicator={true}
style={containerStyle}
testID='search_results.post_list.flat_list'
/>
);

View file

@ -100,7 +100,7 @@ const Results = ({
}
{!loading &&
<Animated.View style={[styles.container, transform]}>
<View style={styles.result} >
<View style={styles.result}>
<PostResults
appsEnabled={appsEnabled}
currentTimezone={currentTimezone}
@ -112,7 +112,7 @@ const Results = ({
searchValue={searchValue}
/>
</View>
<View style={styles.result} >
<View style={styles.result}>
<FileResults
canDownloadFiles={canDownloadFiles}
fileChannels={fileChannels}

View file

@ -372,9 +372,7 @@ const SearchScreen = ({teamId, teams}: Props) => {
setTeamId={handleResultsTeamChange}
onTabSelect={setSelectedTab}
onFilterChanged={handleFilterChange}
numberMessages={posts.length}
selectedTab={selectedTab}
numberFiles={fileInfos.length}
selectedFilter={filter}
teams={teams}
/>

View file

@ -28,7 +28,7 @@ const NO_TEAMS_HEIGHT = 392;
const getStyleFromTheme = makeStyleSheetFromTheme((theme) => {
return {
teamContainer: {
paddingLeft: 12,
paddingLeft: 8,
flexDirection: 'row',
alignItems: 'center',
},

View file

@ -681,6 +681,7 @@
"mobile.search.show_less": "Show less",
"mobile.search.show_more": "Show more",
"mobile.search.team.select": "Select a team to search",
"mobile.search.results": "{count} search {count, plural, one {result} other {results}}",
"mobile.server_identifier.exists": "You are already connected to this server.",
"mobile.server_link.error.text": "The link could not be found on this server.",
"mobile.server_link.error.title": "Link Error",
@ -1061,4 +1062,4 @@
"video.download_description": "This video must be downloaded to play it.",
"video.failed_description": "An error occurred while trying to play the video.",
"your.servers": "Your servers"
}
}