Skip to content

Commit

Permalink
Merge pull request #1712 from hicom150/change_audio_tracks
Browse files Browse the repository at this point in the history
Add support for multiple audio tracks
  • Loading branch information
hicom150 authored Oct 13, 2019
2 parents c33acd0 + 2d7b6c0 commit 45920e0
Show file tree
Hide file tree
Showing 5 changed files with 91 additions and 0 deletions.
17 changes: 17 additions & 0 deletions src/renderer/controllers/audio-tracks-controller.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,17 @@
const { dispatch } = require('../lib/dispatcher')

module.exports = class AudioTracksController {
constructor (state) {
this.state = state
}

selectAudioTrack (ix) {
this.state.playing.audioTracks.selectedIndex = ix
dispatch('skip', 0.2) // HACK: hardcoded seek value for smooth audio change
}

toggleAudioTracksMenu () {
const audioTracks = this.state.playing.audioTracks
audioTracks.showMenu = !audioTracks.showMenu
}
}
5 changes: 5 additions & 0 deletions src/renderer/lib/state.js
Original file line number Diff line number Diff line change
Expand Up @@ -105,6 +105,11 @@ function getDefaultPlayState () {
selectedIndex: -1, /* current subtitle track */
showMenu: false /* popover menu, above the video */
},
audioTracks: {
tracks: [],
selectedIndex: 0, /* current audio track */
showMenu: false /* popover menu, above the video */
},
aspectRatio: 0 /* aspect ratio of the video */
}
}
Expand Down
8 changes: 8 additions & 0 deletions src/renderer/main.js
Original file line number Diff line number Diff line change
Expand Up @@ -99,6 +99,10 @@ function onState (err, _state) {
const SubtitlesController = require('./controllers/subtitles-controller')
return new SubtitlesController(state)
}),
audioTracks: createGetter(() => {
const AudioTracksController = require('./controllers/audio-tracks-controller')
return new AudioTracksController(state)
}),
torrent: createGetter(() => {
const TorrentController = require('./controllers/torrent-controller')
return new TorrentController(state)
Expand Down Expand Up @@ -281,6 +285,10 @@ const dispatchHandlers = {
checkForSubtitles: () => controllers.subtitles().checkForSubtitles(),
addSubtitles: (files, autoSelect) => controllers.subtitles().addSubtitles(files, autoSelect),

// Audio Tracks
selectAudioTrack: (index) => controllers.audioTracks().selectAudioTrack(index),
toggleAudioTracksMenu: () => controllers.audioTracks().toggleAudioTracksMenu(),

// Local media: <video>, <audio>, external players
mediaStalled: () => controllers.media().mediaStalled(),
mediaError: (err) => controllers.media().mediaError(err),
Expand Down
56 changes: 56 additions & 0 deletions src/renderer/pages/player-page.js
Original file line number Diff line number Diff line change
Expand Up @@ -95,6 +95,13 @@ function renderMedia (state) {
delete file.selectedSubtitle
}

// Switch to selected audio track
const audioTracks = mediaElement.audioTracks || []
for (let j = 0; j < audioTracks.length; j++) {
const isSelectedTrack = j === state.playing.audioTracks.selectedIndex
audioTracks[j].enabled = isSelectedTrack
}

state.playing.volume = mediaElement.volume
}

Expand Down Expand Up @@ -167,6 +174,18 @@ function renderMedia (state) {

// As soon as we know the video dimensions, resize the window
dispatch('setDimensions', dimensions)

// set audioTracks
const tracks = []
for (let i = 0; i < mediaElement.audioTracks.length; i++) {
tracks.push({
label: mediaElement.audioTracks[i].label || `Track ${i + 1}`,
language: mediaElement.audioTracks[i].language
})
}

state.playing.audioTracks.tracks = tracks
state.playing.audioTracks.selectedIndex = 0
}

// check if we can decode audio track
Expand Down Expand Up @@ -481,6 +500,27 @@ function renderSubtitleOptions (state) {
)
}

function renderAudioTrackOptions (state) {
const audioTracks = state.playing.audioTracks
if (!audioTracks.tracks.length || !audioTracks.showMenu) return

const items = audioTracks.tracks.map(function (track, ix) {
const isSelected = state.playing.audioTracks.selectedIndex === ix
return (
<li key={ix} onClick={dispatcher('selectAudioTrack', ix)}>
<i className='icon'>{'radio_button_' + (isSelected ? 'checked' : 'unchecked')}</i>
{track.label}
</li>
)
})

return (
<ul key='audio-track-options' className='options-list'>
{items}
</ul>
)
}

function renderPlayerControls (state) {
const positionPercent = 100 * state.playing.currentTime / state.playing.duration
const playbackCursorStyle = { left: 'calc(' + positionPercent + '% - 3px)' }
Expand All @@ -489,6 +529,9 @@ function renderPlayerControls (state) {
: state.playing.subtitles.selectedIndex >= 0
? 'active'
: ''
const multiAudioClass = state.playing.audioTracks.tracks.length > 1
? 'active'
: 'disabled'
const prevClass = Playlist.hasPrevious(state) ? '' : 'disabled'
const nextClass = Playlist.hasNext(state) ? '' : 'disabled'

Expand Down Expand Up @@ -553,6 +596,14 @@ function renderPlayerControls (state) {
>
closed_caption
</i>
), (
<i
key='audio-tracks'
className={'icon multi-audio float-right ' + multiAudioClass}
onClick={handleAudioTracks}
>
library_music
</i>
))
}

Expand Down Expand Up @@ -659,6 +710,7 @@ function renderPlayerControls (state) {
{elements}
{renderCastOptions(state)}
{renderSubtitleOptions(state)}
{renderAudioTrackOptions(state)}
</div>
)

Expand Down Expand Up @@ -702,6 +754,10 @@ function renderPlayerControls (state) {
dispatch('toggleSubtitlesMenu')
}
}

function handleAudioTracks (e) {
dispatch('toggleAudioTracksMenu')
}
}

// Renders the loading bar. Shows which parts of the torrent are loaded, which
Expand Down
5 changes: 5 additions & 0 deletions static/main.css
Original file line number Diff line number Diff line change
Expand Up @@ -623,6 +623,11 @@ body.drag .app::after {
margin-top: 6px;
}

.player .controls .icon.multi-audio {
font-size: 26px;
margin-top: 6px;
}

.player .controls .icon.fullscreen {
font-size: 26px;
margin-right: 15px;
Expand Down

0 comments on commit 45920e0

Please sign in to comment.