@ldelia/react-media 0.8.0 → 0.8.2
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/components/reproduction-widget/models/Player/PlayAlongPlayer.d.ts +5 -1
- package/dist/components/reproduction-widget/models/Player/PlayAlongPlayer.js +4 -7
- package/dist/components/reproduction-widget/models/Player/PlayerEvents.d.ts +1 -0
- package/dist/components/reproduction-widget/models/Player/PlayerEvents.js +1 -0
- package/dist/components/reproduction-widget/models/Player/YouTubePlayer.d.ts +10 -2
- package/dist/components/reproduction-widget/models/Player/YouTubePlayer.js +64 -10
- package/dist/components/reproduction-widget/models/Reproduction.d.ts +3 -4
- package/dist/components/reproduction-widget/models/Reproduction.js +15 -20
- package/dist/stories/reproduction-widget.stories.js +8 -2
- package/package.json +2 -2
|
@@ -13,12 +13,12 @@ export declare class PlayAlongPlayer {
|
|
|
13
13
|
static get EVENTS(): {
|
|
14
14
|
readonly READY: "READY";
|
|
15
15
|
readonly FINISH: "FINISH";
|
|
16
|
+
readonly ERROR: "ERROR";
|
|
16
17
|
};
|
|
17
18
|
play(): void;
|
|
18
19
|
pause(): void;
|
|
19
20
|
stop(): void;
|
|
20
21
|
seekTo(seconds: number): void;
|
|
21
|
-
setVolume(volume: number): void;
|
|
22
22
|
getCurrentTime(): number;
|
|
23
23
|
getDuration(): number;
|
|
24
24
|
isAvailable(): boolean;
|
|
@@ -26,6 +26,10 @@ export declare class PlayAlongPlayer {
|
|
|
26
26
|
setPlaybackRate(playbackRate: number): void;
|
|
27
27
|
on(eventName: keyof typeof PlayAlongPlayer.EVENTS, handler: () => void): number | undefined;
|
|
28
28
|
dispatch(eventName: keyof typeof PlayAlongPlayer.EVENTS): void;
|
|
29
|
+
countingStarted(): void;
|
|
30
|
+
countingFinished(): void;
|
|
31
|
+
setVolume(volume: number): void;
|
|
32
|
+
getVolume(): number;
|
|
29
33
|
private setInnerPlayer;
|
|
30
34
|
}
|
|
31
35
|
export {};
|
|
@@ -44,7 +44,6 @@ export class PlayAlongPlayer {
|
|
|
44
44
|
seekTo(seconds) {
|
|
45
45
|
this.currentTime = seconds;
|
|
46
46
|
}
|
|
47
|
-
setVolume(volume) { }
|
|
48
47
|
getCurrentTime() {
|
|
49
48
|
return this.currentTime;
|
|
50
49
|
}
|
|
@@ -65,8 +64,6 @@ export class PlayAlongPlayer {
|
|
|
65
64
|
}
|
|
66
65
|
on(eventName, handler) {
|
|
67
66
|
switch (eventName) {
|
|
68
|
-
case PlayAlongPlayer.EVENTS.READY:
|
|
69
|
-
return this[dispatchOnReadyHandlers].push(handler);
|
|
70
67
|
case PlayAlongPlayer.EVENTS.FINISH:
|
|
71
68
|
return this[dispatchOnFinishHandlers].push(handler);
|
|
72
69
|
default:
|
|
@@ -77,9 +74,6 @@ export class PlayAlongPlayer {
|
|
|
77
74
|
let handler, i, len;
|
|
78
75
|
let ref = [];
|
|
79
76
|
switch (eventName) {
|
|
80
|
-
case PlayAlongPlayer.EVENTS.READY:
|
|
81
|
-
ref = this[dispatchOnReadyHandlers];
|
|
82
|
-
break;
|
|
83
77
|
case PlayAlongPlayer.EVENTS.FINISH:
|
|
84
78
|
ref = this[dispatchOnFinishHandlers];
|
|
85
79
|
break;
|
|
@@ -91,8 +85,11 @@ export class PlayAlongPlayer {
|
|
|
91
85
|
handler();
|
|
92
86
|
}
|
|
93
87
|
}
|
|
88
|
+
countingStarted() { }
|
|
89
|
+
countingFinished() { }
|
|
90
|
+
setVolume(volume) { }
|
|
91
|
+
getVolume() { return 0; }
|
|
94
92
|
setInnerPlayer(innerPlayer) {
|
|
95
93
|
this.innerPlayer = innerPlayer;
|
|
96
|
-
this.dispatch(PlayAlongPlayer.EVENTS.READY);
|
|
97
94
|
}
|
|
98
95
|
}
|
|
@@ -3,16 +3,20 @@ import { PlayAlongPlayer } from './PlayAlongPlayer';
|
|
|
3
3
|
export type InnerYouTubePlayerInterface = YT.Player;
|
|
4
4
|
declare const dispatchOnReadyHandlers: unique symbol;
|
|
5
5
|
declare const dispatchOnFinishHandlers: unique symbol;
|
|
6
|
+
declare const dispatchOnErrorHandlers: unique symbol;
|
|
6
7
|
export declare class YouTubePlayer {
|
|
7
8
|
private currentTime;
|
|
8
9
|
private isRunning;
|
|
10
|
+
private volume;
|
|
9
11
|
private innerPlayer;
|
|
10
12
|
private [dispatchOnReadyHandlers];
|
|
11
13
|
private [dispatchOnFinishHandlers];
|
|
14
|
+
private [dispatchOnErrorHandlers];
|
|
12
15
|
constructor(innerPlayer: InnerYouTubePlayerInterface);
|
|
13
16
|
static get EVENTS(): {
|
|
14
17
|
readonly READY: "READY";
|
|
15
18
|
readonly FINISH: "FINISH";
|
|
19
|
+
readonly ERROR: "ERROR";
|
|
16
20
|
};
|
|
17
21
|
getInnerPlayer(): YT.Player;
|
|
18
22
|
play(): void;
|
|
@@ -20,12 +24,16 @@ export declare class YouTubePlayer {
|
|
|
20
24
|
stop(): void;
|
|
21
25
|
seekTo(seconds: number): void;
|
|
22
26
|
setVolume(volume: number): void;
|
|
27
|
+
getVolume(): number;
|
|
23
28
|
getCurrentTime(): number;
|
|
24
29
|
getDuration(): number | undefined;
|
|
25
30
|
getAvailablePlaybackRates(): number[];
|
|
26
31
|
setPlaybackRate(playbackRate: number): void;
|
|
27
32
|
isAvailable(): boolean;
|
|
28
|
-
on(eventName: keyof typeof PlayAlongPlayer.EVENTS, handler: () => void): number | undefined;
|
|
29
|
-
dispatch(eventName: keyof typeof PlayAlongPlayer.EVENTS): void;
|
|
33
|
+
on(eventName: keyof typeof PlayAlongPlayer.EVENTS, handler: (error?: any) => void): number | undefined;
|
|
34
|
+
dispatch(eventName: keyof typeof PlayAlongPlayer.EVENTS, error?: any): void;
|
|
35
|
+
countingStarted(): void;
|
|
36
|
+
countingFinished(): void;
|
|
37
|
+
private getErrorMessage;
|
|
30
38
|
}
|
|
31
39
|
export {};
|
|
@@ -2,19 +2,27 @@ import { PlayAlongPlayer } from './PlayAlongPlayer';
|
|
|
2
2
|
import { PLAYER_EVENTS } from './PlayerEvents';
|
|
3
3
|
const dispatchOnReadyHandlers = Symbol();
|
|
4
4
|
const dispatchOnFinishHandlers = Symbol();
|
|
5
|
+
const dispatchOnErrorHandlers = Symbol();
|
|
5
6
|
export class YouTubePlayer {
|
|
6
7
|
constructor(innerPlayer) {
|
|
8
|
+
this.volume = 50; // between 0 and 100
|
|
7
9
|
this[dispatchOnFinishHandlers] = [];
|
|
8
10
|
this[dispatchOnReadyHandlers] = [];
|
|
11
|
+
this[dispatchOnErrorHandlers] = [];
|
|
9
12
|
this.currentTime = 0;
|
|
10
13
|
this.isRunning = false;
|
|
11
14
|
this.innerPlayer = innerPlayer;
|
|
12
|
-
this.innerPlayer = innerPlayer;
|
|
13
|
-
this.dispatch(YouTubePlayer.EVENTS.READY);
|
|
14
15
|
// This is necessary for avoiding the state video cued.
|
|
15
16
|
// When a video is in this state, when the user seeks to X, the song is played
|
|
16
17
|
this.innerPlayer.playVideo();
|
|
17
18
|
this.innerPlayer.pauseVideo();
|
|
19
|
+
this.innerPlayer.addEventListener('onError', (event) => {
|
|
20
|
+
this.isRunning = false;
|
|
21
|
+
this.dispatch(YouTubePlayer.EVENTS.ERROR, {
|
|
22
|
+
code: event.data,
|
|
23
|
+
message: this.getErrorMessage(event.data)
|
|
24
|
+
});
|
|
25
|
+
});
|
|
18
26
|
this.innerPlayer.addEventListener('onStateChange', (videoState) => {
|
|
19
27
|
switch (videoState.data) {
|
|
20
28
|
case YT.PlayerState.ENDED:
|
|
@@ -62,8 +70,12 @@ export class YouTubePlayer {
|
|
|
62
70
|
}
|
|
63
71
|
}
|
|
64
72
|
setVolume(volume) {
|
|
73
|
+
this.volume = volume;
|
|
65
74
|
this.getInnerPlayer().setVolume(volume);
|
|
66
75
|
}
|
|
76
|
+
getVolume() {
|
|
77
|
+
return this.volume;
|
|
78
|
+
}
|
|
67
79
|
getCurrentTime() {
|
|
68
80
|
return this.isRunning
|
|
69
81
|
? this.getInnerPlayer().getCurrentTime()
|
|
@@ -88,30 +100,72 @@ export class YouTubePlayer {
|
|
|
88
100
|
}
|
|
89
101
|
on(eventName, handler) {
|
|
90
102
|
switch (eventName) {
|
|
91
|
-
case PlayAlongPlayer.EVENTS.READY:
|
|
92
|
-
return this[dispatchOnReadyHandlers].push(handler);
|
|
93
103
|
case PlayAlongPlayer.EVENTS.FINISH:
|
|
94
104
|
return this[dispatchOnFinishHandlers].push(handler);
|
|
105
|
+
case PlayAlongPlayer.EVENTS.ERROR:
|
|
106
|
+
return this[dispatchOnErrorHandlers].push(handler);
|
|
95
107
|
default:
|
|
96
108
|
break;
|
|
97
109
|
}
|
|
98
110
|
}
|
|
99
|
-
dispatch(eventName) {
|
|
100
|
-
let handler
|
|
111
|
+
dispatch(eventName, error) {
|
|
112
|
+
let handler;
|
|
113
|
+
let i;
|
|
114
|
+
let len;
|
|
101
115
|
let ref = [];
|
|
102
116
|
switch (eventName) {
|
|
103
|
-
case YouTubePlayer.EVENTS.READY:
|
|
104
|
-
ref = this[dispatchOnReadyHandlers];
|
|
105
|
-
break;
|
|
106
117
|
case YouTubePlayer.EVENTS.FINISH:
|
|
107
118
|
ref = this[dispatchOnFinishHandlers];
|
|
108
119
|
break;
|
|
120
|
+
case YouTubePlayer.EVENTS.ERROR:
|
|
121
|
+
ref = this[dispatchOnErrorHandlers];
|
|
122
|
+
break;
|
|
109
123
|
default:
|
|
110
124
|
break;
|
|
111
125
|
}
|
|
112
126
|
for (i = 0, len = ref.length; i < len; i++) {
|
|
113
127
|
handler = ref[i];
|
|
114
|
-
setTimeout(handler, 0);
|
|
128
|
+
setTimeout(() => handler(error), 0);
|
|
129
|
+
}
|
|
130
|
+
}
|
|
131
|
+
countingStarted() {
|
|
132
|
+
/**
|
|
133
|
+
* iOS browsers enforce strict autoplay policies that require video playback
|
|
134
|
+
* to begin synchronously within a user interaction event (e.g., a tap or click).
|
|
135
|
+
* When we implemented the counting-in feature (1, 2, 1, 2, 3, go...),
|
|
136
|
+
* the asynchronous delays between counts caused iOS to lose the user interaction context,
|
|
137
|
+
* blocking video playback after the countdown completed.
|
|
138
|
+
* The video would work fine on web and Android, but fail to start on iOS Safari.
|
|
139
|
+
* To resolve this, we adopted a muted-first approach:
|
|
140
|
+
* the video begins playing immediately when the user initiates playback,
|
|
141
|
+
* but remains muted during the countdown sequence.
|
|
142
|
+
* Once the countdown completes, we unmute the video and restore the desired volume.
|
|
143
|
+
* This strategy satisfies iOS's autoplay requirements (muted videos can autoplay)
|
|
144
|
+
* while preserving the musical countdown experience.
|
|
145
|
+
* The user never notices the video is playing during the countdown
|
|
146
|
+
* since it's both muted and visually obscured by the countdown overlay.
|
|
147
|
+
* */
|
|
148
|
+
this.getInnerPlayer().setVolume(0);
|
|
149
|
+
this.getInnerPlayer().playVideo();
|
|
150
|
+
}
|
|
151
|
+
countingFinished() {
|
|
152
|
+
this.getInnerPlayer().pauseVideo();
|
|
153
|
+
this.getInnerPlayer().seekTo(0, true);
|
|
154
|
+
this.setVolume(this.volume);
|
|
155
|
+
}
|
|
156
|
+
getErrorMessage(errorCode) {
|
|
157
|
+
switch (errorCode) {
|
|
158
|
+
case YT.PlayerError.InvalidParam:
|
|
159
|
+
return 'Invalid parameter value';
|
|
160
|
+
case YT.PlayerError.Html5Error:
|
|
161
|
+
return 'HTML5 player error';
|
|
162
|
+
case YT.PlayerError.VideoNotFound:
|
|
163
|
+
return 'Video not found';
|
|
164
|
+
case YT.PlayerError.EmbeddingNotAllowed:
|
|
165
|
+
case YT.PlayerError.EmbeddingNotAllowed2:
|
|
166
|
+
return 'Video cannot be played in embedded players';
|
|
167
|
+
default:
|
|
168
|
+
return `Unknown error (code: ${errorCode})`;
|
|
115
169
|
}
|
|
116
170
|
}
|
|
117
171
|
}
|
|
@@ -10,15 +10,14 @@ declare const dispatchOnPlayHandlers: unique symbol;
|
|
|
10
10
|
declare const dispatchOnPlayingHandlers: unique symbol;
|
|
11
11
|
declare const dispatchOnPausedHandlers: unique symbol;
|
|
12
12
|
declare const dispatchOnFinishHandlers: unique symbol;
|
|
13
|
+
declare const dispatchOnErrorHandlers: unique symbol;
|
|
13
14
|
export declare class Reproduction {
|
|
14
15
|
private player;
|
|
15
16
|
private requiresCountingIn;
|
|
16
17
|
private songTempo;
|
|
17
18
|
private state;
|
|
18
|
-
private ready;
|
|
19
19
|
private interval;
|
|
20
20
|
private countingInCounter;
|
|
21
|
-
private volume;
|
|
22
21
|
private [dispatchOnReadyHandlers];
|
|
23
22
|
private [dispatchOnSongStartHandlers];
|
|
24
23
|
private [dispatchOnCountingInHandlers];
|
|
@@ -26,15 +25,16 @@ export declare class Reproduction {
|
|
|
26
25
|
private [dispatchOnPlayingHandlers];
|
|
27
26
|
private [dispatchOnPausedHandlers];
|
|
28
27
|
private [dispatchOnFinishHandlers];
|
|
28
|
+
private [dispatchOnErrorHandlers];
|
|
29
29
|
constructor(player: Player, requiresCountingIn: boolean, songTempo: number, volume: number);
|
|
30
30
|
static get EVENTS(): {
|
|
31
|
-
readonly READY: "READY";
|
|
32
31
|
readonly START: "START";
|
|
33
32
|
readonly COUNTING_IN: "COUNTING_IN";
|
|
34
33
|
readonly PLAY: "PLAY";
|
|
35
34
|
readonly PLAYING: "PLAYING";
|
|
36
35
|
readonly PAUSED: "PAUSED";
|
|
37
36
|
readonly FINISH: "FINISH";
|
|
37
|
+
readonly ERROR: "ERROR";
|
|
38
38
|
};
|
|
39
39
|
static get STATES(): {
|
|
40
40
|
STOPPED: number;
|
|
@@ -49,7 +49,6 @@ export declare class Reproduction {
|
|
|
49
49
|
play(): void;
|
|
50
50
|
pause(): void;
|
|
51
51
|
stop(): void;
|
|
52
|
-
isReady(): boolean;
|
|
53
52
|
isPlaying(): boolean;
|
|
54
53
|
isStopped(): boolean;
|
|
55
54
|
isPaused(): boolean;
|
|
@@ -7,13 +7,13 @@ const STATES = {
|
|
|
7
7
|
PAUSED: 3,
|
|
8
8
|
};
|
|
9
9
|
const EVENTS = {
|
|
10
|
-
READY: 'READY',
|
|
11
10
|
START: 'START',
|
|
12
11
|
COUNTING_IN: 'COUNTING_IN',
|
|
13
12
|
PLAY: 'PLAY',
|
|
14
13
|
PLAYING: 'PLAYING',
|
|
15
14
|
PAUSED: 'PAUSED',
|
|
16
15
|
FINISH: 'FINISH',
|
|
16
|
+
ERROR: 'ERROR',
|
|
17
17
|
};
|
|
18
18
|
const dispatchOnReadyHandlers = Symbol();
|
|
19
19
|
const dispatchOnSongStartHandlers = Symbol();
|
|
@@ -22,9 +22,9 @@ const dispatchOnPlayHandlers = Symbol();
|
|
|
22
22
|
const dispatchOnPlayingHandlers = Symbol();
|
|
23
23
|
const dispatchOnPausedHandlers = Symbol();
|
|
24
24
|
const dispatchOnFinishHandlers = Symbol();
|
|
25
|
+
const dispatchOnErrorHandlers = Symbol();
|
|
25
26
|
export class Reproduction {
|
|
26
27
|
constructor(player, requiresCountingIn, songTempo, volume) {
|
|
27
|
-
this.volume = 50; // between 0 and 100
|
|
28
28
|
this[dispatchOnReadyHandlers] = [];
|
|
29
29
|
this[dispatchOnSongStartHandlers] = [];
|
|
30
30
|
this[dispatchOnCountingInHandlers] = [];
|
|
@@ -32,23 +32,22 @@ export class Reproduction {
|
|
|
32
32
|
this[dispatchOnPlayingHandlers] = [];
|
|
33
33
|
this[dispatchOnPausedHandlers] = [];
|
|
34
34
|
this[dispatchOnFinishHandlers] = [];
|
|
35
|
+
this[dispatchOnErrorHandlers] = [];
|
|
35
36
|
this.songTempo = songTempo;
|
|
36
37
|
this.player = player;
|
|
37
|
-
this.ready = false;
|
|
38
38
|
this.state = Reproduction.STATES.STOPPED;
|
|
39
39
|
this.interval = null;
|
|
40
40
|
this.requiresCountingIn = requiresCountingIn;
|
|
41
41
|
this.countingInCounter = 0;
|
|
42
|
-
this.setVolume(volume);
|
|
43
|
-
this.player.on(PLAYER_EVENTS.READY, () => {
|
|
44
|
-
this.ready = true;
|
|
45
|
-
this.dispatch(Reproduction.EVENTS.READY);
|
|
46
|
-
});
|
|
42
|
+
this.player.setVolume(volume);
|
|
47
43
|
this.player.on(PLAYER_EVENTS.FINISH, () => {
|
|
48
44
|
this.state = Reproduction.STATES.STOPPED;
|
|
49
45
|
clearInterval(this.interval);
|
|
50
46
|
this.dispatch(Reproduction.EVENTS.FINISH);
|
|
51
47
|
});
|
|
48
|
+
this.player.on(PLAYER_EVENTS.ERROR, (error) => {
|
|
49
|
+
this.dispatch(Reproduction.EVENTS.ERROR, { error });
|
|
50
|
+
});
|
|
52
51
|
}
|
|
53
52
|
static get EVENTS() {
|
|
54
53
|
return EVENTS;
|
|
@@ -61,8 +60,6 @@ export class Reproduction {
|
|
|
61
60
|
}
|
|
62
61
|
on(eventName, handler) {
|
|
63
62
|
switch (eventName) {
|
|
64
|
-
case Reproduction.EVENTS.READY:
|
|
65
|
-
return this[dispatchOnReadyHandlers].push(handler);
|
|
66
63
|
case Reproduction.EVENTS.START:
|
|
67
64
|
return this[dispatchOnSongStartHandlers].push(handler);
|
|
68
65
|
case Reproduction.EVENTS.COUNTING_IN:
|
|
@@ -75,6 +72,8 @@ export class Reproduction {
|
|
|
75
72
|
return this[dispatchOnPausedHandlers].push(handler);
|
|
76
73
|
case Reproduction.EVENTS.FINISH:
|
|
77
74
|
return this[dispatchOnFinishHandlers].push(handler);
|
|
75
|
+
case Reproduction.EVENTS.ERROR:
|
|
76
|
+
return this[dispatchOnErrorHandlers].push(handler);
|
|
78
77
|
default:
|
|
79
78
|
break;
|
|
80
79
|
}
|
|
@@ -83,9 +82,6 @@ export class Reproduction {
|
|
|
83
82
|
let handler, i, len;
|
|
84
83
|
let ref = [];
|
|
85
84
|
switch (eventName) {
|
|
86
|
-
case Reproduction.EVENTS.READY:
|
|
87
|
-
ref = this[dispatchOnReadyHandlers];
|
|
88
|
-
break;
|
|
89
85
|
case Reproduction.EVENTS.START:
|
|
90
86
|
ref = this[dispatchOnSongStartHandlers];
|
|
91
87
|
break;
|
|
@@ -104,13 +100,15 @@ export class Reproduction {
|
|
|
104
100
|
case Reproduction.EVENTS.FINISH:
|
|
105
101
|
ref = this[dispatchOnFinishHandlers];
|
|
106
102
|
break;
|
|
103
|
+
case Reproduction.EVENTS.ERROR:
|
|
104
|
+
ref = this[dispatchOnErrorHandlers];
|
|
105
|
+
break;
|
|
107
106
|
default:
|
|
108
107
|
break;
|
|
109
108
|
}
|
|
110
109
|
for (i = 0, len = ref.length; i < len; i++) {
|
|
111
110
|
handler = ref[i];
|
|
112
111
|
handler(args);
|
|
113
|
-
// setTimeout(handler, 0);
|
|
114
112
|
}
|
|
115
113
|
}
|
|
116
114
|
start() {
|
|
@@ -148,10 +146,6 @@ export class Reproduction {
|
|
|
148
146
|
clearInterval(this.interval);
|
|
149
147
|
this.dispatch(Reproduction.EVENTS.FINISH);
|
|
150
148
|
}
|
|
151
|
-
isReady() {
|
|
152
|
-
// It's necessary to avoid play the reproduction-widget when the player is not ready
|
|
153
|
-
return this.ready;
|
|
154
|
-
}
|
|
155
149
|
isPlaying() {
|
|
156
150
|
return this.state === Reproduction.STATES.PLAYING;
|
|
157
151
|
}
|
|
@@ -181,7 +175,7 @@ export class Reproduction {
|
|
|
181
175
|
this.player.seekTo(seconds);
|
|
182
176
|
}
|
|
183
177
|
getVolume() {
|
|
184
|
-
return this.
|
|
178
|
+
return this.player.getVolume();
|
|
185
179
|
}
|
|
186
180
|
setVolume(volume) {
|
|
187
181
|
if (volume < 0) {
|
|
@@ -190,7 +184,6 @@ export class Reproduction {
|
|
|
190
184
|
else if (volume > 100) {
|
|
191
185
|
volume = 100;
|
|
192
186
|
}
|
|
193
|
-
this.volume = volume;
|
|
194
187
|
this.player.setVolume(volume);
|
|
195
188
|
}
|
|
196
189
|
getAvailablePlaybackRates() {
|
|
@@ -207,6 +200,7 @@ export class Reproduction {
|
|
|
207
200
|
}
|
|
208
201
|
countInAndPlay(timeout, limit) {
|
|
209
202
|
// the initial count starts instantly, no need to wait
|
|
203
|
+
this.player.countingStarted();
|
|
210
204
|
this.countingInCounter++;
|
|
211
205
|
this.dispatch(Reproduction.EVENTS.COUNTING_IN, { countingInCounter: this.countingInCounter });
|
|
212
206
|
const interval = setInterval(() => {
|
|
@@ -218,6 +212,7 @@ export class Reproduction {
|
|
|
218
212
|
this.countInAndPlay(this.getBPMInterval(), 5);
|
|
219
213
|
}
|
|
220
214
|
else {
|
|
215
|
+
this.player.countingFinished();
|
|
221
216
|
this.play();
|
|
222
217
|
}
|
|
223
218
|
}
|
|
@@ -18,7 +18,7 @@ const Template = (args) => {
|
|
|
18
18
|
reproductionInstance.on('PLAYING', refreshEvent);
|
|
19
19
|
reproductionInstance.on('PAUSED', refreshEvent);
|
|
20
20
|
reproductionInstance.on('FINISH', refreshEvent);
|
|
21
|
-
reproductionInstance.
|
|
21
|
+
reproductionInstance.on('ERROR', (args) => { console.error("Reproduction error", args); });
|
|
22
22
|
}, []);
|
|
23
23
|
const handleStop = () => {
|
|
24
24
|
if (reproduction) {
|
|
@@ -35,12 +35,18 @@ const Template = (args) => {
|
|
|
35
35
|
reproduction.play();
|
|
36
36
|
}
|
|
37
37
|
};
|
|
38
|
+
const handleStart = () => {
|
|
39
|
+
if (reproduction) {
|
|
40
|
+
reproduction.start();
|
|
41
|
+
}
|
|
42
|
+
};
|
|
38
43
|
return (React.createElement("div", null,
|
|
39
44
|
React.createElement(ReproductionWidget, Object.assign({}, args, { onInit: handleInit })),
|
|
40
45
|
React.createElement("div", null,
|
|
41
46
|
React.createElement("button", { onClick: handleStop, disabled: !reproduction || reproduction.isStopped() }, "Stop"),
|
|
42
47
|
React.createElement("button", { onClick: handlePause, disabled: !reproduction || !reproduction.isPlaying() }, "Pause"),
|
|
43
|
-
React.createElement("button", { onClick: handleResume, disabled: !reproduction || reproduction.isPlaying() }, "Resume"),
|
|
48
|
+
React.createElement("button", { onClick: handleResume, disabled: !reproduction || reproduction.isPlaying() || reproduction.getCurrentTime() > 0 }, "Resume"),
|
|
49
|
+
React.createElement("button", { onClick: handleStart, disabled: !reproduction || reproduction.isPlaying() }, "Start"),
|
|
44
50
|
reproduction && (React.createElement("div", null,
|
|
45
51
|
"Current time: ", reproduction === null || reproduction === void 0 ? void 0 :
|
|
46
52
|
reproduction.getCurrentTime())),
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@ldelia/react-media",
|
|
3
|
-
"version": "0.8.
|
|
3
|
+
"version": "0.8.2",
|
|
4
4
|
"description": "A React components collection for media-related features.",
|
|
5
5
|
"private": false,
|
|
6
6
|
"keywords": [
|
|
@@ -127,7 +127,7 @@
|
|
|
127
127
|
"@types/react": "^18.3.3",
|
|
128
128
|
"@types/react-dom": "^18.3.0",
|
|
129
129
|
"@types/styled-components": "^5.1.34",
|
|
130
|
-
"@types/youtube": "^0.
|
|
130
|
+
"@types/youtube": "^0.1.2",
|
|
131
131
|
"babel-loader": "^9.1.3",
|
|
132
132
|
"eslint-config-prettier": "^9.1.0",
|
|
133
133
|
"eslint-plugin-prettier": "^5.1.3",
|