From 4765fa452caba35793003e48c953ddfddd7a05e0 Mon Sep 17 00:00:00 2001 From: et0h Date: Sat, 17 Aug 2019 16:33:01 +0100 Subject: [PATCH] Seamless advancement and auto-looping for music (mpv) --- syncplay/__init__.py | 2 +- syncplay/client.py | 24 ++++++++++++++++++++---- syncplay/constants.py | 1 + syncplay/players/mpv.py | 4 ++++ 4 files changed, 26 insertions(+), 5 deletions(-) diff --git a/syncplay/__init__.py b/syncplay/__init__.py index 5132d32..d544005 100755 --- a/syncplay/__init__.py +++ b/syncplay/__init__.py @@ -1,5 +1,5 @@ version = '1.6.5' revision = ' development' milestone = 'Yoitsu' -release_number = '81' +release_number = '82' projectURL = 'https://syncplay.pl/' diff --git a/syncplay/client.py b/syncplay/client.py index 8a42bc8..1df4acf 100755 --- a/syncplay/client.py +++ b/syncplay/client.py @@ -199,9 +199,16 @@ class SyncplayClient(object): self.setPosition(-1) self.ui.showDebugMessage("Rewinded after double-check") + def isPlayingMusic(self): + if self.userlist.currentUser.file: + for musicFormat in constants.MUSIC_FORMATS: + if self.userlist.currentUser.file['name'].lower().endswith(musicFormat): + return True + def updatePlayerStatus(self, paused, position): position -= self.getUserOffset() pauseChange, seeked = self._determinePlayerStateChange(paused, position) + positionBeforeSeek = self._playerPosition self._playerPosition = position self._playerPaused = paused currentLength = self.userlist.currentUser.file["duration"] if self.userlist.currentUser.file else 0 @@ -222,7 +229,9 @@ class SyncplayClient(object): if self._lastGlobalUpdate: self._lastPlayerUpdate = time.time() - if (pauseChange or seeked) and self._protocol: + if seeked and not pauseChange and self.isPlayingMusic() and abs(positionBeforeSeek - currentLength) < constants.PLAYLIST_LOAD_NEXT_FILE_TIME_FROM_END_THRESHOLD and self.playlist.notJustChangedPlaylist(): + self.playlist.loadNextFileInPlaylist() + elif (pauseChange or seeked) and self._protocol: if seeked: self.playerPositionBeforeLastSeek = self.getGlobalPosition() self._protocol.sendState(self.getPlayerPosition(), self.getPlayerPaused(), seeked, None, True) @@ -230,7 +239,10 @@ class SyncplayClient(object): def prepareToAdvancePlaylist(self): if self.playlist.canSwitchToNextPlaylistIndex(): self.ui.showDebugMessage("Preparing to advance playlist...") - self._protocol.sendState(0, True, True, None, True) + if self.isPlayingMusic(): + self._protocol.sendState(0, False, True, None, True) + else: + self._protocol.sendState(0, True, True, None, True) else: self.ui.showDebugMessage("Not preparing to advance playlist because the next file cannot be switched to") @@ -527,10 +539,10 @@ class SyncplayClient(object): self.playlist.changeToPlaylistIndex(*args, **kwargs) def loopSingleFiles(self): - return self._config["loopSingleFiles"] + return self._config["loopSingleFiles"] or self.isPlayingMusic() def isPlaylistLoopingEnabled(self): - return self._config["loopAtEndOfPlaylist"] + return self._config["loopAtEndOfPlaylist"] or self.isPlayingMusic() def __executePrivacySettings(self, filename, size): if self._config['filenamePrivacyMode'] == PRIVACY_SENDHASHED_MODE: @@ -830,12 +842,16 @@ class SyncplayClient(object): self.autoplayCheck() def autoplayCheck(self): + if self.isPlayingMusic(): + return True if self.autoplayConditionsMet(): self.startAutoplayCountdown() else: self.stopAutoplayCountdown() def instaplayConditionsMet(self): + if self.isPlayingMusic(): + return True if not self.userlist.currentUser.canControl(): return False diff --git a/syncplay/constants.py b/syncplay/constants.py index 7f0fcf5..7cde152 100755 --- a/syncplay/constants.py +++ b/syncplay/constants.py @@ -30,6 +30,7 @@ UI_TIME_FORMAT = "[%X] " CONFIG_NAMES = [".syncplay", "syncplay.ini"] # Syncplay searches first to last DEFAULT_CONFIG_NAME = "syncplay.ini" RECENT_CLIENT_THRESHOLD = "1.6.4" # This and higher considered 'recent' clients (no warnings) +MUSIC_FORMATS = [".mp3", ".m4a", ".m4p", ".wav", ".aiff", ".r", ".ogg", ".flac"] # ALL LOWER CASE! WARN_OLD_CLIENTS = True # Use MOTD to inform old clients to upgrade LIST_RELATIVE_CONFIGS = True # Print list of relative configs loaded SHOW_CONTACT_INFO = True # Displays dev contact details below list in GUI diff --git a/syncplay/players/mpv.py b/syncplay/players/mpv.py index c27a684..68beb0d 100755 --- a/syncplay/players/mpv.py +++ b/syncplay/players/mpv.py @@ -197,6 +197,10 @@ class NewMpvPlayer(OldMpvPlayer): return self._position def _storePosition(self, value): + if self._client.isPlayingMusic() and self._paused == False and self._position == value and abs(self._position-self._position) < 0.5: + self._client.ui.showDebugMessage("EOF DETECTED!") + self._position = 0 + self.setPosition(0) self.lastMPVPositionUpdate = time.time() if self._recentlyReset(): self._client.ui.showDebugMessage("Recently reset, so storing position as 0")