diff --git a/.github/home-bottom.png b/.github/home-bottom.png new file mode 100644 index 0000000..6621c9c Binary files /dev/null and b/.github/home-bottom.png differ diff --git a/.github/home.png b/.github/home.png index bb88926..5e9834d 100644 Binary files a/.github/home.png and b/.github/home.png differ diff --git a/.github/movies.png b/.github/movies.png index b4b78df..d6c925f 100644 Binary files a/.github/movies.png and b/.github/movies.png differ diff --git a/.github/my-list.png b/.github/my-list.png new file mode 100644 index 0000000..5f45861 Binary files /dev/null and b/.github/my-list.png differ diff --git a/.github/show.png b/.github/show.png index 9c0cce9..e7aa03b 100644 Binary files a/.github/show.png and b/.github/show.png differ diff --git a/.github/shows.png b/.github/shows.png index 72245e7..72231ae 100644 Binary files a/.github/shows.png and b/.github/shows.png differ diff --git a/README.md b/README.md index 1270b81..f2a9f30 100644 --- a/README.md +++ b/README.md @@ -55,9 +55,13 @@ Please see the [contributing guide](https://github.com/tripss/popcorn-native/blo ## Screenshots -Home Screen | Movies Screen +Home Screen | Home Screen :-------------------------:|:-------------------------: -![Home Screen](./.github/home.png) | ![Movies Screen](./.github/movies.png) +![Home Screen](./.github/home.png) | ![Home Screen](./.github/home-bottom.png) + +My List Screen | Movies Screen +:-------------------------:|:-------------------------: +![My List Screen](./.github/my-list.png) |![Show Screen](./.github/movies.png) Shows Screen | Show Screen :-------------------------:|:-------------------------: diff --git a/android/app/build.gradle b/android/app/build.gradle index 8a1cdd1..bd92b66 100644 --- a/android/app/build.gradle +++ b/android/app/build.gradle @@ -107,8 +107,8 @@ android { applicationId "com.popcorn" minSdkVersion 16 targetSdkVersion 26 - versionCode 9 - versionName "v0.6.3" + versionCode 10 + versionName "v0.7.0" ndk { abiFilters "armeabi-v7a", "x86" } diff --git a/app/components/Card/Card.js b/app/components/Card/Card.js index b0b5897..238a281 100644 --- a/app/components/Card/Card.js +++ b/app/components/Card/Card.js @@ -10,7 +10,7 @@ const styles = StyleSheet.create({ root: { height : 190, - width : 120, + width : 121, marginLeft : 8, marginRight: 8, alignSelf : 'stretch', @@ -24,33 +24,56 @@ const styles = StyleSheet.create({ }) -export const Card = ({ item, empty, ...rest }) => ( - console.warn(item.title)} - // onPress={() => this.openItem(item)} - {...rest}> - - - - -) - -Card.propTypes = { - item : PropTypes.object, - empty: PropTypes.bool, -} +export default class Card extends React.Component { -Card.defaultProps = { - item : null, - empty: false, -} + static propTypes = { + item : PropTypes.object, + empty: PropTypes.bool, + } + + static defaultProps = { + item : null, + empty: false, + } + + constructor(props) { + super(props) + + const { item, empty } = props -export default Card + this.state = { + showPlaceholder: empty || !item.images.poster.thumb, + } + } + + handleImageError = () => { + this.setState({ + showPlaceholder: true, + }) + } + + render() { + const { item, empty, ...rest } = this.props + const { showPlaceholder } = this.state + + return ( + console.warn(item.title)} + // onPress={() => this.openItem(item)} + {...rest}> + + + + + ) + } +} diff --git a/app/components/Disclaimer/Disclaimer.js b/app/components/Disclaimer/Disclaimer.js index c3c4ca6..b3e1a1e 100644 --- a/app/components/Disclaimer/Disclaimer.js +++ b/app/components/Disclaimer/Disclaimer.js @@ -82,17 +82,19 @@ export default class CheckForUpdates extends React.Component { children: PropTypes.node.isRequired, } - state = { - accepted : false, - animating: false, - loading : true, + constructor(props, context) { + super(props, context) + + this.state = { + accepted : false, + animating: false, + } } componentWillMount() { Settings.getItem(Settings.DISCLAIMER_ACCEPTED).then((accepted) => { this.setState({ accepted: accepted && accepted === 'y', - loading : false, }, () => { if (!accepted) { SplashScreen.hide() @@ -122,7 +124,7 @@ export default class CheckForUpdates extends React.Component { render() { const { children } = this.props - const { animating, accepted, loading } = this.state + const { animating, accepted } = this.state return ( diff --git a/app/modules/BookmarkAdapter/BookmarkAdapter.js b/app/modules/BookmarkAdapter/BookmarkAdapter.js new file mode 100644 index 0000000..8e784c8 --- /dev/null +++ b/app/modules/BookmarkAdapter/BookmarkAdapter.js @@ -0,0 +1,31 @@ +import DefaultBookmarkAdapter from 'popcorn-sdk/BookmarkAdapter' + +import Bookmarks from '../db/Bookmarks' + +export default new (class BookmarkAdapter extends DefaultBookmarkAdapter { + + getAll = Bookmarks.getAll + + checkMovie = movie => new Promise(async(resolve) => { + const bookmarks = await Bookmarks.getAllMovies() + + resolve({ + ...movie, + bookmarked: bookmarks.filter(bookmark => bookmark.id === movie.id).length === 1, + }) + }) + + checkShow = show => new Promise(async(resolve) => { + const bookmarks = await Bookmarks.getAllShows() + + resolve({ + ...show, + bookmarked: bookmarks.filter(bookmark => bookmark.id === show.id).length === 1, + }) + }) + + addItem = Bookmarks.addItem + + removeItem = Bookmarks.removeItem + +})() diff --git a/app/modules/BookmarkAdapter/index.js b/app/modules/BookmarkAdapter/index.js new file mode 100644 index 0000000..fb9afa6 --- /dev/null +++ b/app/modules/BookmarkAdapter/index.js @@ -0,0 +1 @@ +export { default } from './BookmarkAdapter' diff --git a/app/modules/PopcornSDK.js b/app/modules/PopcornSDK.js new file mode 100644 index 0000000..5a8ea29 --- /dev/null +++ b/app/modules/PopcornSDK.js @@ -0,0 +1,8 @@ +import Popcorn from 'popcorn-sdk' + +import BookmarkAdapter from './BookmarkAdapter' + +const SDK = Popcorn +SDK.setBookmarkAdapter(BookmarkAdapter) + +export default SDK diff --git a/app/modules/db/Bookmarks.js b/app/modules/db/Bookmarks.js new file mode 100644 index 0000000..cc9434f --- /dev/null +++ b/app/modules/db/Bookmarks.js @@ -0,0 +1,55 @@ +import { Constants } from 'popcorn-sdk' +import Base from './Base' + +export default new (class BookmarksDB extends Base { + + KEY_BOOKMARKS = '@Popcorn:Bookmarks' + + bookmarks = [] + + getAll = async() => { + if (this.bookmarks.length > 0) { + return this.bookmarks + } + + const bookmarks = await this.getItem(this.KEY_BOOKMARKS) + + if (bookmarks) { + this.bookmarks = JSON.parse(bookmarks) + console.log('this.bookmarks', this.bookmarks) + return this.bookmarks + } + + return this.bookmarks + } + + getAllMovies = async() => { + await this.getAll() + + return this.bookmarks.filter(bookmark => bookmark.type === Constants.TYPE_MOVIE) + } + + getAllShows = async() => { + await this.getAll() + + return this.bookmarks.filter(bookmark => bookmark.type === Constants.TYPE_SHOW) + } + + addItem = ({ id, title, type, images }) => { + this.bookmarks.push({ + id, + title, + type, + images, + }) + + this.setItem(this.KEY_BOOKMARKS, JSON.stringify(this.bookmarks)) + } + + removeItem = ({ id }) => { + this.bookmarks = this.bookmarks.filter(bookmark => bookmark.id !== id) + + this.setItem(this.KEY_BOOKMARKS, JSON.stringify(this.bookmarks)) + } + +})() diff --git a/app/modules/db/Settings.js b/app/modules/db/Settings.js index 28bf559..e55b727 100644 --- a/app/modules/db/Settings.js +++ b/app/modules/db/Settings.js @@ -2,6 +2,6 @@ import Base from './Base' export default new (class SettingsDB extends Base { - DISCLAIMER_ACCEPTED = 'Settings.DISCLAIMER_ACCEPTED' + DISCLAIMER_ACCEPTED = '@Popcorn:Settings:DISCLAIMER_ACCEPTED' })() diff --git a/app/modules/i18n/translations/en.json b/app/modules/i18n/translations/en.json index 2cc7491..f2d861a 100644 --- a/app/modules/i18n/translations/en.json +++ b/app/modules/i18n/translations/en.json @@ -1,5 +1,6 @@ { "Home": "Home", + "My List": "My List", "Movies": "Movies", "Shows": "Shows", "Season {{number}}": "Season {{number}}", diff --git a/app/modules/i18n/translations/nl.json b/app/modules/i18n/translations/nl.json index 78e00e6..dd30b93 100644 --- a/app/modules/i18n/translations/nl.json +++ b/app/modules/i18n/translations/nl.json @@ -1,5 +1,6 @@ { "Home": "Home", + "My List": "Mijn Lijst", "Movies": "Films", "Shows": "Series", "Season {{number}}": "Seizoen {{number}}", diff --git a/app/screens/Home/HomeActions.js b/app/screens/Home/HomeActions.js index e70604c..d4bbecd 100644 --- a/app/screens/Home/HomeActions.js +++ b/app/screens/Home/HomeActions.js @@ -1,4 +1,5 @@ -import Popcorn, { Constants } from 'popcorn-sdk' +import { Constants } from 'popcorn-sdk' +import Popcorn from 'modules/PopcornSDK' import * as HomeConstants from './HomeConstants' import * as HomeSelectors from './HomeSelectors' @@ -42,9 +43,32 @@ export const getItems = (mode, page = 1, givenFilters = {}) => (dispatch, getSta case Constants.TYPE_MOVIE: return Popcorn.getMovies(page, filters).then(movies => dispatch(fetchedItems(movies, mode))).catch(catchNoCon) + case 'movieSearch': + // Clear the items + dispatch(clearItems(mode)) + + return Popcorn.getMovies(page, filters).then(movies => dispatch(fetchedItems(movies, mode))).catch(catchNoCon) + case Constants.TYPE_SHOW: return Popcorn.getShows(page, filters).then(shows => dispatch(fetchedItems(shows, mode))).catch(catchNoCon) + case 'showSearch': + // Clear the items + dispatch(clearItems(mode)) + + return Popcorn.getShows(page, filters).then(shows => dispatch(fetchedItems(shows, mode))).catch(catchNoCon) + + case Constants.TYPE_BOOKMARK: + return Popcorn.bookmarks.getAll().then(bookmarks => dispatch(fetchedItems(bookmarks, mode))) + + case 'bookmarkSearch': + return Popcorn.bookmarks.getAll().then(bookmarks => dispatch( + fetchedItems( + bookmarks.filter(bookmark => bookmark.title.toLowerCase().indexOf(filters.keywords.toLowerCase()) > -1), + mode, + ), + )) + default: return null } diff --git a/app/screens/Home/HomeConstants.js b/app/screens/Home/HomeConstants.js index dfc9372..28ca94f 100644 --- a/app/screens/Home/HomeConstants.js +++ b/app/screens/Home/HomeConstants.js @@ -4,10 +4,14 @@ export const INITIAL_STATE = { isLoading : true, hasInternet: true, modes : { - bookmark: { page: 1, items: [], filters: {} }, - movie : { page: 1, items: [], filters: { limit: 50, sort: 'trending' } }, - show : { page: 1, items: [], filters: { limit: 50, sort: 'trending' } }, - search : { page: 1, items: [], filters: {} }, + bookmark : { items: [] }, + bookmarkSearch: { items: [] }, + + movie : { page: 1, items: [], filters: { limit: 50, sort: 'trending' } }, + movieSearch : { page: 1, items: [], filters: {} }, + + show : { page: 1, items: [], filters: { limit: 50, sort: 'trending' } }, + showSearch : { page: 1, items: [], filters: {} }, }, } diff --git a/app/screens/Home/HomeReducer.js b/app/screens/Home/HomeReducer.js index a16db2f..e38a8c0 100644 --- a/app/screens/Home/HomeReducer.js +++ b/app/screens/Home/HomeReducer.js @@ -1,4 +1,5 @@ import * as HomeConstants from './HomeConstants' +import * as ItemConstants from '../Item/ItemConstants' export default (state = HomeConstants.INITIAL_STATE, action) => { switch (action.type) { @@ -40,6 +41,33 @@ export default (state = HomeConstants.INITIAL_STATE, action) => { }, } + case ItemConstants.ADD_TO_BOOKMARKS: + return { + ...state, + modes: { + ...state.modes, + bookmark: { + ...state.modes.bookmark, + items: [ + ...state.modes.bookmark.items, + action.payload, + ], + }, + }, + } + + case ItemConstants.REMOVE_FROM_BOOKMARKS: + return { + ...state, + modes: { + ...state.modes, + bookmark: { + ...state.modes.bookmark, + items: state.modes.bookmark.items.filter(bookmark => bookmark.id !== action.payload.id), + }, + }, + } + default: return state } diff --git a/app/screens/Home/HomeScreen.js b/app/screens/Home/HomeScreen.js index d457d0e..e5989f0 100644 --- a/app/screens/Home/HomeScreen.js +++ b/app/screens/Home/HomeScreen.js @@ -43,6 +43,7 @@ export default class Home extends React.PureComponent { getItems(Constants.TYPE_MOVIE) getItems(Constants.TYPE_SHOW) + getItems(Constants.TYPE_BOOKMARK) } componentWillUnmount() { @@ -69,7 +70,11 @@ export default class Home extends React.PureComponent { return null } - getMyList = () => [] + getMyList = () => { + const { modes } = this.props + + return modes[Constants.TYPE_BOOKMARK].items.slice(0, 10) + } getMovies = (withSlice = true) => { const { modes } = this.props @@ -92,6 +97,8 @@ export default class Home extends React.PureComponent { render() { const { isLoading, hasInternet } = this.props + const myList = this.getMyList() + return ( @@ -104,8 +111,20 @@ export default class Home extends React.PureComponent { onLoad={this.handleCoverLoaded} item={this.getMainCover()} /> + {myList && myList.length > 0 && ( + + )} + 0 ? 0 : -20, + marginBottom: 8, + }} onPress={this.handleItemOpen} loading={isLoading} title={i18n.t('Movies')} diff --git a/app/screens/Item/ItemActions.js b/app/screens/Item/ItemActions.js index 7b6e183..aa1287c 100644 --- a/app/screens/Item/ItemActions.js +++ b/app/screens/Item/ItemActions.js @@ -1,4 +1,5 @@ -import Popcorn, { Constants } from 'popcorn-sdk' +import { Constants } from 'popcorn-sdk' +import Popcorn from 'modules/PopcornSDK' import * as ItemConstants from './ItemConstants' import * as HomeSelectors from '../Home/HomeSelectors' @@ -21,21 +22,8 @@ export function partlyFetchedItem(item) { } } -export function fetchEpisodeTorrents() { - return { - type: ItemConstants.FETCH_EPISODE_TORRENTS, - } -} - -export function fetchedEpisodeTorrents(item) { - return { - type : ItemConstants.FETCHED_EPISODE_TORRENTS, - payload: item, - } -} - export function getItem(type, itemId) { - return (dispatch, getState) => new Promise((resolve) => { + return (dispatch, getState) => new Promise(async(resolve) => { dispatch({ type: ItemConstants.FETCH_ITEM, }) @@ -44,7 +32,9 @@ export function getItem(type, itemId) { if (type === Constants.TYPE_MOVIE) { if (item) { - resolve(dispatch(fetchedItem(item))) + resolve(dispatch(fetchedItem( + await Popcorn.bookmarks.checkMovie(item), + ))) } else { resolve(Popcorn.getMovie(itemId).then(movie => dispatch(fetchedItem(movie)))) @@ -52,16 +42,36 @@ export function getItem(type, itemId) { } else if (type === Constants.TYPE_SHOW) { if (item) { - dispatch(partlyFetchedItem(item)) + resolve(dispatch(partlyFetchedItem( + await Popcorn.bookmarks.checkMovie(item), + ))) } return Popcorn.getShowBasic(itemId).then((basicShow) => { dispatch(partlyFetchedItem(basicShow)) - return resolve(Popcorn.getShowMeta(basicShow).then(show => dispatch(fetchedItem(show)))) + Popcorn.getShowMeta(basicShow).then(show => dispatch(fetchedItem(show))) }) } return null }) } + +export const addToBookmarks = (item) => (dispatch) => { + Popcorn.bookmarks.addItem(item) + + dispatch({ + type : ItemConstants.ADD_TO_BOOKMARKS, + payload: item, + }) +} + +export const removeFromBookmarks = (item) => (dispatch) => { + Popcorn.bookmarks.removeItem(item) + + dispatch({ + type : ItemConstants.REMOVE_FROM_BOOKMARKS, + payload: item, + }) +} diff --git a/app/screens/Item/ItemConstants.js b/app/screens/Item/ItemConstants.js index 61c33fe..dd55e2e 100644 --- a/app/screens/Item/ItemConstants.js +++ b/app/screens/Item/ItemConstants.js @@ -12,8 +12,6 @@ export const INITIAL_STATE = { export const FETCH_ITEM = `${REDUCER_NAME}.fetch.item` export const PARTLY_FETCH_ITEM = `${REDUCER_NAME}.partly.fetch.item` export const FETCHED_ITEM = `${REDUCER_NAME}.fetched.item` -export const UPDATE_ITEM = `${REDUCER_NAME}.update.item` -export const SELECT_SEASON_EPISODE = `${REDUCER_NAME}.select.season.episode` -export const FETCH_EPISODE_TORRENTS = `${REDUCER_NAME}.fetch.episode.torrents` -export const FETCHED_EPISODE_TORRENTS = `${REDUCER_NAME}.fetched.episode.torrents` +export const ADD_TO_BOOKMARKS = `${REDUCER_NAME}.add.to.bookmarks` +export const REMOVE_FROM_BOOKMARKS = `${REDUCER_NAME}.remove.from.bookmarks` diff --git a/app/screens/Item/ItemReducer.js b/app/screens/Item/ItemReducer.js index 4f1585a..835bc8d 100644 --- a/app/screens/Item/ItemReducer.js +++ b/app/screens/Item/ItemReducer.js @@ -23,23 +23,22 @@ export default (state = ItemConstants.INITIAL_STATE, action) => { item : action.payload, } - case ItemConstants.FETCH_EPISODE_TORRENTS: + case ItemConstants.ADD_TO_BOOKMARKS: return { ...state, - fetchingEpisodeTorrents: true, + item: { + ...state.item, + bookmarked: true, + }, } - case ItemConstants.FETCHED_EPISODE_TORRENTS: + case ItemConstants.REMOVE_FROM_BOOKMARKS: return { ...state, - fetchingEpisodeTorrents: false, - item : action.payload, - } - - case ItemConstants.SELECT_SEASON_EPISODE: - return { - ...state, - ...action.payload, + item: { + ...state.item, + bookmarked: false, + }, } default: diff --git a/app/screens/Item/ItemScreen.js b/app/screens/Item/ItemScreen.js index d193cf9..069661b 100644 --- a/app/screens/Item/ItemScreen.js +++ b/app/screens/Item/ItemScreen.js @@ -7,6 +7,7 @@ import i18n from 'modules/i18n' import ScrollViewWithStatusBar from 'components/ScrollViewWithStatusBar' import Typography from 'components/Typography' +import IconButton from 'components/IconButton' import colors from 'modules/colors' @@ -36,8 +37,22 @@ const styles = StyleSheet.create({ export default class Item extends React.Component { + static getDerivedStateFromProps(nextProps, state) { + const { item: nextItem } = nextProps + const { activeSeason } = state + + // If we retrieve more season then update to the latest one + if (nextItem && nextItem.seasons && nextItem.seasons.length > activeSeason) { + return { + activeSeason: nextItem.seasons[nextItem.seasons.length - 1].number, + } + } + + return null + } + state = { - activeSeason: 0, + activeSeason: null, } componentDidMount() { @@ -54,6 +69,17 @@ export default class Item extends React.Component { }) } + handleToggleBookmarks = () => { + const { item, addToBookmarks, removeFromBookmarks } = this.props + + if (item.bookmarked) { + removeFromBookmarks(item) + + } else { + addToBookmarks(item) + } + } + playItem = (torrents, episode = {}) => { const { navigation: { navigate, state: { params: item } } } = this.props @@ -66,24 +92,15 @@ export default class Item extends React.Component { }) } - getSelectedSeason = () => { - const { item } = this.props - - const { activeSeason } = this.state - - return item.seasons.find(season => season.number === activeSeason) - } - getAiredEpisodes = () => { - const { item, isLoading } = this.props + const { activeSeason } = this.state + const today = Date.now() - if (isLoading || !item || !item.seasons) { + if (!activeSeason) { return [] } - const today = Date.now() - - const season = this.getSelectedSeason() + const season = this.getSeasons(activeSeason) if (!season) { return [] @@ -92,13 +109,21 @@ export default class Item extends React.Component { return season.episodes.filter(episode => episode.aired < today) } - getSeasonsForPicker = () => { - const { item, isLoading } = this.props + getSeasons = (seasonNr = null) => { + const { item } = this.props + + if (!item || !item.seasons || item.seasons.length === 0) { + if (seasonNr) { + return null + } - if (isLoading) { return [] } + if (seasonNr) { + return item.seasons.find(season => season.number === seasonNr) + } + return item.seasons } @@ -119,14 +144,25 @@ export default class Item extends React.Component { )} + {item && ( + + + + )} + {item && item.type === Constants.TYPE_SHOW && ( this.setState({ activeSeason: itemValue })}> + onValueChange={(itemValue) => this.setState({ activeSeason: itemValue })}> - {this.getSeasonsForPicker().map(season => ( + {this.getSeasons().map(season => ( ( )) diff --git a/app/screens/Mode/ModeScreen.js b/app/screens/Mode/ModeScreen.js index 33a0ebe..19fb0a7 100644 --- a/app/screens/Mode/ModeScreen.js +++ b/app/screens/Mode/ModeScreen.js @@ -1,11 +1,15 @@ import React from 'react' import PropTypes from 'prop-types' -import { StyleSheet, Text, View, FlatList, StatusBar } from 'react-native' +import { StyleSheet, Text, View, FlatList, StatusBar, TextInput } from 'react-native' import Orientation from 'react-native-orientation' +import * as Animatable from 'react-native-animatable' +import Icon from 'react-native-vector-icons/MaterialIcons' +import { Constants } from 'popcorn-sdk' import colors from 'modules/colors' import Card from 'components/Card' +import IconButton from 'components/IconButton' import FullScreenLoading from 'components/FullScreenLoading' const styles = StyleSheet.create({ @@ -20,14 +24,44 @@ const styles = StyleSheet.create({ flexDirection: 'column', }, - list: { - marginTop: 32, - }, - listItem: { marginTop: 16, }, + searchRoot: { + width : '100%', + height : 50, + marginTop : 40, + display : 'flex', + justifyContent: 'center', + alignItems : 'center', + }, + + searchContainer: { + backgroundColor: colors.BACKGROUND_LIGHTER, + width : '90%', + height : '100%', + }, + + input: { + height : '100%', + width : '80%', + color : '#FFF', + marginLeft: 40, + }, + + cancelSearch: { + position: 'absolute', + right : 8, + top : 8, + }, + + searchIcon: { + position: 'absolute', + left : 8, + top : 8, + }, + }) export default class Mode extends React.Component { @@ -48,7 +82,10 @@ export default class Mode extends React.Component { } state = { - page: 1, + page : 1, + firstSearch: true, + searching : false, + searchText : '', } componentDidMount() { @@ -61,6 +98,11 @@ export default class Mode extends React.Component { getItems = () => { const { modes, mode } = this.props + const { searching } = this.state + + if (searching) { + return modes[`${mode}Search`].items + } return modes[mode].items } @@ -71,10 +113,36 @@ export default class Mode extends React.Component { navigation.navigate('Item', item) } + handleSearch = () => { + const { isLoading, getItems, mode } = this.props + const { searchText } = this.state + + if (!isLoading && searchText.trim().length > 0) { + getItems(`${mode}Search`, 1, { keywords: searchText }).then(() => { + this.setState({ + searching: true, + }) + }) + } + } + + handleCancelSearch = () => { + this.setState({ + searchText: '', + searching : false, + }) + } + + handleTextChange = text => this.setState({ searchText: text, firstSearch: false }) + handleEndReached = () => { const { isLoading, getItems, mode } = this.props const { page } = this.state + if (mode === Constants.TYPE_BOOKMARK) { + return + } + const nPage = page + 1 this.setState({ @@ -93,6 +161,48 @@ export default class Mode extends React.Component { /> ) + renderSearchBar = () => { + const { searchText, firstSearch } = this.state + + return ( + + + + + 0 ? 'zoomIn' : 'zoomOut'} + duration={firstSearch ? 1 : 300} + useNativeDriver> + + + + + + + + + + + ) + } + render() { const { isLoading, hasInternet } = this.props @@ -106,18 +216,22 @@ export default class Mode extends React.Component { {hasInternet && ( - `${item.id}-${index}`} - onEndReachedThreshold={100} - onEndReached={this.handleEndReached} - ListHeaderComponent={() => } - ListFooterComponent={() => } - /> + + + `${item.id}-${index}`} + onEndReachedThreshold={100} + onEndReached={this.handleEndReached} + ListHeaderComponent={this.renderSearchBar} + ListFooterComponent={() => } + /> + + )} {!hasInternet && ( diff --git a/app/screens/index.js b/app/screens/index.js index 2b7f1ea..63fc557 100644 --- a/app/screens/index.js +++ b/app/screens/index.js @@ -30,6 +30,21 @@ export default createStackNavigator({ }, }, + MyList: { + screen: ({ ...props }) => , + + navigationOptions: { + tabBarLabel: i18n.t('My List'), + tabBarIcon : ({ tintColor }) => ( + + ), + }, + }, + Movies: { screen: ({ ...props }) => , diff --git a/package.json b/package.json index 1670f58..8707196 100644 --- a/package.json +++ b/package.json @@ -15,7 +15,7 @@ }, "dependencies": { "i18n-js": "^3.0.11", - "popcorn-sdk": "0.5.0", + "popcorn-sdk": "1.1.0", "prop-types": "^15.6.2", "react": "16.3.1", "react-native": "~0.55.2", diff --git a/yarn.lock b/yarn.lock index 2467a87..86ec092 100644 --- a/yarn.lock +++ b/yarn.lock @@ -4781,9 +4781,9 @@ pn@^1.1.0: version "1.1.0" resolved "https://registry.yarnpkg.com/pn/-/pn-1.1.0.tgz#e2f4cef0e219f463c179ab37463e4e1ecdccbafb" -popcorn-sdk@0.5.0: - version "0.5.0" - resolved "https://registry.yarnpkg.com/popcorn-sdk/-/popcorn-sdk-0.5.0.tgz#7b08bd1d1d7ed202cd42f780921fd25a1a300e47" +popcorn-sdk@1.1.0: + version "1.1.0" + resolved "https://registry.yarnpkg.com/popcorn-sdk/-/popcorn-sdk-1.1.0.tgz#f7dc79c79a48fea764991327dceb9596449b6563" dependencies: axios "^0.18.0"