Skip to content

Commit

Permalink
fix: null error on un-supported platforms
Browse files Browse the repository at this point in the history
  • Loading branch information
tien committed Nov 28, 2021
1 parent 18b7b10 commit 7ceff9f
Show file tree
Hide file tree
Showing 6 changed files with 48 additions and 35 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,6 @@
import com.facebook.soloader.SoLoader;
import java.lang.reflect.InvocationTargetException;
import java.util.List;
import com.reactairplay.ReactAirplayPackage;

public class MainApplication extends Application implements ReactApplication {

Expand All @@ -27,7 +26,6 @@ protected List<ReactPackage> getPackages() {
List<ReactPackage> packages = new PackageList(this).getPackages();
// Packages that cannot be autolinked yet can be added manually here, for ReactAirplayExample:
// packages.add(new MyReactNativePackage());
packages.add(new ReactAirplayPackage());
return packages;
}

Expand Down
3 changes: 2 additions & 1 deletion example/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -5,12 +5,13 @@
"private": true,
"scripts": {
"ios": "react-native run-ios",
"android": "react-native run-android",
"start": "react-native start"
},
"dependencies": {
"react": "17.0.2",
"react-native": "0.65.1",
"react-native-video": "^5.1.1"
"react-native-video": "^5.2.0"
},
"devDependencies": {
"@babel/core": "^7.15.0",
Expand Down
15 changes: 9 additions & 6 deletions example/src/App.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@ import {
useAirplayConnectivity,
useExternalPlaybackAvailability,
} from 'react-airplay';
import {Platform} from 'react-native';
import {Button, StyleSheet, Text, View} from 'react-native';
import Video from 'react-native-video';

Expand All @@ -30,12 +31,14 @@ export default () => {
<Text>Airplay connected: {String(isAirplayConnected)}</Text>
</View>
<View style={styles.box}>
<AirplayButton
style={styles.button}
prioritizesVideoDevices={true}
tintColor="yellow"
activeTintColor="red"
/>
{Platform.OS === 'ios' && (
<AirplayButton
style={styles.button}
prioritizesVideoDevices={true}
tintColor="yellow"
activeTintColor="red"
/>
)}
</View>
<View>
<Button
Expand Down
10 changes: 5 additions & 5 deletions example/yarn.lock
Original file line number Diff line number Diff line change
Expand Up @@ -5358,7 +5358,7 @@ fsevents@^2.1.2:
react: 17.0.2
react-native: 0.65.1
react-native-codegen: ^0.0.7
react-native-video: ^5.1.1
react-native-video: ^5.2.0
languageName: unknown
linkType: soft

Expand Down Expand Up @@ -5397,14 +5397,14 @@ fsevents@^2.1.2:
languageName: node
linkType: hard

"react-native-video@npm:^5.1.1":
version: 5.1.1
resolution: "react-native-video@npm:5.1.1"
"react-native-video@npm:^5.2.0":
version: 5.2.0
resolution: "react-native-video@npm:5.2.0"
dependencies:
keymirror: ^0.1.1
prop-types: ^15.7.2
shaka-player: ^2.5.9
checksum: 83f3289c2998dc969a81117743e163085dbd2a407dbb5cde90e35c654de66f6340353c862604960a26e8b7bc4dcbcfeacf8d442a16f75d07b8f02a23c40fe197
checksum: 6182b8c880620bc16ef1871634a92e563542615a27db40d732faca72762e6bd2539cdedaf473d447b336bb40168461d51dc34995d9876ee4913ace76b890b59d
languageName: node
linkType: hard

Expand Down
44 changes: 29 additions & 15 deletions src/airplayModule.ts
Original file line number Diff line number Diff line change
@@ -1,13 +1,22 @@
import {NativeEventEmitter, NativeModules, Platform} from 'react-native';
import {
NativeEventEmitter,
NativeModule,
NativeModules,
Platform,
} from 'react-native';

export type ExternalPlaybackAvailabilityContext = {
export type ExternalPlaybackAvailabilityContext = NativeModule & {
fetchExternalPlaybackAvailability: () => Promise<boolean>;
};

export type AirplayConnectivityContext = {
export type AirplayConnectivityContext = NativeModule & {
fetchAirplayConnectivity: () => Promise<boolean>;
};

export type RoutePickerContext = NativeModule & {
showRoutePicker: (options?: ShowRoutePickerOptions) => Promise<void>;
};

export type ShowRoutePickerOptions = {
prioritizesVideoDevices?: boolean;
};
Expand All @@ -17,22 +26,23 @@ const {
RAAirplayConnectivityContext,
RAExternalPlaybackAvailabilityContext,
RARoutePickerContext,
} = NativeModules;
} = NativeModules as {
RAEvents?: {getConstants: () => Record<string, string>};
RAAirplayConnectivityContext?: AirplayConnectivityContext;
RAExternalPlaybackAvailabilityContext?: ExternalPlaybackAvailabilityContext;
RARoutePickerContext?: RoutePickerContext;
};

const constants =
Platform.OS !== 'ios'
? {}
: (RAEvents.getConstants() as Record<string, string>);
const constants = RAEvents?.getConstants();

export const AirplayConnectivityContext = RAAirplayConnectivityContext;
export const ExternalPlaybackAvailabilityContext =
RAExternalPlaybackAvailabilityContext as ExternalPlaybackAvailabilityContext;
export const AirplayConnectivityContext =
RAAirplayConnectivityContext as AirplayConnectivityContext;
RAExternalPlaybackAvailabilityContext;

export const {
EXTERNAL_PLAYBACK_AVAILABILITY_CHANGED,
AIRPLAY_CONNECTIVITY_CHANGED,
} = constants;
} = constants ?? {};

export const ExternalPlaybackAvailabilityEventEmitter = new NativeEventEmitter(
RAExternalPlaybackAvailabilityContext,
Expand All @@ -58,6 +68,10 @@ export const onAirplayConnectivityChanged = (
callback,
);

export const showRoutePicker: (
options?: ShowRoutePickerOptions,
) => Promise<void> = RARoutePickerContext.showRoutePicker;
export const showRoutePicker = (options: ShowRoutePickerOptions) => {
if (Platform.OS !== 'ios' && RARoutePickerContext === undefined) {
console.warn('showRoutePicker is only supported on iOS');
}

return RARoutePickerContext?.showRoutePicker(options) ?? Promise.resolve();
};
9 changes: 3 additions & 6 deletions src/hooks.ts
Original file line number Diff line number Diff line change
@@ -1,5 +1,4 @@
import {useEffect, useState} from 'react';
import {Platform} from 'react-native';

import {
AirplayConnectivityContext,
Expand All @@ -19,13 +18,13 @@ export const useExternalPlaybackAvailability = (
useState(false);

useEffect(() => {
if (Platform.OS !== 'ios' || (options?.useCachedValue ?? false)) return;
if (options?.useCachedValue ?? false) return;

const subscription = onExternalPlaybackAvailabilityChanged(
setIsExternalPlaybackAvailable,
);

ExternalPlaybackAvailabilityContext.fetchExternalPlaybackAvailability().then(
ExternalPlaybackAvailabilityContext?.fetchExternalPlaybackAvailability().then(
setIsExternalPlaybackAvailable,
);

Expand All @@ -39,11 +38,9 @@ export const useAirplayConnectivity = () => {
const [isAirplayConnected, setIsAirplayConnected] = useState(false);

useEffect(() => {
if (Platform.OS !== 'ios') return;

const subscription = onAirplayConnectivityChanged(setIsAirplayConnected);

AirplayConnectivityContext.fetchAirplayConnectivity().then(
AirplayConnectivityContext?.fetchAirplayConnectivity().then(
setIsAirplayConnected,
);

Expand Down

0 comments on commit 7ceff9f

Please sign in to comment.