AbstractGroupState.cs 10 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218
  1. using System.Threading;
  2. using MediaBrowser.Controller.Session;
  3. using MediaBrowser.Model.SyncPlay;
  4. using Microsoft.Extensions.Logging;
  5. namespace MediaBrowser.Controller.SyncPlay
  6. {
  7. /// <summary>
  8. /// Class AbstractGroupState.
  9. /// </summary>
  10. /// <remarks>
  11. /// Class is not thread-safe, external locking is required when accessing methods.
  12. /// </remarks>
  13. public abstract class AbstractGroupState : ISyncPlayState
  14. {
  15. /// <summary>
  16. /// The logger.
  17. /// </summary>
  18. protected readonly ILogger _logger;
  19. /// <summary>
  20. /// Default constructor.
  21. /// </summary>
  22. public AbstractGroupState(ILogger logger)
  23. {
  24. _logger = logger;
  25. }
  26. /// <summary>
  27. /// Sends a group state update to all group.
  28. /// </summary>
  29. /// <param name="context">The context of the state.</param>
  30. /// <param name="reason">The reason of the state change.</param>
  31. /// <param name="session">The session.</param>
  32. /// <param name="cancellationToken">The cancellation token.</param>
  33. protected void SendGroupStateUpdate(ISyncPlayStateContext context, IPlaybackGroupRequest reason, SessionInfo session, CancellationToken cancellationToken)
  34. {
  35. // Notify relevant state change event.
  36. var stateUpdate = new GroupStateUpdate()
  37. {
  38. State = GetGroupState(),
  39. Reason = reason.GetRequestType()
  40. };
  41. var update = context.NewSyncPlayGroupUpdate(GroupUpdateType.StateUpdate, stateUpdate);
  42. context.SendGroupUpdate(session, SyncPlayBroadcastType.AllGroup, update, cancellationToken);
  43. }
  44. /// <inheritdoc />
  45. public abstract GroupState GetGroupState();
  46. /// <inheritdoc />
  47. public abstract void SessionJoined(ISyncPlayStateContext context, GroupState prevState, SessionInfo session, CancellationToken cancellationToken);
  48. /// <inheritdoc />
  49. public abstract void SessionLeaving(ISyncPlayStateContext context, GroupState prevState, SessionInfo session, CancellationToken cancellationToken);
  50. /// <inheritdoc />
  51. public virtual void HandleRequest(ISyncPlayStateContext context, GroupState prevState, IPlaybackGroupRequest request, SessionInfo session, CancellationToken cancellationToken)
  52. {
  53. UnhandledRequest(request);
  54. }
  55. /// <inheritdoc />
  56. public virtual void HandleRequest(ISyncPlayStateContext context, GroupState prevState, PlayGroupRequest request, SessionInfo session, CancellationToken cancellationToken)
  57. {
  58. UnhandledRequest(request);
  59. }
  60. /// <inheritdoc />
  61. public virtual void HandleRequest(ISyncPlayStateContext context, GroupState prevState, SetPlaylistItemGroupRequest request, SessionInfo session, CancellationToken cancellationToken)
  62. {
  63. var waitingState = new WaitingGroupState(_logger);
  64. context.SetState(waitingState);
  65. waitingState.HandleRequest(context, GetGroupState(), request, session, cancellationToken);
  66. }
  67. /// <inheritdoc />
  68. public virtual void HandleRequest(ISyncPlayStateContext context, GroupState prevState, RemoveFromPlaylistGroupRequest request, SessionInfo session, CancellationToken cancellationToken)
  69. {
  70. var playingItemRemoved = context.RemoveFromPlayQueue(request.PlaylistItemIds);
  71. var playQueueUpdate = context.GetPlayQueueUpdate(PlayQueueUpdateReason.RemoveItems);
  72. var update = context.NewSyncPlayGroupUpdate(GroupUpdateType.PlayQueue, playQueueUpdate);
  73. context.SendGroupUpdate(session, SyncPlayBroadcastType.AllGroup, update, cancellationToken);
  74. if (playingItemRemoved)
  75. {
  76. var PlayingItemIndex = context.PlayQueue.PlayingItemIndex;
  77. if (context.PlayQueue.PlayingItemIndex == -1)
  78. {
  79. _logger.LogDebug("HandleRequest: {0} in group {1}, play queue is empty.", request.GetRequestType(), context.GroupId.ToString());
  80. ISyncPlayState idleState = new IdleGroupState(_logger);
  81. context.SetState(idleState);
  82. var stopRequest = new StopGroupRequest();
  83. idleState.HandleRequest(context, GetGroupState(), stopRequest, session, cancellationToken);
  84. }
  85. }
  86. }
  87. /// <inheritdoc />
  88. public virtual void HandleRequest(ISyncPlayStateContext context, GroupState prevState, MovePlaylistItemGroupRequest request, SessionInfo session, CancellationToken cancellationToken)
  89. {
  90. var result = context.MoveItemInPlayQueue(request.PlaylistItemId, request.NewIndex);
  91. if (!result)
  92. {
  93. _logger.LogError("HandleRequest: {0} in group {1}, unable to move item in play queue.", request.GetRequestType(), context.GroupId.ToString());
  94. return;
  95. }
  96. var playQueueUpdate = context.GetPlayQueueUpdate(PlayQueueUpdateReason.MoveItem);
  97. var update = context.NewSyncPlayGroupUpdate(GroupUpdateType.PlayQueue, playQueueUpdate);
  98. context.SendGroupUpdate(session, SyncPlayBroadcastType.AllGroup, update, cancellationToken);
  99. }
  100. /// <inheritdoc />
  101. public virtual void HandleRequest(ISyncPlayStateContext context, GroupState prevState, QueueGroupRequest request, SessionInfo session, CancellationToken cancellationToken)
  102. {
  103. var result = context.AddToPlayQueue(request.ItemIds, request.Mode);
  104. if (!result)
  105. {
  106. _logger.LogError("HandleRequest: {0} in group {1}, unable to add items to play queue.", request.GetRequestType(), context.GroupId.ToString());
  107. return;
  108. }
  109. var reason = request.Mode.Equals("next") ? PlayQueueUpdateReason.QueueNext : PlayQueueUpdateReason.Queue;
  110. var playQueueUpdate = context.GetPlayQueueUpdate(reason);
  111. var update = context.NewSyncPlayGroupUpdate(GroupUpdateType.PlayQueue, playQueueUpdate);
  112. context.SendGroupUpdate(session, SyncPlayBroadcastType.AllGroup, update, cancellationToken);
  113. }
  114. /// <inheritdoc />
  115. public virtual void HandleRequest(ISyncPlayStateContext context, GroupState prevState, UnpauseGroupRequest request, SessionInfo session, CancellationToken cancellationToken)
  116. {
  117. UnhandledRequest(request);
  118. }
  119. /// <inheritdoc />
  120. public virtual void HandleRequest(ISyncPlayStateContext context, GroupState prevState, PauseGroupRequest request, SessionInfo session, CancellationToken cancellationToken)
  121. {
  122. UnhandledRequest(request);
  123. }
  124. /// <inheritdoc />
  125. public virtual void HandleRequest(ISyncPlayStateContext context, GroupState prevState, StopGroupRequest request, SessionInfo session, CancellationToken cancellationToken)
  126. {
  127. UnhandledRequest(request);
  128. }
  129. /// <inheritdoc />
  130. public virtual void HandleRequest(ISyncPlayStateContext context, GroupState prevState, SeekGroupRequest request, SessionInfo session, CancellationToken cancellationToken)
  131. {
  132. UnhandledRequest(request);
  133. }
  134. /// <inheritdoc />
  135. public virtual void HandleRequest(ISyncPlayStateContext context, GroupState prevState, BufferGroupRequest request, SessionInfo session, CancellationToken cancellationToken)
  136. {
  137. UnhandledRequest(request);
  138. }
  139. /// <inheritdoc />
  140. public virtual void HandleRequest(ISyncPlayStateContext context, GroupState prevState, ReadyGroupRequest request, SessionInfo session, CancellationToken cancellationToken)
  141. {
  142. UnhandledRequest(request);
  143. }
  144. /// <inheritdoc />
  145. public virtual void HandleRequest(ISyncPlayStateContext context, GroupState prevState, NextTrackGroupRequest request, SessionInfo session, CancellationToken cancellationToken)
  146. {
  147. UnhandledRequest(request);
  148. }
  149. /// <inheritdoc />
  150. public virtual void HandleRequest(ISyncPlayStateContext context, GroupState prevState, PreviousTrackGroupRequest request, SessionInfo session, CancellationToken cancellationToken)
  151. {
  152. UnhandledRequest(request);
  153. }
  154. /// <inheritdoc />
  155. public virtual void HandleRequest(ISyncPlayStateContext context, GroupState prevState, SetRepeatModeGroupRequest request, SessionInfo session, CancellationToken cancellationToken)
  156. {
  157. context.SetRepeatMode(request.Mode);
  158. var playQueueUpdate = context.GetPlayQueueUpdate(PlayQueueUpdateReason.RepeatMode);
  159. var update = context.NewSyncPlayGroupUpdate(GroupUpdateType.PlayQueue, playQueueUpdate);
  160. context.SendGroupUpdate(session, SyncPlayBroadcastType.AllGroup, update, cancellationToken);
  161. }
  162. /// <inheritdoc />
  163. public virtual void HandleRequest(ISyncPlayStateContext context, GroupState prevState, SetShuffleModeGroupRequest request, SessionInfo session, CancellationToken cancellationToken)
  164. {
  165. context.SetShuffleMode(request.Mode);
  166. var playQueueUpdate = context.GetPlayQueueUpdate(PlayQueueUpdateReason.ShuffleMode);
  167. var update = context.NewSyncPlayGroupUpdate(GroupUpdateType.PlayQueue, playQueueUpdate);
  168. context.SendGroupUpdate(session, SyncPlayBroadcastType.AllGroup, update, cancellationToken);
  169. }
  170. /// <inheritdoc />
  171. public virtual void HandleRequest(ISyncPlayStateContext context, GroupState prevState, PingGroupRequest request, SessionInfo session, CancellationToken cancellationToken)
  172. {
  173. // Collected pings are used to account for network latency when unpausing playback.
  174. context.UpdatePing(session, request.Ping);
  175. }
  176. /// <inheritdoc />
  177. public virtual void HandleRequest(ISyncPlayStateContext context, GroupState prevState, IgnoreWaitGroupRequest request, SessionInfo session, CancellationToken cancellationToken)
  178. {
  179. context.SetIgnoreGroupWait(session, request.IgnoreWait);
  180. }
  181. private void UnhandledRequest(IPlaybackGroupRequest request)
  182. {
  183. _logger.LogWarning("HandleRequest: unhandled {0} request for {1} state.", request.GetRequestType(), GetGroupState());
  184. }
  185. }
  186. }