diff --git a/Emby.Server.Implementations/LiveTv/EmbyTV/EmbyTV.cs b/Emby.Server.Implementations/LiveTv/EmbyTV/EmbyTV.cs
index 1fc3dcd72..82f32efa2 100644
--- a/Emby.Server.Implementations/LiveTv/EmbyTV/EmbyTV.cs
+++ b/Emby.Server.Implementations/LiveTv/EmbyTV/EmbyTV.cs
@@ -635,6 +635,7 @@ namespace Emby.Server.Implementations.LiveTv.EmbyTV
existingTimer.Status == RecordingStatus.Completed)
{
existingTimer.Status = RecordingStatus.New;
+ existingTimer.IsManual = true;
_timerProvider.Update(existingTimer);
return Task.FromResult(existingTimer.Id);
}
@@ -663,6 +664,7 @@ namespace Emby.Server.Implementations.LiveTv.EmbyTV
RecordingHelper.CopyProgramInfoToTimerInfo(programInfo, timer);
}
+ timer.IsManual = true;
_timerProvider.Add(timer);
return Task.FromResult(timer.Id);
}
@@ -758,6 +760,8 @@ namespace Emby.Server.Implementations.LiveTv.EmbyTV
existingTimer.PostPaddingSeconds = updatedTimer.PostPaddingSeconds;
existingTimer.IsPostPaddingRequired = updatedTimer.IsPostPaddingRequired;
existingTimer.IsPrePaddingRequired = updatedTimer.IsPrePaddingRequired;
+
+ _timerProvider.Update(existingTimer);
}
return Task.FromResult(true);
@@ -2203,6 +2207,11 @@ namespace Emby.Server.Implementations.LiveTv.EmbyTV
private bool ShouldCancelTimerForSeriesTimer(SeriesTimerInfo seriesTimer, TimerInfo timer)
{
+ if (timer.IsManual)
+ {
+ return false;
+ }
+
if (!seriesTimer.RecordAnyTime)
{
if (Math.Abs(seriesTimer.StartDate.TimeOfDay.Ticks - timer.StartDate.TimeOfDay.Ticks) >= TimeSpan.FromMinutes(5).Ticks)
diff --git a/Emby.Server.Implementations/Session/SessionManager.cs b/Emby.Server.Implementations/Session/SessionManager.cs
index a20fb67b2..8051b7848 100644
--- a/Emby.Server.Implementations/Session/SessionManager.cs
+++ b/Emby.Server.Implementations/Session/SessionManager.cs
@@ -954,8 +954,11 @@ namespace Emby.Server.Implementations.Session
{
var session = GetSessionToRemoteControl(sessionId);
- var controllingSession = GetSession(controllingSessionId);
- AssertCanControl(session, controllingSession);
+ if (!string.IsNullOrWhiteSpace(controllingSessionId))
+ {
+ var controllingSession = GetSession(controllingSessionId);
+ AssertCanControl(session, controllingSession);
+ }
return session.SessionController.SendGeneralCommand(command, cancellationToken);
}
@@ -1042,11 +1045,14 @@ namespace Emby.Server.Implementations.Session
}
}
- var controllingSession = GetSession(controllingSessionId);
- AssertCanControl(session, controllingSession);
- if (controllingSession.UserId.HasValue)
+ if (!string.IsNullOrWhiteSpace(controllingSessionId))
{
- command.ControllingUserId = controllingSession.UserId.Value.ToString("N");
+ var controllingSession = GetSession(controllingSessionId);
+ AssertCanControl(session, controllingSession);
+ if (controllingSession.UserId.HasValue)
+ {
+ command.ControllingUserId = controllingSession.UserId.Value.ToString("N");
+ }
}
await session.SessionController.SendPlayCommand(command, cancellationToken).ConfigureAwait(false);
@@ -1136,11 +1142,14 @@ namespace Emby.Server.Implementations.Session
{
var session = GetSessionToRemoteControl(sessionId);
- var controllingSession = GetSession(controllingSessionId);
- AssertCanControl(session, controllingSession);
- if (controllingSession.UserId.HasValue)
+ if (!string.IsNullOrWhiteSpace(controllingSessionId))
{
- command.ControllingUserId = controllingSession.UserId.Value.ToString("N");
+ var controllingSession = GetSession(controllingSessionId);
+ AssertCanControl(session, controllingSession);
+ if (controllingSession.UserId.HasValue)
+ {
+ command.ControllingUserId = controllingSession.UserId.Value.ToString("N");
+ }
}
return session.SessionController.SendPlaystateCommand(command, cancellationToken);
diff --git a/MediaBrowser.Api/Playback/MediaInfoService.cs b/MediaBrowser.Api/Playback/MediaInfoService.cs
index 80885271c..ed8449b83 100644
--- a/MediaBrowser.Api/Playback/MediaInfoService.cs
+++ b/MediaBrowser.Api/Playback/MediaInfoService.cs
@@ -127,7 +127,7 @@ namespace MediaBrowser.Api.Playback
SetDeviceSpecificData(item, result.MediaSource, profile, authInfo, request.MaxStreamingBitrate,
request.StartTimeTicks ?? 0, result.MediaSource.Id, request.AudioStreamIndex,
- request.SubtitleStreamIndex, request.MaxAudioChannels, request.PlaySessionId, request.UserId);
+ request.SubtitleStreamIndex, request.MaxAudioChannels, request.PlaySessionId, request.UserId, true, true, true);
}
else
{
@@ -169,7 +169,7 @@ namespace MediaBrowser.Api.Playback
{
var mediaSourceId = request.MediaSourceId;
- SetDeviceSpecificData(request.Id, info, profile, authInfo, request.MaxStreamingBitrate ?? profile.MaxStreamingBitrate, request.StartTimeTicks ?? 0, mediaSourceId, request.AudioStreamIndex, request.SubtitleStreamIndex, request.MaxAudioChannels, request.UserId);
+ SetDeviceSpecificData(request.Id, info, profile, authInfo, request.MaxStreamingBitrate ?? profile.MaxStreamingBitrate, request.StartTimeTicks ?? 0, mediaSourceId, request.AudioStreamIndex, request.SubtitleStreamIndex, request.MaxAudioChannels, request.UserId, request.EnableDirectPlay, request.EnableDirectStream, request.EnableTranscoding);
}
return info;
@@ -251,13 +251,16 @@ namespace MediaBrowser.Api.Playback
int? audioStreamIndex,
int? subtitleStreamIndex,
int? maxAudioChannels,
- string userId)
+ string userId,
+ bool enableDirectPlay,
+ bool enableDirectStream,
+ bool enableTranscoding)
{
var item = _libraryManager.GetItemById(itemId);
foreach (var mediaSource in result.MediaSources)
{
- SetDeviceSpecificData(item, mediaSource, profile, auth, maxBitrate, startTimeTicks, mediaSourceId, audioStreamIndex, subtitleStreamIndex, maxAudioChannels, result.PlaySessionId, userId);
+ SetDeviceSpecificData(item, mediaSource, profile, auth, maxBitrate, startTimeTicks, mediaSourceId, audioStreamIndex, subtitleStreamIndex, maxAudioChannels, result.PlaySessionId, userId, enableDirectPlay, enableDirectStream, enableTranscoding);
}
SortMediaSources(result, maxBitrate);
@@ -274,7 +277,10 @@ namespace MediaBrowser.Api.Playback
int? subtitleStreamIndex,
int? maxAudioChannels,
string playSessionId,
- string userId)
+ string userId,
+ bool enableDirectPlay,
+ bool enableDirectStream,
+ bool enableTranscoding)
{
var streamBuilder = new StreamBuilder(_mediaEncoder, Logger);
@@ -297,6 +303,19 @@ namespace MediaBrowser.Api.Playback
var user = _userManager.GetUserById(userId);
+ if (!enableDirectPlay)
+ {
+ mediaSource.SupportsDirectPlay = false;
+ }
+ if (!enableDirectStream)
+ {
+ mediaSource.SupportsDirectStream = false;
+ }
+ if (!enableTranscoding)
+ {
+ mediaSource.SupportsTranscoding = false;
+ }
+
if (mediaSource.SupportsDirectPlay)
{
var supportsDirectStream = mediaSource.SupportsDirectStream;
diff --git a/MediaBrowser.Controller/LiveTv/TimerInfo.cs b/MediaBrowser.Controller/LiveTv/TimerInfo.cs
index ea12db7f9..0b94c85fa 100644
--- a/MediaBrowser.Controller/LiveTv/TimerInfo.cs
+++ b/MediaBrowser.Controller/LiveTv/TimerInfo.cs
@@ -88,6 +88,8 @@ namespace MediaBrowser.Controller.LiveTv
/// true if this instance is post padding required; otherwise, false.
public bool IsPostPaddingRequired { get; set; }
+ public bool IsManual { get; set; }
+
///
/// Gets or sets the priority.
///
diff --git a/MediaBrowser.Model/MediaInfo/PlaybackInfoRequest.cs b/MediaBrowser.Model/MediaInfo/PlaybackInfoRequest.cs
index fc4714be3..57a2254b0 100644
--- a/MediaBrowser.Model/MediaInfo/PlaybackInfoRequest.cs
+++ b/MediaBrowser.Model/MediaInfo/PlaybackInfoRequest.cs
@@ -23,5 +23,16 @@ namespace MediaBrowser.Model.MediaInfo
public string LiveStreamId { get; set; }
public DeviceProfile DeviceProfile { get; set; }
+
+ public bool EnableDirectPlay { get; set; }
+ public bool EnableDirectStream { get; set; }
+ public bool EnableTranscoding { get; set; }
+
+ public PlaybackInfoRequest()
+ {
+ EnableDirectPlay = true;
+ EnableDirectStream = true;
+ EnableTranscoding = true;
+ }
}
}
diff --git a/SharedVersion.cs b/SharedVersion.cs
index ef83fd78c..7d9fa0d70 100644
--- a/SharedVersion.cs
+++ b/SharedVersion.cs
@@ -1,3 +1,3 @@
using System.Reflection;
-[assembly: AssemblyVersion("3.2.1.110")]
+[assembly: AssemblyVersion("3.2.1.111")]