1
0
Fork 0
mirror of https://github.com/jellyfin/jellyfin-web synced 2025-03-30 19:56:21 +00:00

fixes #1003 - [Transcoding] VP8 + OGG to VP8 + OGG

This commit is contained in:
Luke Pulverenti 2015-03-26 14:23:46 -04:00
parent 1fc390dc50
commit 640b6df867
2 changed files with 192 additions and 180 deletions

View file

@ -933,69 +933,18 @@
self.playVideo = function (deviceProfile, playbackInfo, item, mediaSource, startPosition) { self.playVideo = function (deviceProfile, playbackInfo, item, mediaSource, startPosition) {
var videoUrl; var streamInfo = self.createStreamInfo('video', item, mediaSource, startPosition);
var contentType;
var videoUrl = streamInfo.url;
var contentType = streamInfo.contentType;
var startPositionInSeekParam = streamInfo.startPositionInSeekParam;
self.startTimeTicksOffset = streamInfo.startTimeTicksOffset;
var mediaStreams = mediaSource.MediaStreams || []; var mediaStreams = mediaSource.MediaStreams || [];
var subtitleStreams = mediaStreams.filter(function (s) { var subtitleStreams = mediaStreams.filter(function (s) {
return s.Type == 'Subtitle'; return s.Type == 'Subtitle';
}); });
if (mediaSource.enableDirectPlay) {
videoUrl = mediaSource.Path;
self.startTimeTicksOffset = 0;
contentType = 'video/' + mediaSource.Container;
} else {
var selectedSubtitleStream = subtitleStreams.filter(function (s) {
return s.Index == mediaSource.DefaultSubtitleStreamIndex;
})[0];
var transcodingParams = {
audioChannels: 2,
StartTimeTicks: startPosition,
AudioStreamIndex: mediaSource.DefaultAudioStreamIndex,
deviceId: ApiClient.deviceId(),
mediaSourceId: mediaSource.Id,
api_key: ApiClient.accessToken(),
StreamId: playbackInfo.StreamId,
ClientTime: new Date().getTime()
};
if (selectedSubtitleStream && (!self.supportsSubtitleStreamExternally(selectedSubtitleStream) || !self.supportsTextTracks())) {
transcodingParams.SubtitleStreamIndex = mediaSource.DefaultSubtitleStreamIndex;
}
self.startTimeTicksOffset = mediaSource.SupportsDirectStream ? 0 : startPosition || 0;
var startPositionInSeekParam = startPosition ? (startPosition / 10000000) : 0;
var seekParam = startPositionInSeekParam ? '#t=' + startPositionInSeekParam : '';
if (mediaSource.SupportsDirectStream) {
videoUrl = ApiClient.getUrl('Videos/' + item.Id + '/stream.' + mediaSource.Container, {
Static: true,
mediaSourceId: mediaSource.Id,
api_key: ApiClient.accessToken()
});
videoUrl += seekParam;
contentType = 'video/' + mediaSource.Container;
} else {
videoUrl = ApiClient.getUrl(mediaSource.TranscodingUrl);
if (mediaSource.TranscodingSubProtocol == 'hls') {
videoUrl += seekParam;
contentType = 'application/x-mpegURL';
}
else {
contentType = 'video/' + mediaSource.TranscodingContainer;
}
}
}
//======================================================================================> //======================================================================================>
// Create video player // Create video player

View file

@ -378,71 +378,73 @@
if (canClientSeek && params == null) { if (canClientSeek && params == null) {
element.currentTime = ticks / (1000 * 10000); element.currentTime = ticks / (1000 * 10000);
return;
} else { }
params = params || {}; params = params || {};
var currentSrc = element.currentSrc; var currentSrc = element.currentSrc;
var transcodingExtension;
var isStatic;
var currentStreamId = getParameterByName('StreamId', currentSrc); var currentStreamId = getParameterByName('StreamId', currentSrc);
if (self.currentItem.MediaType == "Video") { //if (self.currentItem.MediaType == "Video") {
transcodingExtension = self.getVideoTranscodingExtension(currentSrc); // transcodingExtension = self.getVideoTranscodingExtension(currentSrc);
if (params.AudioStreamIndex != null) { // if (params.AudioStreamIndex != null) {
currentSrc = replaceQueryString(currentSrc, 'AudioStreamIndex', params.AudioStreamIndex); // currentSrc = replaceQueryString(currentSrc, 'AudioStreamIndex', params.AudioStreamIndex);
} // }
if (params.SubtitleStreamIndex != null) { // if (params.SubtitleStreamIndex != null) {
currentSrc = replaceQueryString(currentSrc, 'SubtitleStreamIndex', (params.SubtitleStreamIndex == -1 ? '' : params.SubtitleStreamIndex)); // currentSrc = replaceQueryString(currentSrc, 'SubtitleStreamIndex', (params.SubtitleStreamIndex == -1 ? '' : params.SubtitleStreamIndex));
} // }
var audioStreamIndex = params.AudioStreamIndex == null ? getParameterByName('AudioStreamIndex', currentSrc) : params.AudioStreamIndex; // var audioStreamIndex = params.AudioStreamIndex == null ? getParameterByName('AudioStreamIndex', currentSrc) : params.AudioStreamIndex;
if (typeof (audioStreamIndex) == 'string') { // if (typeof (audioStreamIndex) == 'string') {
audioStreamIndex = parseInt(audioStreamIndex); // audioStreamIndex = parseInt(audioStreamIndex);
} // }
var subtitleStreamIndex = self.currentSubtitleStreamIndex; // var subtitleStreamIndex = self.currentSubtitleStreamIndex;
var videoBitrate = parseInt(getParameterByName('VideoBitrate', currentSrc) || '0'); // var videoBitrate = parseInt(getParameterByName('VideoBitrate', currentSrc) || '0');
var audioBitrate = parseInt(getParameterByName('AudioBitrate', currentSrc) || '0'); // var audioBitrate = parseInt(getParameterByName('AudioBitrate', currentSrc) || '0');
var bitrate = params.Bitrate || (videoBitrate + audioBitrate); // var bitrate = params.Bitrate || (videoBitrate + audioBitrate);
var finalParams = self.getFinalVideoParams(self.currentMediaSource, bitrate, audioStreamIndex, subtitleStreamIndex, transcodingExtension); // var finalParams = self.getFinalVideoParams(self.currentMediaSource, bitrate, audioStreamIndex, subtitleStreamIndex, transcodingExtension);
currentSrc = replaceQueryString(currentSrc, 'VideoBitrate', finalParams.videoBitrate); // currentSrc = replaceQueryString(currentSrc, 'VideoBitrate', finalParams.videoBitrate);
currentSrc = replaceQueryString(currentSrc, 'VideoCodec', finalParams.videoCodec); // currentSrc = replaceQueryString(currentSrc, 'VideoCodec', finalParams.videoCodec);
currentSrc = replaceQueryString(currentSrc, 'profile', finalParams.profile || ''); // currentSrc = replaceQueryString(currentSrc, 'profile', finalParams.profile || '');
currentSrc = replaceQueryString(currentSrc, 'level', finalParams.level || ''); // currentSrc = replaceQueryString(currentSrc, 'level', finalParams.level || '');
// if (finalParams.isStatic) {
// currentSrc = currentSrc.replace('.webm', '.mp4').replace('.m3u8', '.mp4');
// currentSrc = replaceQueryString(currentSrc, 'ClientTime', '');
// } else {
// currentSrc = currentSrc.replace('.mp4', transcodingExtension).replace('.m4v', transcodingExtension).replace('.mkv', transcodingExtension).replace('.webm', transcodingExtension);
// currentSrc = replaceQueryString(currentSrc, 'ClientTime', new Date().getTime());
// }
// currentSrc = replaceQueryString(currentSrc, 'AudioBitrate', finalParams.audioBitrate);
// currentSrc = replaceQueryString(currentSrc, 'Static', finalParams.isStatic);
// currentSrc = replaceQueryString(currentSrc, 'AudioCodec', finalParams.audioCodec);
// isStatic = finalParams.isStatic;
//}
if (params.AudioStreamIndex == null && params.SubtitleStreamIndex == null && params.Bitrate == null) {
var transcodingProfile = self.getDeviceProfile().TranscodingProfiles.filter(function (t) {
return t.Type == self.currentItem.MediaType;
})[0];
if (finalParams.isStatic) {
currentSrc = currentSrc.replace('.webm', '.mp4').replace('.m3u8', '.mp4');
currentSrc = replaceQueryString(currentSrc, 'ClientTime', '');
} else { } else {
currentSrc = currentSrc.replace('.mp4', transcodingExtension).replace('.m4v', transcodingExtension).replace('.mkv', transcodingExtension).replace('.webm', transcodingExtension);
currentSrc = replaceQueryString(currentSrc, 'ClientTime', new Date().getTime());
}
currentSrc = replaceQueryString(currentSrc, 'AudioBitrate', finalParams.audioBitrate); currentSrc = replaceQueryString(currentSrc, 'starttimeticks', ticks || 0);
currentSrc = replaceQueryString(currentSrc, 'Static', finalParams.isStatic); changeStreamToUrl(currentStreamId, currentSrc, ticks);
currentSrc = replaceQueryString(currentSrc, 'AudioCodec', finalParams.audioCodec);
isStatic = finalParams.isStatic;
} else {
transcodingExtension = '.mp3';
} }
};
var isSeekableMedia = self.currentMediaSource.RunTimeTicks; function changeStreamToUrl(currentStreamId, url, newPositionTicks) {
var isClientSeekable = isStatic || (isSeekableMedia && transcodingExtension == '.m3u8');
if (isClientSeekable || !ticks || !isSeekableMedia) {
currentSrc = replaceQueryString(currentSrc, 'starttimeticks', '');
}
else {
currentSrc = replaceQueryString(currentSrc, 'starttimeticks', ticks);
}
clearProgressInterval(); clearProgressInterval();
@ -460,19 +462,18 @@
if (self.currentItem.MediaType == "Video") { if (self.currentItem.MediaType == "Video") {
ApiClient.stopActiveEncodings(currentStreamId).done(function () { ApiClient.stopActiveEncodings(currentStreamId).done(function () {
self.startTimeTicksOffset = ticks; self.startTimeTicksOffset = newPositionTicks;
element.src = currentSrc; element.src = url;
}); });
self.updateTextStreamUrls(ticks || 0); self.updateTextStreamUrls(newPositionTicks || 0);
} else { } else {
self.startTimeTicksOffset = ticks; self.startTimeTicksOffset = newPositionTicks;
element.src = currentSrc; element.src = url;
element.play(); element.play();
} }
} }
};
self.setCurrentTime = function (ticks, positionSlider, currentTimeElement) { self.setCurrentTime = function (ticks, positionSlider, currentTimeElement) {
@ -791,6 +792,106 @@
})[0]; })[0];
} }
function getPlaybackInfo(itemId, deviceProfile, startPosition) {
return ApiClient.ajax({
url: ApiClient.getUrl('Items/' + itemId + '/PlaybackInfo', {
UserId: Dashboard.getCurrentUserId(),
StartPositionTicks: startPosition || 0
}),
type: 'POST',
data: JSON.stringify({
DeviceProfile: deviceProfile
}),
contentType: "application/json",
dataType: "json"
});
}
self.createStreamInfo = function (type, item, mediaSource, startPosition) {
var mediaUrl;
var contentType;
var startTimeTicksOffset = 0;
var startPositionInSeekParam = startPosition ? (startPosition / 10000000) : 0;
var seekParam = startPositionInSeekParam ? '#t=' + startPositionInSeekParam : '';
if (type == 'video') {
contentType = 'video/' + mediaSource.Container;
if (mediaSource.enableDirectPlay) {
mediaUrl = mediaSource.Path;
} else {
if (mediaSource.SupportsDirectStream) {
mediaUrl = ApiClient.getUrl('Videos/' + item.Id + '/stream.' + mediaSource.Container, {
Static: true,
mediaSourceId: mediaSource.Id,
api_key: ApiClient.accessToken()
});
mediaUrl += seekParam;
} else {
startTimeTicksOffset = startPosition || 0;
mediaUrl = ApiClient.getUrl(mediaSource.TranscodingUrl);
if (mediaSource.TranscodingSubProtocol == 'hls') {
mediaUrl += seekParam;
contentType = 'application/x-mpegURL';
} else {
contentType = 'video/' + mediaSource.TranscodingContainer;
}
}
}
} else {
contentType = 'audio/' + mediaSource.Container;
if (mediaSource.enableDirectPlay) {
mediaUrl = mediaSource.Path;
} else {
var isDirectStream = mediaSource.SupportsDirectStream;
if (isDirectStream) {
var outputContainer = (mediaSource.Container || '').toLowerCase();
mediaUrl = ApiClient.getUrl('Audio/' + item.Id + '/stream.' + outputContainer, {
mediaSourceId: mediaSource.Id,
deviceId: ApiClient.deviceId(),
api_key: ApiClient.accessToken()
});
mediaUrl += "&static=true" + seekParam;
} else {
contentType = 'audio/' + mediaSource.TranscodingContainer;
mediaUrl = ApiClient.getUrl(mediaSource.TranscodingUrl);
}
startTimeTicksOffset = startPosition || 0;
}
}
return {
url: mediaUrl,
contentType: contentType,
startTimeTicksOffset: startTimeTicksOffset,
startPositionInSeekParam: startPositionInSeekParam
};
};
self.playInternal = function (item, startPosition, callback) { self.playInternal = function (item, startPosition, callback) {
if (item == null) { if (item == null) {
@ -813,20 +914,7 @@
var mediaSource; var mediaSource;
var deviceProfile = self.getDeviceProfile(); var deviceProfile = self.getDeviceProfile();
ApiClient.ajax({ getPlaybackInfo(item.Id, deviceProfile, startPosition).done(function (result) {
url: ApiClient.getUrl('Items/' + item.Id + '/PlaybackInfo', {
userId: Dashboard.getCurrentUserId()
}),
type: 'POST',
data: JSON.stringify({
DeviceProfile: deviceProfile
}),
contentType: "application/json",
dataType: "json"
}).done(function (result) {
if (validatePlaybackInfoResult(result)) { if (validatePlaybackInfoResult(result)) {
@ -846,7 +934,7 @@
} else if (item.MediaType === "Audio") { } else if (item.MediaType === "Audio") {
self.currentMediaElement = playAudio(result, item, self.currentMediaSource, startPosition); self.currentMediaElement = playAudio(item, self.currentMediaSource, startPosition);
self.currentDurationTicks = self.currentMediaSource.RunTimeTicks; self.currentDurationTicks = self.currentMediaSource.RunTimeTicks;
} }
@ -1607,36 +1695,11 @@
return $('.mediaPlayerAudio'); return $('.mediaPlayerAudio');
} }
function playAudio(playbackInfo, item, mediaSource, startPositionTicks) { function playAudio(item, mediaSource, startPositionTicks) {
var audioUrl; var streamInfo = self.createStreamInfo('audio', item, mediaSource, startPositionTicks);
if (mediaSource.enableDirectPlay) { var audioUrl = streamInfo.url;
self.startTimeTicksOffset = streamInfo.startTimeTicksOffset;
audioUrl = mediaSource.Path;
self.startTimeTicksOffset = 0;
} else {
var isDirectStream = mediaSource.SupportsDirectStream;
startPositionTicks = startPositionTicks || 0;
if (isDirectStream) {
var outputContainer = (mediaSource.Container || '').toLowerCase();
var seekParam = startPositionTicks ? '#t=' + (startPositionTicks / 10000000) : '';
audioUrl = ApiClient.getUrl('Audio/' + item.Id + '/stream.' + outputContainer, {
mediaSourceId: mediaSource.Id,
deviceId: ApiClient.deviceId(),
api_key: ApiClient.accessToken()
});
audioUrl += "&static=true" + seekParam;
} else {
audioUrl = ApiClient.getUrl(mediaSource.TranscodingUrl);
}
self.startTimeTicksOffset = isDirectStream ? 0 : startPositionTicks;
}
var initialVolume = self.getSavedVolume(); var initialVolume = self.getSavedVolume();