import React, { Fragment } from 'react';
import PropTypes from 'prop-types';
import Sound from 'react-sound';
import { sprintf } from 'sprintf-js';
import classNames from 'classnames';
import soundProvider from './soundProvider';
import Cover from './components/Cover';
import Button from './components/Button';
import ProgressBar from './components/ProgressBar';
import Time from './components/Time';
import VolumeControl from './components/VolumeControl';
import TracklistWrap from './components/TracklistWrap';
import {
PlayIcon,
PauseIcon,
NextIcon,
PreviousIcon,
PlaylistIcon,
RefreshIcon,
LyricsIcon,
} from './components/Icons';
import { AppContext } from '../App';
import typographyDisabled from '../utils/typography-disabled';
class GlobalFooterPlayer extends React.Component {
constructor(props) {
super(props);
this.state = {
isTrackListOpen: this.props.displayTracklist,
};
this.toggleTracklist = this.toggleTracklist.bind(this);
}
toggleTracklist() {
this.setState(state => ({
isTrackListOpen: !state.isTrackListOpen,
}));
}
render() {
const { isTrackListOpen } = this.state;
const {
tracks,
playStatus,
activeIndex,
volume,
position,
duration,
playbackRate,
currentTrack,
playTrack,
togglePlay,
nextTrack,
prevTrack,
setPosition,
setVolume,
toggleTracklistCycling,
cycleTracks,
setTrackCycling,
setPlaybackRate,
allowPlaybackRate,
allowTracklistToggle,
allowTracklistLoop,
allowTrackLoop,
reverseTrackOrder,
displayTrackNo,
displayTracklistCovers,
displayActiveCover,
limitTracklistHeight,
tracklistHeight,
displayBuyButtons,
buyButtonsTarget,
displayArtistNames,
repeatingTrackIndex,
skipAmount,
skipPosition,
countdownTimerByDefault,
buffering,
} = this.props;
const classes = classNames({
'ai-wrap': true,
'ai-type-global-footer': true,
'ai-is-loading': !tracks.length,
'ai-with-typography': !typographyDisabled(),
});
const audioControlClasses = classNames({
'ai-audio-control': true,
'ai-audio-playing': playStatus === Sound.status.PLAYING,
'ai-audio-loading': buffering,
});
return (
(this.root = ref)} // eslint-disable-line no-return-assign
className={classes}
>
{displayActiveCover && (
)}
{tracks.length > 1 && (
)}
{tracks.length > 1 && (
)}
{allowTracklistLoop && (
)}
{allowPlaybackRate && (
)}
{skipAmount > 0 && (
)}
{currentTrack && currentTrack.lyrics && !isTrackListOpen && (
{({ toggleLyricsModal }) => (
)}
)}
{currentTrack.title}
{(tracks.length === 0 || currentTrack.subtitle) &&
displayArtistNames && (
{currentTrack.subtitle}
)}
{allowTracklistToggle && (
)}
);
}
}
GlobalFooterPlayer.propTypes = {
tracks: PropTypes.arrayOf(PropTypes.object),
playStatus: PropTypes.oneOf([
Sound.status.PLAYING,
Sound.status.PAUSED,
Sound.status.STOPPED,
]),
activeIndex: PropTypes.number,
volume: PropTypes.number,
position: PropTypes.number,
duration: PropTypes.number,
currentTrack: PropTypes.object.isRequired, // eslint-disable-line react/forbid-prop-types
playTrack: PropTypes.func.isRequired,
togglePlay: PropTypes.func.isRequired,
nextTrack: PropTypes.func.isRequired,
prevTrack: PropTypes.func.isRequired,
setPosition: PropTypes.func.isRequired,
setVolume: PropTypes.func.isRequired,
toggleTracklistCycling: PropTypes.func.isRequired,
cycleTracks: PropTypes.bool.isRequired,
displayTracklist: PropTypes.bool,
allowTracklistToggle: PropTypes.bool,
allowTracklistLoop: PropTypes.bool,
reverseTrackOrder: PropTypes.bool,
displayTrackNo: PropTypes.bool,
displayActiveCover: PropTypes.bool,
displayTracklistCovers: PropTypes.bool,
limitTracklistHeight: PropTypes.bool,
tracklistHeight: PropTypes.number,
displayBuyButtons: PropTypes.bool,
buyButtonsTarget: PropTypes.bool,
displayArtistNames: PropTypes.bool,
setTrackCycling: PropTypes.func.isRequired,
repeatingTrackIndex: PropTypes.number,
allowTrackLoop: PropTypes.bool,
playbackRate: PropTypes.number,
setPlaybackRate: PropTypes.func,
skipAmount: PropTypes.number,
skipPosition: PropTypes.func.isRequired,
countdownTimerByDefault: PropTypes.bool,
allowPlaybackRate: PropTypes.bool,
buffering: PropTypes.bool,
};
export default soundProvider(GlobalFooterPlayer, {
onFinishedPlaying(props) {
const {
repeatingTrackIndex,
cycleTracks,
nextTrack,
activeIndex,
playTrack,
trackQueue,
} = props;
if (repeatingTrackIndex != null) {
playTrack(repeatingTrackIndex);
return;
}
if (cycleTracks) {
nextTrack();
return;
}
// Check if not the last track
if (activeIndex !== trackQueue[trackQueue.length - 1]) {
nextTrack();
}
},
});