Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat: Android Auto Support #1928

Merged
merged 15 commits into from
Oct 6, 2023
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
53 changes: 31 additions & 22 deletions App.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -10,12 +10,13 @@ import Orientation from 'react-native-orientation-locker'
import { initialWindowMetrics, SafeAreaProvider } from 'react-native-safe-area-context'
import TrackPlayer from 'react-native-track-player'
import { setGlobal } from 'reactn'
import {
UpdateRequiredOverlay,
OverlayAlert,
ImageFullView,
BoostDropdownBanner,
LoadingInterstitialView

import {
UpdateRequiredOverlay,
OverlayAlert,
ImageFullView,
BoostDropdownBanner,
LoadingInterstitialView
} from './src/components'
import { pvIsTablet } from './src/lib/deviceDetection'
import { refreshDownloads } from './src/lib/downloader'
Expand All @@ -41,8 +42,9 @@ import {
showRootView,
unregisterCarModule
} from './src/lib/carplay/PVCarPlay'
import { registerAndroidAutoModule, unregisterAndroidAutoModule } from './src/lib/carplay/PVCarPlay.android'

LogBox.ignoreLogs(['EventEmitter.removeListener', "Require cycle"])
LogBox.ignoreLogs(['EventEmitter.removeListener', 'Require cycle'])

type Props = any

Expand Down Expand Up @@ -77,7 +79,12 @@ class App extends Component<Props, State> {
async componentDidMount() {
TrackPlayer.registerPlaybackService(() => require('./src/services/playerAudioEvents'))
await PlayerAudioSetupService()

// Android Auto
if (Platform.OS === 'android') {
// initialize Android Auto Tabs with no content. Content will be updated as they are loaded to the global state.
registerAndroidAutoModule()
}

StatusBar.setBarStyle('light-content')
Platform.OS === 'android' && StatusBar.setBackgroundColor(PV.Colors.ink, true)
const darkModeEnabled = await AsyncStorage.getItem(PV.Keys.DARK_MODE_ENABLED)
Expand All @@ -94,13 +101,17 @@ class App extends Component<Props, State> {

this.unsubscribeNetListener = NetInfo.addEventListener(this.handleNetworkChange)

registerCarModule(this.onConnect, this.onDisconnect)
// iOS CarPlay
Platform.OS === 'ios' && registerCarModule(this.onConnect, this.onDisconnect)
}

componentWillUnmount() {
this.unsubscribeNetListener && this.unsubscribeNetListener()

unregisterCarModule(this.onConnect, this.onDisconnect);
// iOS CarPlay
Platform.OS === 'ios' && unregisterCarModule(this.onConnect, this.onDisconnect)
// Android Auto
Platform.OS === 'android' && unregisterAndroidAutoModule()
}

onConnect = () => {
Expand Down Expand Up @@ -130,7 +141,7 @@ class App extends Component<Props, State> {
}

handleNetworkChange = () => {
(async () => {
;(async () => {
// isInternetReachable will be false

await this.checkAppVersion()
Expand All @@ -154,14 +165,12 @@ class App extends Component<Props, State> {
const appMode = await AsyncStorage.getItem(PV.Keys.APP_MODE)
const fontScaleMode = determineFontScaleMode(fontScale)

setGlobal(
{
globalTheme: theme,
fontScaleMode,
fontScale,
appMode: appMode || PV.AppMode.podcasts
}
)
setGlobal({
globalTheme: theme,
fontScaleMode,
fontScale,
appMode: appMode || PV.AppMode.podcasts
})
}

checkAppVersion = async () => {
Expand Down Expand Up @@ -192,8 +201,8 @@ class App extends Component<Props, State> {
opacity: 1
}
: {
flex: 1
}
flex: 1
}

if (this.state.minVersionMismatch) {
return <UpdateRequiredOverlay />
Expand All @@ -209,7 +218,7 @@ class App extends Component<Props, State> {
<ImageFullView />
<BoostDropdownBanner />
</SafeAreaProvider>
<LoadingInterstitialView/>
<LoadingInterstitialView />
</GestureHandlerRootView>
) : (
this._renderIntersitial()
Expand Down
6 changes: 6 additions & 0 deletions android/app/src/main/AndroidManifest.xml
Original file line number Diff line number Diff line change
Expand Up @@ -227,6 +227,10 @@
android:scheme="com.podverse"
android:host="callback_alby" />
</intent-filter>
<intent-filter>
<action android:name="android.media.action.MEDIA_PLAY_FROM_SEARCH" />
<category android:name="android.intent.category.DEFAULT" />
</intent-filter>
</activity>
<activity android:name="com.facebook.react.devsupport.DevSettingsActivity" />

Expand All @@ -239,6 +243,8 @@
<action android:name="org.unifiedpush.android.connector.REGISTRATION_REFUSED"/>
</intent-filter>
</receiver>
<meta-data android:name="com.google.android.gms.car.application"
android:resource="@xml/automotive_app_desc"/>
</application>

</manifest>
8 changes: 7 additions & 1 deletion android/app/src/main/java/com/podverse/MainActivity.java
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@
import com.facebook.react.bridge.WritableMap;
import com.facebook.react.bridge.WritableNativeMap;

import android.os.Build;
import android.os.Bundle;

import android.content.Intent;
Expand All @@ -27,7 +28,12 @@ protected String getMainComponentName() {
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(null);

// This is to support Android Auto wake PV when the screen is locked.
// and to prevent app showing up on the lock screen, use PVAndroidAutoModule to turn this off
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O_MR1) {
setShowWhenLocked(true);
setTurnScreenOn(true);
}
if(getResources().getBoolean(R.bool.portrait_only)){
setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_PORTRAIT);
}
Expand Down
48 changes: 48 additions & 0 deletions android/app/src/main/java/com/podverse/PVAndroidAutoModule.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,48 @@
package com.podverse;

import android.app.Activity;
import android.net.Uri;
import android.os.Build;
import android.provider.Settings;
import android.content.Intent;

import com.facebook.react.bridge.Promise;
import com.facebook.react.bridge.ReactApplicationContext;
import com.facebook.react.bridge.ReactContextBaseJavaModule;
import com.facebook.react.bridge.ReactMethod;

public class PVAndroidAutoModule extends ReactContextBaseJavaModule{
PVAndroidAutoModule(ReactApplicationContext context) {
super(context);
}

public String getName() {
return "PVAndroidAutoModule";
}

@ReactMethod
public void turnOffShowWhenLocked() {
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O_MR1) {
Activity activity = getReactApplicationContext().getCurrentActivity();
activity.setShowWhenLocked(false);
activity.setTurnScreenOn(false);
}
}

@ReactMethod
public void getDrawOverAppsPermission(Promise promise) {
Activity activity = getReactApplicationContext().getCurrentActivity();
promise.resolve(Settings.canDrawOverlays(activity));
}

@ReactMethod
public void askDrawOverAppsPermission() {
ReactApplicationContext context = getReactApplicationContext();
Activity activity = context.getCurrentActivity();
Intent intent = new Intent(Settings.ACTION_MANAGE_OVERLAY_PERMISSION, Uri.parse("package:com.podverse"));
intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
context.startActivity(intent);
}


}
Original file line number Diff line number Diff line change
Expand Up @@ -22,6 +22,7 @@ public List<NativeModule> createNativeModules(

modules.add(new PVAsyncStorageModule(reactContext));
modules.add(new PVUnifiedPushModule(reactContext));
modules.add(new PVAndroidAutoModule(reactContext));

return modules;
}
Expand Down
3 changes: 3 additions & 0 deletions android/app/src/main/res/xml/automotive_app_desc.xml
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
<automotiveApp>
<uses name="media"/>
</automotiveApp>
2 changes: 1 addition & 1 deletion package.json
Original file line number Diff line number Diff line change
Expand Up @@ -106,7 +106,7 @@
"react-native-swipe-list-view": "3.2.9",
"react-native-system-setting": "1.7.6",
"react-native-text-ticker": "1.13.0",
"react-native-track-player": "3.2.0-32baacdfdcbf5edb81a8a3199fdf30896dcce0cc",
"react-native-track-player": "git+https://lovegaoshi@github.com/lovegaoshi/react-native-track-player.git#dev-podverse-aa",
"react-native-tracking-transparency": "0.1.1",
"react-native-vector-icons": "8.1.0",
"react-native-video": "6.0.0-alpha.4",
Expand Down
Loading