Skip to content

Commit a847582

Browse files
committed
refactor TwitchPlayer component for improved state management and embed initialization; update package dependencies
1 parent fef450c commit a847582

File tree

4 files changed

+89
-59
lines changed

4 files changed

+89
-59
lines changed

package.json

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
{
22
"name": "@grandlinex/react-components",
3-
"version": "0.10.0-alpha.10",
3+
"version": "0.10.0-alpha.11",
44
"private": false,
55
"main": "dist/index.js",
66
"types": "dist/index.d.ts",
@@ -60,7 +60,7 @@
6060
"style-loader": "4.0.0",
6161
"ts-loader": "9.5.1",
6262
"ts-node": "10.9.2",
63-
"typescript": "5.6.2",
63+
"typescript": "5.9.2",
6464
"webpack": "5.95.0",
6565
"webpack-cli": "5.1.4",
6666
"webpack-dev-server": "5.2.2"

src/components/mediaPlayer/player/FilePlayer.tsx

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -3,7 +3,6 @@ import { cnx } from '../../../util';
33
import {
44
FilePlayerProps,
55
MediaPlayerFunction,
6-
MediaPlayerParentFunction,
76
MediaPlayerPlaybackRates,
87
} from '../lib';
98

src/components/mediaPlayer/player/TwitchPlayer.tsx

Lines changed: 86 additions & 56 deletions
Original file line numberDiff line numberDiff line change
@@ -1,11 +1,12 @@
11
import React, {
22
forwardRef,
3+
useEffect,
34
useImperativeHandle,
45
useRef,
5-
useEffect,
6+
useState,
67
} from 'react';
78
import { cnx } from '../../../util';
8-
import { FilePlayerProps, MediaPlayerFunction } from '../lib';
9+
import { MediaPlayerFunction, PlayerProps } from '../lib';
910

1011
// Helper to extract Twitch video/clip ID from src
1112
function getTwitchInfo(src: string | { src: string }) {
@@ -21,10 +22,12 @@ function getTwitchInfo(src: string | { src: string }) {
2122
return null;
2223
}
2324

24-
const TwitchPlayer = forwardRef<MediaPlayerFunction, FilePlayerProps>(
25+
const TwitchPlayer = forwardRef<MediaPlayerFunction, PlayerProps<any>>(
2526
(props, ref) => {
27+
const [playling, setPlaying] = useState(false);
2628
const embedRef = useRef<HTMLDivElement>(null);
27-
const playerRef = useRef<any>(null);
29+
const [init, setInit] = useState<boolean>(false);
30+
const [player, setPlayer] = useState<any>(null);
2831
const { playerProps } = props;
2932
const {
3033
className,
@@ -33,7 +36,6 @@ const TwitchPlayer = forwardRef<MediaPlayerFunction, FilePlayerProps>(
3336
height,
3437
controls,
3538
autoplay,
36-
loop,
3739
onEnded,
3840
onPause,
3941
onPlay,
@@ -46,7 +48,6 @@ const TwitchPlayer = forwardRef<MediaPlayerFunction, FilePlayerProps>(
4648

4749
// Load Twitch embed script
4850
useEffect(() => {
49-
console.log('Loading Twitch embed script');
5051
if ((window as any).Twitch && (window as any).Twitch.Embed) return;
5152
if (!document.getElementById('twitch-embed-script')) {
5253
const script = document.createElement('script');
@@ -56,12 +57,29 @@ const TwitchPlayer = forwardRef<MediaPlayerFunction, FilePlayerProps>(
5657
}
5758
}, []);
5859

59-
// Create Twitch embed
6060
useEffect(() => {
61-
if (!twitchInfo || !embedRef.current) return () => {};
62-
function createEmbed() {
63-
console.log('PlayerRef', playerRef.current);
64-
if (playerRef.current) return;
61+
if (playling && player && onProgress) {
62+
onDurationChange?.({
63+
target: player,
64+
currentTime: player.getPlayer?.()?.getCurrentTime?.() ?? 0,
65+
duration: player.getPlayer?.()?.getDuration?.() ?? 0,
66+
});
67+
const interval = setInterval(() => {
68+
onProgress?.({
69+
target: player,
70+
currentTime: player.getPlayer?.()?.getCurrentTime?.() ?? 0,
71+
duration: player.getPlayer?.()?.getDuration?.() ?? 0,
72+
});
73+
}, 1000);
74+
return () => {
75+
clearInterval(interval);
76+
};
77+
}
78+
return () => {};
79+
}, [player, playling]);
80+
81+
useEffect(() => {
82+
if (init && !player) {
6583
const options: any = {
6684
width: width || '100%',
6785
height: height || 360,
@@ -73,77 +91,89 @@ const TwitchPlayer = forwardRef<MediaPlayerFunction, FilePlayerProps>(
7391
} else {
7492
options.clip = twitchInfo!.id;
7593
}
76-
if (controls !== undefined) options.controls = controls;
77-
if (loop !== undefined) options.loop = loop;
78-
playerRef.current = new (window as any).Twitch.Embed(
94+
95+
options.controls = controls === true;
96+
97+
const pl = new (window as any).Twitch.Embed(
7998
embedRef.current!.id,
8099
options,
81100
);
82-
playerRef.current.addEventListener('play', () => onPlay?.());
83-
playerRef.current.addEventListener('pause', () => onPause?.());
84-
playerRef.current.addEventListener('ended', () => onEnded?.());
85-
playerRef.current.addEventListener('ready', () => onStart?.());
86-
playerRef.current.addEventListener('playing', () => onPlay?.());
87-
playerRef.current.addEventListener('timeupdate', () => {
88-
const player = playerRef.current.getPlayer();
89-
onProgress?.({
90-
target: player,
91-
currentTime: player.getCurrentTime(),
92-
duration: player.getDuration(),
93-
});
101+
pl.addEventListener('play', () => {
102+
setPlaying(true);
103+
onPlay?.();
104+
});
105+
pl.addEventListener('pause', () => {
106+
setPlaying(false);
107+
onPause?.();
108+
});
109+
pl.addEventListener('ended', () => {
110+
setPlaying(false);
111+
onEnded?.();
112+
});
113+
pl.addEventListener('ready', () => {
94114
onDurationChange?.({
95-
target: player,
96-
currentTime: player.getCurrentTime(),
97-
duration: player.getDuration(),
115+
target: pl,
116+
currentTime: pl.getPlayer?.()?.getCurrentTime?.() ?? 0,
117+
duration: pl.getPlayer?.()?.getDuration?.() ?? 0,
98118
});
119+
onStart?.();
120+
});
121+
pl.addEventListener('playing', () => {
122+
setPlaying(true);
123+
onPlay?.();
124+
});
125+
console.log(pl);
126+
pl.addEventListener('timeupdate', () => {
127+
console.log('timeupdate');
99128
});
129+
setPlayer(pl);
130+
return () => {
131+
if (pl) {
132+
pl.removeEventListener?.('play', onPlay);
133+
pl.removeEventListener?.('pause', onPause);
134+
pl.removeEventListener?.('ended', onEnded);
135+
pl.removeEventListener?.('ready', onStart);
136+
pl.removeEventListener?.('playing', onPlay);
137+
pl.removeEventListener?.('timeupdate', onProgress);
138+
}
139+
};
100140
}
101-
if ((window as any).Twitch && (window as any).Twitch.Embed) {
102-
createEmbed();
103-
} else {
141+
return () => {};
142+
}, [player, init]);
143+
144+
// Create Twitch embed
145+
useEffect(() => {
146+
if (!twitchInfo || !embedRef.current) return;
147+
if (!(window as any).Twitch || !(window as any).Twitch.Embed) {
104148
document
105149
.getElementById('twitch-embed-script')
106150
?.addEventListener('load', () => {
107-
createEmbed();
151+
setInit(true);
108152
});
153+
} else {
154+
setInit(true);
109155
}
110-
return () => {
111-
if (playerRef.current) {
112-
playerRef.current.removeEventListener?.('play', onPlay);
113-
playerRef.current.removeEventListener?.('pause', onPause);
114-
playerRef.current.removeEventListener?.('ended', onEnded);
115-
playerRef.current.removeEventListener?.('ready', onStart);
116-
playerRef.current.removeEventListener?.('playing', onPlay);
117-
playerRef.current.removeEventListener?.('timeupdate', onProgress);
118-
playerRef.current = null;
119-
}
120-
};
121-
}, [twitchInfo, playerRef]);
156+
}, [twitchInfo, embedRef]);
122157

123158
// Imperative API
124159
useImperativeHandle(ref, () => ({
125160
seekTo(to: number) {
126-
const player = playerRef.current?.getPlayer?.();
127-
player?.seek?.(to);
161+
player?.getPlayer?.()?.seek?.(to);
128162
},
129163
getRawPlayer<Y>(): Y | null {
130-
return playerRef.current?.getPlayer?.() as Y | null;
164+
return player?.getPlayer?.() as Y | null;
131165
},
132166
play() {
133-
const player = playerRef.current?.getPlayer?.();
134-
player?.play?.();
167+
player?.getPlayer?.()?.play?.();
135168
},
136169
pause() {
137-
const player = playerRef.current?.getPlayer?.();
138-
player?.pause?.();
170+
player?.getPlayer?.()?.pause?.();
139171
},
140172
getDuration() {
141-
const player = playerRef.current?.getPlayer?.();
142-
return player?.getDuration?.() ?? -1;
173+
return player?.getPlayer?.()?.getDuration?.() ?? -1;
143174
},
144175
getCurrentTime() {
145-
const player = playerRef.current?.getPlayer?.();
146-
return player?.getCurrentTime?.() ?? -1;
176+
return player?.getPlayer?.()?.getCurrentTime?.() ?? -1;
147177
},
148178
setPlayBackRate() {},
149179
}));

src/renderer.tsx

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -49,6 +49,7 @@ const App = () => {
4949
onEnded={() => setStarted(false)}
5050
onPlay={() => setPlaying(true)}
5151
onPause={() => setPlaying(false)}
52+
controls
5253
/>
5354
<MediaplayerDevControls
5455
ref={ref}

0 commit comments

Comments
 (0)