Skip to content

Commit 9b8f7a9

Browse files
committed
Use YouTube API for videoId and playlist updates
1 parent 35dec9d commit 9b8f7a9

File tree

2 files changed

+44
-21
lines changed

2 files changed

+44
-21
lines changed

src/PlayerScripts.js

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -53,6 +53,12 @@ true;
5353

5454
return `player.${func}({playlist: ${playlistJson}, index: ${index}); true;`;
5555
},
56+
57+
loadVideoById: (videoId, play) => {
58+
const func = play ? 'loadVideoById' : 'cueVideoById';
59+
60+
return `player.${func}({videoId: ${JSON.stringify(videoId)}}); true;`;
61+
},
5662
};
5763

5864
export const playMode = {

src/YoutubeIframe.js

Lines changed: 38 additions & 21 deletions
Original file line numberDiff line numberDiff line change
@@ -126,6 +126,40 @@ const YoutubeIframe = (props, ref) => {
126126
].forEach(webViewRef.current.injectJavaScript);
127127
}, [play, playerReady, mute, volume, playbackRate]);
128128

129+
useEffect(() => {
130+
if (playerReady < 1) {
131+
// no instance of player is ready
132+
return;
133+
}
134+
135+
webViewRef.current.injectJavaScript(
136+
PLAYER_FUNCTIONS.loadVideoById(videoId, play),
137+
);
138+
// We do not need `play` prop because we should not
139+
// recall the load function when the prop changes
140+
// eslint-disable-next-line react-hooks/exhaustive-deps
141+
}, [videoId, playerReady]);
142+
143+
useEffect(() => {
144+
if (playerReady < 1) {
145+
// no instance of player is ready
146+
return;
147+
}
148+
149+
if (!playList) {
150+
return;
151+
}
152+
153+
webViewRef.current.injectJavaScript(
154+
PLAYER_FUNCTIONS.loadPlaylist(playList, playListStartIndex, play),
155+
);
156+
// We do not need `play` and `playListStartIndex` props because we should not
157+
// recall the load function when the props changes
158+
// Also, right now, we are helping users by doing "deep" comparisons of playList prop,
159+
// but in the next major we should leave the responsibility to user (either via useMemo or moving the array outside)
160+
// eslint-disable-next-line react-hooks/exhaustive-deps
161+
}, [Array.isArray(playList) ? playList.join('') : playList, playerReady]);
162+
129163
const onWebMessage = useCallback(
130164
event => {
131165
try {
@@ -141,15 +175,6 @@ const YoutubeIframe = (props, ref) => {
141175
case 'playerReady':
142176
onReady();
143177
setPlayerReady(prev => prev + 1);
144-
if (Array.isArray(playList)) {
145-
webViewRef.current.injectJavaScript(
146-
PLAYER_FUNCTIONS.loadPlaylist(
147-
playList,
148-
playListStartIndex,
149-
play,
150-
),
151-
);
152-
}
153178
break;
154179
case 'playerQualityChange':
155180
onPlaybackQualityChange(message.data);
@@ -169,13 +194,10 @@ const YoutubeIframe = (props, ref) => {
169194
}
170195
},
171196
[
172-
play,
173197
onReady,
174198
onError,
175-
playList,
176199
onChangeState,
177200
onFullScreenChange,
178-
playListStartIndex,
179201
onPlaybackRateChange,
180202
onPlaybackQualityChange,
181203
],
@@ -219,15 +241,10 @@ const YoutubeIframe = (props, ref) => {
219241
const data = ytScript.urlEncodedJSON;
220242

221243
return {uri: base + '?data=' + data};
222-
}, [
223-
videoId,
224-
playList,
225-
useLocalHTML,
226-
contentScale,
227-
baseUrlOverride,
228-
allowWebViewZoom,
229-
initialPlayerParams,
230-
]);
244+
// videoId, playlist, initialPlayerParams are only used once when initializing YT.Player instance
245+
// further changes are handled by injectJavaScript
246+
// eslint-disable-next-line react-hooks/exhaustive-deps
247+
}, [useLocalHTML, contentScale, baseUrlOverride, allowWebViewZoom]);
231248

232249
return (
233250
<View style={{height, width}}>

0 commit comments

Comments
 (0)