implement direct search and show featured claim result (#468)
This commit is contained in:
parent
bac202d4ec
commit
e402a0376a
5 changed files with 78 additions and 18 deletions
|
@ -51,6 +51,7 @@ class FileListItem extends React.PureComponent {
|
||||||
claim,
|
claim,
|
||||||
fileInfo,
|
fileInfo,
|
||||||
metadata,
|
metadata,
|
||||||
|
featuredResult,
|
||||||
isResolvingUri,
|
isResolvingUri,
|
||||||
isDownloaded,
|
isDownloaded,
|
||||||
style,
|
style,
|
||||||
|
@ -72,6 +73,10 @@ class FileListItem extends React.PureComponent {
|
||||||
fullChannelUri = channelClaimId ? `${channel}#${channelClaimId}` : channel;
|
fullChannelUri = channelClaimId ? `${channel}#${channelClaimId}` : channel;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (featuredResult && !isResolvingUri && !claim && !title && !name) {
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<View style={style}>
|
<View style={style}>
|
||||||
<TouchableOpacity style={style} onPress={onPress}>
|
<TouchableOpacity style={style} onPress={onPress}>
|
||||||
|
@ -81,15 +86,17 @@ class FileListItem extends React.PureComponent {
|
||||||
title={(title || name)}
|
title={(title || name)}
|
||||||
thumbnail={metadata ? metadata.thumbnail : null} />
|
thumbnail={metadata ? metadata.thumbnail : null} />
|
||||||
<View style={fileListStyle.detailsContainer}>
|
<View style={fileListStyle.detailsContainer}>
|
||||||
|
{featuredResult && <Text style={fileListStyle.featuredUri} numberOfLines={1}>{uri}</Text>}
|
||||||
|
|
||||||
{!title && !name && !channel && isResolving && (
|
{!title && !name && !channel && isResolving && (
|
||||||
<View>
|
<View>
|
||||||
{(!title && !name) && <Text style={fileListStyle.uri}>{uri}</Text>}
|
{(!title && !name) && <Text style={fileListStyle.uri}>{uri}</Text>}
|
||||||
{(!title && !name) && <View style={fileListStyle.row}>
|
{(!title && !name) && <View style={fileListStyle.row}>
|
||||||
<ActivityIndicator size={"small"} color={Colors.LbryGreen} />
|
<ActivityIndicator size={"small"} color={featuredResult ? Colors.White : Colors.LbryGreen} />
|
||||||
</View>}
|
</View>}
|
||||||
</View>)}
|
</View>)}
|
||||||
|
|
||||||
{(title || name) && <Text style={fileListStyle.title}>{this.formatTitle(title) || this.formatTitle(name)}</Text>}
|
{(title || name) && <Text style={featuredResult ? fileListStyle.featuredTitle : fileListStyle.title}>{this.formatTitle(title) || this.formatTitle(name)}</Text>}
|
||||||
{channel &&
|
{channel &&
|
||||||
<Link style={fileListStyle.publisher} text={channel} onPress={() => {
|
<Link style={fileListStyle.publisher} text={channel} onPress={() => {
|
||||||
navigateToUri(navigation, normalizeURI(fullChannelUri));
|
navigateToUri(navigation, normalizeURI(fullChannelUri));
|
||||||
|
|
|
@ -32,17 +32,29 @@ class UriBar extends React.PureComponent {
|
||||||
changeTextTimeout: null,
|
changeTextTimeout: null,
|
||||||
currentValue: null,
|
currentValue: null,
|
||||||
inputText: null,
|
inputText: null,
|
||||||
focused: false
|
focused: false,
|
||||||
|
// TODO: Add a setting to enable / disable direct search?
|
||||||
|
directSearch: true
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
handleChangeText = text => {
|
handleChangeText = text => {
|
||||||
const newValue = text ? text : '';
|
const newValue = text ? text : '';
|
||||||
clearTimeout(this.state.changeTextTimeout);
|
clearTimeout(this.state.changeTextTimeout);
|
||||||
const { updateSearchQuery } = this.props;
|
const { updateSearchQuery, onSearchSubmitted, navigation } = this.props;
|
||||||
|
|
||||||
let timeout = setTimeout(() => {
|
let timeout = setTimeout(() => {
|
||||||
updateSearchQuery(text);
|
updateSearchQuery(text);
|
||||||
|
|
||||||
|
if (!text.startsWith('lbry://')) {
|
||||||
|
// not a URI input, so this is a search, perform a direct search
|
||||||
|
if (onSearchSubmitted) {
|
||||||
|
onSearchSubmitted(text);
|
||||||
|
} else {
|
||||||
|
navigation.navigate({ routeName: 'Search', key: 'searchPage', params: { searchQuery: text }});
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
}, UriBar.INPUT_TIMEOUT);
|
}, UriBar.INPUT_TIMEOUT);
|
||||||
this.setState({ inputText: newValue, currentValue: newValue, changeTextTimeout: timeout });
|
this.setState({ inputText: newValue, currentValue: newValue, changeTextTimeout: timeout });
|
||||||
}
|
}
|
||||||
|
@ -141,7 +153,7 @@ class UriBar extends React.PureComponent {
|
||||||
}
|
}
|
||||||
}}/>
|
}}/>
|
||||||
</View>
|
</View>
|
||||||
{this.state.focused && (
|
{(this.state.focused && !this.state.directSearch) && (
|
||||||
<View style={uriBarStyle.suggestions}>
|
<View style={uriBarStyle.suggestions}>
|
||||||
<FlatList style={uriBarStyle.suggestionList}
|
<FlatList style={uriBarStyle.suggestionList}
|
||||||
data={suggestions}
|
data={suggestions}
|
||||||
|
|
|
@ -1,5 +1,5 @@
|
||||||
import React from 'react';
|
import React from 'react';
|
||||||
import { Lbry } from 'lbry-redux';
|
import { Lbry, parseURI, normalizeURI, isURIValid } from 'lbry-redux';
|
||||||
import {
|
import {
|
||||||
ActivityIndicator,
|
ActivityIndicator,
|
||||||
Button,
|
Button,
|
||||||
|
@ -8,15 +8,19 @@ import {
|
||||||
View,
|
View,
|
||||||
ScrollView
|
ScrollView
|
||||||
} from 'react-native';
|
} from 'react-native';
|
||||||
import { navigateToUri } from '../../utils/helper';
|
import { navigateToUri } from 'utils/helper';
|
||||||
import Colors from '../../styles/colors';
|
import Colors from 'styles/colors';
|
||||||
import PageHeader from '../../component/pageHeader';
|
import PageHeader from 'component/pageHeader';
|
||||||
import FileListItem from '../../component/fileListItem';
|
import FileListItem from 'component/fileListItem';
|
||||||
import FloatingWalletBalance from '../../component/floatingWalletBalance';
|
import FloatingWalletBalance from 'component/floatingWalletBalance';
|
||||||
import UriBar from '../../component/uriBar';
|
import UriBar from 'component/uriBar';
|
||||||
import searchStyle from '../../styles/search';
|
import searchStyle from 'styles/search';
|
||||||
|
|
||||||
class SearchPage extends React.PureComponent {
|
class SearchPage extends React.PureComponent {
|
||||||
|
state = {
|
||||||
|
currentUri: null
|
||||||
|
}
|
||||||
|
|
||||||
static navigationOptions = {
|
static navigationOptions = {
|
||||||
title: 'Search Results'
|
title: 'Search Results'
|
||||||
};
|
};
|
||||||
|
@ -29,22 +33,38 @@ class SearchPage extends React.PureComponent {
|
||||||
const { navigation, search } = this.props;
|
const { navigation, search } = this.props;
|
||||||
const { searchQuery } = navigation.state.params;
|
const { searchQuery } = navigation.state.params;
|
||||||
if (searchQuery && searchQuery.trim().length > 0) {
|
if (searchQuery && searchQuery.trim().length > 0) {
|
||||||
|
this.setState({ currentUri: (isURIValid(searchQuery)) ? normalizeURI(searchQuery) : null })
|
||||||
search(searchQuery);
|
search(searchQuery);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
handleSearchSubmitted = (keywords) => {
|
||||||
|
const { search } = this.props;
|
||||||
|
this.setState({ currentUri: (isURIValid(keywords)) ? normalizeURI(keywords) : null });
|
||||||
|
search(keywords);
|
||||||
|
}
|
||||||
|
|
||||||
render() {
|
render() {
|
||||||
const { isSearching, navigation, query, search, uris } = this.props;
|
const { isSearching, navigation, query, uris } = this.props;
|
||||||
const { searchQuery } = navigation.state.params;
|
const { searchQuery } = navigation.state.params;
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<View style={searchStyle.container}>
|
<View style={searchStyle.container}>
|
||||||
<UriBar value={searchQuery}
|
<UriBar value={searchQuery}
|
||||||
navigation={navigation}
|
navigation={navigation}
|
||||||
onSearchSubmitted={(keywords) => search(keywords)} />
|
onSearchSubmitted={this.handleSearchSubmitted} />
|
||||||
{!isSearching && (!uris || uris.length === 0) &&
|
{!isSearching && (!uris || uris.length === 0) &&
|
||||||
<Text style={searchStyle.noResultsText}>No results to display.</Text>}
|
<Text style={searchStyle.noResultsText}>No results to display.</Text>}
|
||||||
<ScrollView style={searchStyle.scrollContainer} contentContainerStyle={searchStyle.scrollPadding}>
|
<ScrollView style={searchStyle.scrollContainer} contentContainerStyle={searchStyle.scrollPadding}>
|
||||||
|
{this.state.currentUri &&
|
||||||
|
<FileListItem
|
||||||
|
key={this.state.currentUri}
|
||||||
|
uri={this.state.currentUri}
|
||||||
|
featuredResult={true}
|
||||||
|
style={searchStyle.featuredResultItem}
|
||||||
|
navigation={navigation}
|
||||||
|
onPress={() => navigateToUri(navigation, this.state.currentUri)}
|
||||||
|
/>}
|
||||||
{!isSearching && uris && uris.length ? (
|
{!isSearching && uris && uris.length ? (
|
||||||
uris.map(uri => <FileListItem key={uri}
|
uris.map(uri => <FileListItem key={uri}
|
||||||
uri={uri}
|
uri={uri}
|
||||||
|
|
|
@ -20,6 +20,16 @@ const fileListStyle = StyleSheet.create({
|
||||||
detailsContainer: {
|
detailsContainer: {
|
||||||
flex: 1
|
flex: 1
|
||||||
},
|
},
|
||||||
|
featuredUri: {
|
||||||
|
fontFamily: 'Inter-UI-SemiBold',
|
||||||
|
fontSize: 24,
|
||||||
|
color: Colors.White
|
||||||
|
},
|
||||||
|
featuredTitle: {
|
||||||
|
fontFamily: 'Inter-UI-SemiBold',
|
||||||
|
fontSize: (screenWidthPixels <= 720) ? 12 : 16,
|
||||||
|
color: Colors.White
|
||||||
|
},
|
||||||
thumbnail: {
|
thumbnail: {
|
||||||
width: thumbnailWidth,
|
width: thumbnailWidth,
|
||||||
height: thumbnailHeight,
|
height: thumbnailHeight,
|
||||||
|
|
|
@ -1,4 +1,5 @@
|
||||||
import { StyleSheet } from 'react-native';
|
import { StyleSheet } from 'react-native';
|
||||||
|
import Colors from 'styles/colors';
|
||||||
|
|
||||||
const searchStyle = StyleSheet.create({
|
const searchStyle = StyleSheet.create({
|
||||||
container: {
|
container: {
|
||||||
|
@ -10,8 +11,6 @@ const searchStyle = StyleSheet.create({
|
||||||
flex: 1,
|
flex: 1,
|
||||||
width: '100%',
|
width: '100%',
|
||||||
height: '100%',
|
height: '100%',
|
||||||
paddingLeft: 16,
|
|
||||||
paddingRight: 16,
|
|
||||||
marginTop: 60
|
marginTop: 60
|
||||||
},
|
},
|
||||||
scrollPadding: {
|
scrollPadding: {
|
||||||
|
@ -21,7 +20,19 @@ const searchStyle = StyleSheet.create({
|
||||||
flex: 1,
|
flex: 1,
|
||||||
flexDirection: 'row',
|
flexDirection: 'row',
|
||||||
justifyContent: 'space-between',
|
justifyContent: 'space-between',
|
||||||
marginTop: 8
|
marginTop: 8,
|
||||||
|
marginLeft: 8,
|
||||||
|
marginRight: 8
|
||||||
|
},
|
||||||
|
featuredResultItem: {
|
||||||
|
flex: 1,
|
||||||
|
flexDirection: 'row',
|
||||||
|
justifyContent: 'space-between',
|
||||||
|
paddingTop: 8,
|
||||||
|
paddingBottom: 8,
|
||||||
|
paddingLeft: 8,
|
||||||
|
paddingRight: 8,
|
||||||
|
backgroundColor: Colors.Black
|
||||||
},
|
},
|
||||||
searchInput: {
|
searchInput: {
|
||||||
width: '100%',
|
width: '100%',
|
||||||
|
|
Loading…
Add table
Reference in a new issue