diff --git a/App.js b/App.js index bb580af..d7980c3 100644 --- a/App.js +++ b/App.js @@ -30,99 +30,99 @@ import Theme from './utils/Theme'; import './i18n'; const App = observer(({ skipLoadingScreen }) => { - const [isSplashReady, setIsSplashReady] = useState(false); - const { rootStore } = useStores(); + const [isSplashReady, setIsSplashReady] = useState(false); + const { rootStore } = useStores(); - const trunk = new AsyncTrunk(rootStore, { - storage: AsyncStorage - }); + const trunk = new AsyncTrunk(rootStore, { + storage: AsyncStorage + }); - const hydrateStores = async () => { - // Migrate servers and settings - // TODO: Remove this for next release - const servers = await CachingStorage.getInstance().getItem(StorageKeys.Servers); - if (servers) { - const activeServer = await CachingStorage.getInstance().getItem(StorageKeys.ActiveServer) || 0; + const hydrateStores = async () => { + // Migrate servers and settings + // TODO: Remove this for next release + const servers = await CachingStorage.getInstance().getItem(StorageKeys.Servers); + if (servers) { + const activeServer = await CachingStorage.getInstance().getItem(StorageKeys.ActiveServer) || 0; - // Initialize the store with the existing servers and settings - await trunk.init({ - serverStore: { servers }, - settingStore: { activeServer } - }); + // Initialize the store with the existing servers and settings + await trunk.init({ + serverStore: { servers }, + settingStore: { activeServer } + }); - // Remove old data values - AsyncStorage.multiRemove(Object.values(StorageKeys)); - } else { - // No servers saved in the old method, initialize normally - await trunk.init(); - } + // Remove old data values + AsyncStorage.multiRemove(Object.values(StorageKeys)); + } else { + // No servers saved in the old method, initialize normally + await trunk.init(); + } - rootStore.storeLoaded = true; + rootStore.storeLoaded = true; - if (typeof rootStore.settingStore.isRotationEnabled === 'undefined') { - rootStore.settingStore.isRotationEnabled = Platform.OS === 'ios' && !Platform.isPad; - console.info('Initializing rotation lock setting', rootStore.settingStore.isRotationEnabled); - } - }; + if (typeof rootStore.settingStore.isRotationEnabled === 'undefined') { + rootStore.settingStore.isRotationEnabled = Platform.OS === 'ios' && !Platform.isPad; + console.info('Initializing rotation lock setting', rootStore.settingStore.isRotationEnabled); + } + }; - useEffect(() => { - // Hydrate mobx data stores - hydrateStores(); - }, []); + useEffect(() => { + // Hydrate mobx data stores + hydrateStores(); + }, []); - useEffect(() => { - console.info('rotation lock setting changed!', rootStore.settingStore.isRotationEnabled); - if (rootStore.settingStore.isRotationEnabled) { - ScreenOrientation.lockAsync(ScreenOrientation.OrientationLock.PORTRAIT_UP); - } else { - ScreenOrientation.unlockAsync(); - } - }, [rootStore.settingStore.isRotationEnabled]); + useEffect(() => { + console.info('rotation lock setting changed!', rootStore.settingStore.isRotationEnabled); + if (rootStore.settingStore.isRotationEnabled) { + ScreenOrientation.lockAsync(ScreenOrientation.OrientationLock.PORTRAIT_UP); + } else { + ScreenOrientation.unlockAsync(); + } + }, [rootStore.settingStore.isRotationEnabled]); - const loadImagesAsync = () => { - const images = [ - require('./assets/images/splash.png'), - require('./assets/images/logowhite.png') - ]; - return images.map(image => Asset.fromModule(image).downloadAsync()); - }; + const loadImagesAsync = () => { + const images = [ + require('./assets/images/splash.png'), + require('./assets/images/logowhite.png') + ]; + return images.map(image => Asset.fromModule(image).downloadAsync()); + }; - const loadResourcesAsync = async () => { - return Promise.all([ - Font.loadAsync({ - // This is the font that we are using for our tab bar - ...Ionicons.font - }), - ...loadImagesAsync() - ]); - }; + const loadResourcesAsync = async () => { + return Promise.all([ + Font.loadAsync({ + // This is the font that we are using for our tab bar + ...Ionicons.font + }), + ...loadImagesAsync() + ]); + }; - if (!isSplashReady && !skipLoadingScreen) { - return ( - setIsSplashReady(true)} - autoHideSplash={false} - /> - ); - } + if (!isSplashReady && !skipLoadingScreen) { + return ( + setIsSplashReady(true)} + autoHideSplash={false} + /> + ); + } - return ( - - - - - - - ); + return ( + + + + + + + ); }); App.propTypes = { - skipLoadingScreen: PropTypes.bool + skipLoadingScreen: PropTypes.bool }; export default App; diff --git a/babel.config.js b/babel.config.js index f38a9e8..ad44602 100644 --- a/babel.config.js +++ b/babel.config.js @@ -4,8 +4,8 @@ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */ module.exports = function(api) { - api.cache(true); - return { - presets: ['babel-preset-expo'] - }; + api.cache(true); + return { + presets: ['babel-preset-expo'] + }; }; diff --git a/components/AppInfoFooter.js b/components/AppInfoFooter.js index a4aab3d..cdc4982 100644 --- a/components/AppInfoFooter.js +++ b/components/AppInfoFooter.js @@ -12,25 +12,25 @@ import { useTranslation } from 'react-i18next'; import { getAppName } from '../utils/Device'; const AppInfoFooter = () => { - const { t } = useTranslation(); + const { t } = useTranslation(); - return ( - - {`${getAppName()}`} - {`${Constants.nativeAppVersion} (${Constants.nativeBuildVersion})`} - {t('settings.expoVersion', { version: Constants.expoVersion })} - - ); + return ( + + {`${getAppName()}`} + {`${Constants.nativeAppVersion} (${Constants.nativeBuildVersion})`} + {t('settings.expoVersion', { version: Constants.expoVersion })} + + ); }; const styles = StyleSheet.create({ - container: { - margin: 15 - }, - text: { - color: colors.grey4, - fontSize: 15 - } + container: { + margin: 15 + }, + text: { + color: colors.grey4, + fontSize: 15 + } }); export default AppInfoFooter; diff --git a/components/BrowserListItem.js b/components/BrowserListItem.js index 7526184..bd7d1e6 100644 --- a/components/BrowserListItem.js +++ b/components/BrowserListItem.js @@ -10,25 +10,25 @@ import PropTypes from 'prop-types'; import { openBrowser } from '../utils/WebBrowser'; const BrowserListItem = ({item, index}) => ( - { - openBrowser(item.url); - }} - /> + { + openBrowser(item.url); + }} + /> ); BrowserListItem.propTypes = { - item: PropTypes.shape({ - name: PropTypes.string.isRequired, - icon: PropTypes.string.isRequired, - url: PropTypes.string.isRequired - }).isRequired, - index: PropTypes.number.isRequired + item: PropTypes.shape({ + name: PropTypes.string.isRequired, + icon: PropTypes.string.isRequired, + url: PropTypes.string.isRequired + }).isRequired, + index: PropTypes.number.isRequired }; export default BrowserListItem; diff --git a/components/ButtonListItem.js b/components/ButtonListItem.js index f2e0fdd..c13a963 100644 --- a/components/ButtonListItem.js +++ b/components/ButtonListItem.js @@ -9,30 +9,30 @@ import { Button, ListItem } from 'react-native-elements'; import PropTypes from 'prop-types'; const ButtonListItem = ({item, index}) => ( - - } - topDivider={index === 0} - bottomDivider - /> + + } + topDivider={index === 0} + bottomDivider + /> ); ButtonListItem.propTypes = { - item: PropTypes.object.isRequired, - index: PropTypes.number.isRequired + item: PropTypes.object.isRequired, + index: PropTypes.number.isRequired }; const styles = StyleSheet.create({ - button: { - justifyContent: 'flex-start', - padding: 0 - } + button: { + justifyContent: 'flex-start', + padding: 0 + } }); export default ButtonListItem; diff --git a/components/ServerInput.js b/components/ServerInput.js index 306db44..a0d69c5 100644 --- a/components/ServerInput.js +++ b/components/ServerInput.js @@ -18,127 +18,127 @@ import JellyfinValidator from '../utils/JellyfinValidator'; const sanitizeHost = (url = '') => url.trim(); const ServerInput = observer(class ServerInput extends React.Component { - static propTypes = { - navigation: PropTypes.object.isRequired, - rootStore: PropTypes.object.isRequired, - t: PropTypes.func.isRequired, - onSuccess: PropTypes.func, - successScreen: PropTypes.string - } + static propTypes = { + navigation: PropTypes.object.isRequired, + rootStore: PropTypes.object.isRequired, + t: PropTypes.func.isRequired, + onSuccess: PropTypes.func, + successScreen: PropTypes.string + } - state = { - host: '', - isValidating: false, - isValid: true, - validationMessage: '' - } + state = { + host: '', + isValidating: false, + isValid: true, + validationMessage: '' + } - async onAddServer() { - const { host } = this.state; - console.log('add server', host); - if (host) { - this.setState({ - isValidating: true, - isValid: true, - validationMessage: '' - }); + async onAddServer() { + const { host } = this.state; + console.log('add server', host); + if (host) { + this.setState({ + isValidating: true, + isValid: true, + validationMessage: '' + }); - // Parse the entered url - let url; - try { - url = JellyfinValidator.parseUrl(host); - console.log('parsed url', url); - } catch (err) { - console.info(err); - this.setState({ - isValidating: false, - isValid: false, - validationMessage: this.props.t('addServer.validation.invalid') - }); - return; - } + // Parse the entered url + let url; + try { + url = JellyfinValidator.parseUrl(host); + console.log('parsed url', url); + } catch (err) { + console.info(err); + this.setState({ + isValidating: false, + isValid: false, + validationMessage: this.props.t('addServer.validation.invalid') + }); + return; + } - // Validate the server is available - const validation = await JellyfinValidator.validate({ url }); - console.log(`Server is ${validation.isValid ? '' : 'not '}valid`); - if (!validation.isValid) { - const message = validation.message || 'invalid'; - this.setState({ - isValidating: false, - isValid: validation.isValid, - validationMessage: this.props.t([`addServer.validation.${message}`, 'addServer.validation.invalid']) - }); - return; - } + // Validate the server is available + const validation = await JellyfinValidator.validate({ url }); + console.log(`Server is ${validation.isValid ? '' : 'not '}valid`); + if (!validation.isValid) { + const message = validation.message || 'invalid'; + this.setState({ + isValidating: false, + isValid: validation.isValid, + validationMessage: this.props.t([`addServer.validation.${message}`, 'addServer.validation.invalid']) + }); + return; + } - // Save the server details - this.props.rootStore.serverStore.addServer({ url }); - this.props.rootStore.settingStore.activeServer = this.props.rootStore.serverStore.servers.length - 1; - // Call the success callback if present - if (this.props.onSuccess) { - this.props.onSuccess(); - } - // Navigate to the main screen - this.props.navigation.replace( - 'Main', - { - screen: this.props.successScreen || 'Home', - params: { activeServer: this.props.rootStore.settingStore.activeServer } - } - ); - } else { - this.setState({ - isValid: false, - validationMessage: this.props.t('addServer.validation.empty') - }); - } - } + // Save the server details + this.props.rootStore.serverStore.addServer({ url }); + this.props.rootStore.settingStore.activeServer = this.props.rootStore.serverStore.servers.length - 1; + // Call the success callback if present + if (this.props.onSuccess) { + this.props.onSuccess(); + } + // Navigate to the main screen + this.props.navigation.replace( + 'Main', + { + screen: this.props.successScreen || 'Home', + params: { activeServer: this.props.rootStore.settingStore.activeServer } + } + ); + } else { + this.setState({ + isValid: false, + validationMessage: this.props.t('addServer.validation.empty') + }); + } + } - render() { - return ( - : null} - selectionColor={Colors.tintColor} - autoCapitalize='none' - autoCorrect={false} - autoCompleteType='off' - autoFocus={true} - keyboardType={Platform.OS === 'ios' ? 'url' : 'default'} - returnKeyType='go' - textContentType='URL' - editable={!this.state.isValidating} - value={this.state.host} - errorMessage={this.state.isValid ? null : this.state.validationMessage} - onChangeText={text => this.setState({ host: sanitizeHost(text) })} - onSubmitEditing={() => this.onAddServer()} - {...this.props} - /> - ); - } + render() { + return ( + : null} + selectionColor={Colors.tintColor} + autoCapitalize='none' + autoCorrect={false} + autoCompleteType='off' + autoFocus={true} + keyboardType={Platform.OS === 'ios' ? 'url' : 'default'} + returnKeyType='go' + textContentType='URL' + editable={!this.state.isValidating} + value={this.state.host} + errorMessage={this.state.isValid ? null : this.state.validationMessage} + onChangeText={text => this.setState({ host: sanitizeHost(text) })} + onSubmitEditing={() => this.onAddServer()} + {...this.props} + /> + ); + } }); const styles = StyleSheet.create({ - inputContainerStyle: { - marginTop: 8, - marginBottom: 12, - backgroundColor: '#292929', - borderBottomWidth: 0 - } + inputContainerStyle: { + marginTop: 8, + marginBottom: 12, + backgroundColor: '#292929', + borderBottomWidth: 0 + } }); // Inject the Navigation Hook as a prop to mimic the legacy behavior const ServerInputWithNavigation = observer((props) => { - const stores = useStores(); - return ; + const stores = useStores(); + return ; }); export default ServerInputWithNavigation; diff --git a/components/ServerListItem.js b/components/ServerListItem.js index 964fb92..56ce514 100644 --- a/components/ServerListItem.js +++ b/components/ServerListItem.js @@ -12,65 +12,65 @@ import { useTranslation } from 'react-i18next'; import { getIconName } from '../utils/Icons'; const ServerListItem = ({item, index, activeServer, onDelete, onPress}) => { - const { t } = useTranslation(); + const { t } = useTranslation(); - const title = item?.name; - const version = item?.info?.Version || t('common.unknown'); - const subtitle = `${t('settings.version', { version })}\n${item.urlString}`; + const title = item?.name; + const version = item?.info?.Version || t('common.unknown'); + const subtitle = `${t('settings.version', { version })}\n${item.urlString}`; - return ( - - ) : ( - - ) - )} - rightElement={( -