diff --git a/buildPy2exe.py b/buildPy2exe.py index 207c875..0309223b 100755 --- a/buildPy2exe.py +++ b/buildPy2exe.py @@ -651,6 +651,7 @@ guiIcons = ['resources/accept.png', 'resources/arrow_undo.png', 'resources/clock 'resources/folder_explore.png', 'resources/help.png', 'resources/table_refresh.png', 'resources/timeline_marker.png','resources/control_play_blue.png', 'resources/mpc-hc.png','resources/mpc-hc64.png','resources/mplayer.png', + 'resources/mpc-be.png', 'resources/mpv.png','resources/vlc.png', 'resources/house.png', 'resources/film_link.png', 'resources/eye.png', 'resources/comments.png', 'resources/cog_delete.png', 'resources/chevrons_right.png', 'resources/user_key.png', 'resources/lock.png', 'resources/key_go.png', 'resources/page_white_key.png', diff --git a/resources/mpc-be.png b/resources/mpc-be.png new file mode 100644 index 0000000..984887e Binary files /dev/null and b/resources/mpc-be.png differ diff --git a/syncplay/__init__.py b/syncplay/__init__.py index f3e9aa8..2cf5466 100644 --- a/syncplay/__init__.py +++ b/syncplay/__init__.py @@ -1,4 +1,4 @@ -version = '1.5.0' +version = '1.5.1' milestone = 'Yoitsu' -release_number = '49' +release_number = '51' projectURL = 'http://syncplay.pl/' diff --git a/syncplay/constants.py b/syncplay/constants.py index 04228c8..b36de1a 100644 --- a/syncplay/constants.py +++ b/syncplay/constants.py @@ -9,7 +9,7 @@ UI_TIME_FORMAT = "[%X] " CONFIG_NAMES = [".syncplay", "syncplay.ini"] #Syncplay searches first to last DEFAULT_CONFIG_NAME_WINDOWS = "syncplay.ini" DEFAULT_CONFIG_NAME_LINUX = ".syncplay" -RECENT_CLIENT_THRESHOLD = "1.5.0" #This and higher considered 'recent' clients (no warnings) +RECENT_CLIENT_THRESHOLD = "1.5.1" #This and higher considered 'recent' clients (no warnings) 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 @@ -89,6 +89,7 @@ COMMANDS_CREATE = ['c','create'] COMMANDS_AUTH = ['a','auth'] COMMANDS_TOGGLE = ['t','toggle'] MPC_MIN_VER = "1.6.4" +MPC_BE_MIN_VER = "1.5.2.3123" VLC_MIN_VERSION = "2.2.1" VLC_INTERFACE_MIN_VERSION = "0.3.4" VLC_LATENCY_ERROR_THRESHOLD = 2.0 @@ -111,6 +112,12 @@ MPC_PATHS = [ r"c:\program files\combined community codec pack\mpc\mpc-hc.exe", r"c:\program files\mpc homecinema (x64)\mpc-hc64.exe", ] +MPC_BE_PATHS = [ + r"c:\Program Files\MPC-BE x64\mpc-be64.exe", + r"c:\Program Files\MPC-BE x64\mpc-be.exe", + r"c:\Program Files\MPC-BE\mpc-be64.exe", + r"c:\Program Files\MPC-BE\mpc-be.exe" +] MPLAYER_PATHS = ["mplayer2", "mplayer"] MPV_PATHS = ["mpv", "/opt/mpv/mpv", r"c:\program files\mpv\mpv.exe", r"c:\program files\mpv-player\mpv.exe", r"c:\program Files (x86)\mpv\mpv.exe", r"c:\program Files (x86)\mpv-player\mpv.exe", @@ -130,6 +137,7 @@ MPLAYER_ICONPATH = "mplayer.png" MPV_ICONPATH = "mpv.png" MPC_ICONPATH = "mpc-hc.png" MPC64_ICONPATH = "mpc-hc64.png" +MPC_BE_ICONPATH = "mpc-be.png" MPV_ERROR_MESSAGES_TO_REPEAT = ['[ytdl_hook] Your version of youtube-dl is too old', '[ytdl_hook] youtube-dl failed', 'Failed to recognize file format.'] @@ -187,8 +195,8 @@ MPV_SYNCPLAYINTF_CONSTANTS_TO_SEND = ["MaxChatMessageLength={}".format(MAX_CHAT_ MPV_SYNCPLAYINTF_LANGUAGE_TO_SEND = ["mpv-key-hint", "alphakey-mode-warning-first-line", "alphakey-mode-warning-second-line"] VLC_SLAVE_ARGS = ['--extraintf=luaintf', '--lua-intf=syncplay', '--no-quiet', '--no-input-fast-seek', '--play-and-pause', '--start-time=0'] -VLC_SLAVE_OSX_ARGS = ['--verbose=2', '--no-file-logging'] -VLC_SLAVE_NONOSX_ARGS = ['--no-one-instance', '--no-one-instance-when-started-from-file'] +VLC_SLAVE_MACOS_ARGS = ['--verbose=2', '--no-file-logging'] +VLC_SLAVE_NONMACOS_ARGS = ['--no-one-instance', '--no-one-instance-when-started-from-file'] MPV_SUPERSEDE_IF_DUPLICATE_COMMANDS = ["no-osd set time-pos ", "loadfile "] MPV_REMOVE_BOTH_IF_DUPLICATE_COMMANDS = ["cycle pause"] MPLAYER_ANSWER_REGEX = "^ANS_([a-zA-Z_-]+)=(.+)$|^(Exiting)\.\.\. \((.+)\)$" @@ -244,4 +252,10 @@ SYNCPLAY_PUBLIC_SERVER_LIST_URL = u"http://syncplay.pl/listpublicservers?{}" # P DEFAULT_TRUSTED_DOMAINS = [u"youtube.com",u"youtu.be"] TRUSTABLE_WEB_PROTOCOLS = [u"http://www.",u"https://www.",u"http://",u"https://"] -PRIVATE_FILE_FIELDS = ["path"] \ No newline at end of file +PRIVATE_FILE_FIELDS = ["path"] + +OS_WINDOWS = "win" +OS_LINUX = "linux" +OS_MACOS = "darwin" +OS_BSD = "freebsd" +OS_DRAGONFLY = "dragonfly" diff --git a/syncplay/messages_de.py b/syncplay/messages_de.py index e468e29..0c740d3 100644 --- a/syncplay/messages_de.py +++ b/syncplay/messages_de.py @@ -108,9 +108,10 @@ de = { "server-timeout-error" : u"Timeout: Verbindung zum Server fehlgeschlagen", "mpc-slave-error" : u"Kann MPC nicht im Slave-Modus starten!", "mpc-version-insufficient-error" : u"MPC-Version nicht ausreichend, bitte nutze `mpc-hc` >= `{}`", + "mpc-be-version-insufficient-error" : u"MPC-Version nicht ausreichend, bitte nutze `mpc-be` >= `{}`", "mpv-version-error" : u"Syncplay ist nicht kompatibel mit dieser Version von mpv. Bitte benutze eine andere Version (z.B. Git HEAD).", "player-file-open-error" : u"Fehler beim Öffnen der Datei durch den Player", - "player-path-error" : u"Ungültiger Player-Pfad", + "player-path-error" : u"Ungültiger Player-Pfad. Supported players are: mpv, VLC, MPC-HC, MPC-BE and mplayer2", # To do: Translate end "hostname-empty-error" : u"Hostname darf nicht leer sein", "empty-error" : u"{} darf nicht leer sein", # Configuration "media-player-error": u"Player-Fehler: \"{}\"", # Error line @@ -120,7 +121,7 @@ de = { "unable-to-start-client-error" : u"Client kann nicht gestartet werden", - "player-path-config-error": u"Player-Pfad ist nicht ordnungsgemäß gesetzt.", + "player-path-config-error": u"Player-Pfad ist nicht ordnungsgemäß gesetzt. Supported players are: mpv, VLC, MPC-HC, MPC-BE and mplayer2.", # To do: Translate end "no-file-path-config-error": u"Es muss eine Datei ausgewählt werden, bevor der Player gestartet wird.", "no-hostname-config-error": u"Hostname darf nicht leer sein", "invalid-port-config-error" : u"Port muss gültig sein", @@ -151,7 +152,7 @@ de = { "failed-to-load-server-list-error" : u"Konnte die Liste der öffentlichen Server nicht laden. Bitte besuche http://www.syncplay.pl/ [Englisch] mit deinem Browser.", # Client arguments - "argument-description" : u'Syncplay ist eine Anwendung um mehrere MPlayer, MPC-HC und VLC-Instanzen über das Internet zu synchronisieren.', + "argument-description" : u'Syncplay ist eine Anwendung um mehrere MPlayer, MPC-HC, MPC-BE und VLC-Instanzen über das Internet zu synchronisieren.', "argument-epilog" : u'Wenn keine Optionen angegeben sind, werden die _config-Werte verwendet', "nogui-argument" : u'Keine GUI anzeigen', "host-argument" : u'Server-Adresse', @@ -195,7 +196,7 @@ de = { "filename-privacy-label" : u"Dateiname:", "filesize-privacy-label" : u"Dateigröße:", "checkforupdatesautomatically-label" : u"Automatisch nach Updates suchen", - "slowondesync-label" : u"Verlangsamen wenn nicht synchron (nicht unterstützt mit MPC-HC)", + "slowondesync-label" : u"Verlangsamen wenn nicht synchron (nicht unterstützt mit MPC-HC/BE)", "dontslowdownwithme-label" : u"Nie verlangsamen oder andere zurückspulen (Experimentell)", "pausing-title" : u"Pausing", # TODO: Translate "pauseonleave-label" : u"Pausieren wenn ein Benutzer austritt", @@ -340,7 +341,7 @@ de = { "password-tooltip" : u"Passwörter sind nur bei Verbindung zu privaten Servern nötig.", "room-tooltip" : u"Der Raum, der betreten werden soll, kann ein x-beliebiger sein. Allerdings werden nur Clients im selben Raum synchronisiert.", - "executable-path-tooltip" : u"Pfad zum ausgewählten, unterstützten Mediaplayer (MPC-HC, VLC, mplayer2 or mpv).", + "executable-path-tooltip" : u"Pfad zum ausgewählten, unterstützten Mediaplayer (MPC-HC, MPC-BE, VLC, mplayer2 or mpv).", "media-path-tooltip" : u"Pfad zum wiederzugebenden Video oder Stream. Notwendig für mplayer2.", # TODO: Confirm translation "player-arguments-tooltip" : u"Zusätzliche Kommandozeilenparameter / -schalter für diesen Mediaplayer.", "mediasearcdirectories-arguments-tooltip" : u"Verzeichnisse, in denen Syncplay nach Mediendateien suchen soll, z.B. wenn du das Click-to-switch-Feature verwendest. Syncplay wird rekursiv Unterordner durchsuchen.", # TODO: Translate Click-to-switch? (or use as name for feature) @@ -418,7 +419,7 @@ de = { "no-salt-notification" : u"WICHTIGER HINWEIS: Damit von dem Server generierte Passwörter für geführte Räume auch nach einem Serverneustart funktionieren, starte den Server mit dem folgenden Parameter: --salt {}", #Salt # Server arguments - "server-argument-description" : u'Anwendung, um mehrere MPlayer, MPC-HC und VLC-Instanzen über das Internet zu synchronisieren. Server', + "server-argument-description" : u'Anwendung, um mehrere MPlayer, MPC-HC/BE und VLC-Instanzen über das Internet zu synchronisieren. Server', "server-argument-epilog" : u'Wenn keine Optionen angegeben sind, werden die _config-Werte verwendet', "server-port-argument" : u'Server TCP-Port', "server-password-argument" : u'Server Passwort', diff --git a/syncplay/messages_en.py b/syncplay/messages_en.py index 4f6c01f..f0ae04e 100644 --- a/syncplay/messages_en.py +++ b/syncplay/messages_en.py @@ -107,9 +107,10 @@ en = { "server-timeout-error" : "Connection with server timed out", "mpc-slave-error" : "Unable to start MPC in slave mode!", "mpc-version-insufficient-error" : "MPC version not sufficient, please use `mpc-hc` >= `{}`", + "mpc-be-version-insufficient-error" : "MPC version not sufficient, please use `mpc-be` >= `{}`", "mpv-version-error" : "Syncplay is not compatible with this version of mpv. Please use a different version of mpv (e.g. Git HEAD).", "player-file-open-error" : "Player failed opening file", - "player-path-error" : "Player path is not set properly. Supported players are: mpv, VLC, MPC-HC and mplayer2", + "player-path-error" : "Player path is not set properly. Supported players are: mpv, VLC, MPC-HC, MPC-BE and mplayer2", "hostname-empty-error" : "Hostname can't be empty", "empty-error" : "{} can't be empty", # Configuration "media-player-error": "Media player error: \"{}\"", # Error line @@ -119,7 +120,7 @@ en = { "unable-to-start-client-error" : "Unable to start client", - "player-path-config-error": "Player path is not set properly. Supported players are: mpv, VLC, MPC-HC and mplayer2.", + "player-path-config-error": "Player path is not set properly. Supported players are: mpv, VLC, MPC-HC, MPC-BE and mplayer2.", "no-file-path-config-error" :"File must be selected before starting your player", "no-hostname-config-error": "Hostname can't be empty", "invalid-port-config-error" : "Port must be valid", @@ -154,7 +155,7 @@ en = { "failed-to-load-server-list-error" : u"Failed to load public server list. Please visit http://www.syncplay.pl/ in your browser.", # Client arguments - "argument-description" : 'Solution to synchronize playback of multiple MPlayer and MPC-HC instances over the network.', + "argument-description" : 'Solution to synchronize playback of multiple media player instances over the network.', "argument-epilog" : 'If no options supplied _config values will be used', "nogui-argument" : 'show no GUI', "host-argument" : 'server\'s address', @@ -198,7 +199,7 @@ en = { "filename-privacy-label" : "Filename information:", "filesize-privacy-label" : "File size information:", "checkforupdatesautomatically-label" : "Check for Syncplay updates automatically", - "slowondesync-label" : "Slow down on minor desync (not supported on MPC-HC)", + "slowondesync-label" : "Slow down on minor desync (not supported on MPC-HC/BE)", "rewindondesync-label" : "Rewind on major desync (recommended)", "fastforwardondesync-label" : "Fast-forward if lagging behind (recommended)", "dontslowdownwithme-label" : "Never slow down or rewind others (experimental)", @@ -345,7 +346,7 @@ en = { "password-tooltip" : "Passwords are only needed for connecting to private servers.", "room-tooltip" : "Room to join upon connection can be almost anything, but you will only be synchronised with people in the same room.", - "executable-path-tooltip" : "Location of your chosen supported media player (mpv, VLC, MPC-HC or mplayer2).", + "executable-path-tooltip" : "Location of your chosen supported media player (mpv, VLC, MPC-HC/BE or mplayer2).", "media-path-tooltip" : "Location of video or stream to be opened. Necessary for mplayer2.", "player-arguments-tooltip" : "Additional command line arguments / switches to pass on to this media player.", "mediasearcdirectories-arguments-tooltip" : u"Directories where Syncplay will search for media files, e.g. when you are using the click to switch feature. Syncplay will look recursively through sub-folders.", @@ -357,7 +358,7 @@ en = { "privacy-sendhashed-tooltip" : "Send a hashed version of the information, making it less visible to other clients.", "privacy-dontsend-tooltip" : "Do not send this information to the server. This provides for maximum privacy.", "checkforupdatesautomatically-tooltip" : "Regularly check with the Syncplay website to see whether a new version of Syncplay is available.", - "slowondesync-tooltip" : "Reduce playback rate temporarily when needed to bring you back in sync with other viewers. Not supported on MPC-HC.", + "slowondesync-tooltip" : "Reduce playback rate temporarily when needed to bring you back in sync with other viewers. Not supported on MPC-HC/BE.", "dontslowdownwithme-tooltip" : "Means others do not get slowed down or rewinded if your playback is lagging. Useful for room operators.", "pauseonleave-tooltip" : "Pause playback if you get disconnected or someone leaves from your room.", "readyatstart-tooltip" : "Set yourself as 'ready' at start (otherwise you are set as 'not ready' until you change your readiness state)", @@ -422,7 +423,7 @@ en = { # Server arguments - "server-argument-description" : 'Solution to synchronize playback of multiple MPlayer and MPC-HC instances over the network. Server instance', + "server-argument-description" : 'Solution to synchronize playback of multiple MPlayer and MPC-HC/BE instances over the network. Server instance', "server-argument-epilog" : 'If no options supplied _config values will be used', "server-port-argument" : 'server TCP port', "server-password-argument" : 'server password', diff --git a/syncplay/messages_ru.py b/syncplay/messages_ru.py index e0c864a..666f3d4 100644 --- a/syncplay/messages_ru.py +++ b/syncplay/messages_ru.py @@ -108,9 +108,10 @@ ru = { "server-timeout-error" : u"Подключение к серверу превысило лимит времени", "mpc-slave-error" : u"Невозможно запустить MPC в slave режиме!", "mpc-version-insufficient-error" : u"Версия MPC слишком старая, пожалуйста, используйте `mpc-hc` >= `{}`", + "mpc-be-version-insufficient-error" : u"Версия MPC слишком старая, пожалуйста, используйте `mpc-be` >= `{}`", "mpv-version-error" : u"Syncplay не совместим с данной версией mpv. Пожалуйста, используйте другую версию mpv (лучше свежайшую).", "player-file-open-error" : u"Проигрыватель не может открыть файл.", - "player-path-error" : u"Путь к проигрывателю задан неверно. Supported players are: mpv, VLC, MPC-HC and mplayer2.", # TODO: Translate last sentence + "player-path-error" : u"Путь к проигрывателю задан неверно. Supported players are: mpv, VLC, MPC-HC, MPC-BE and mplayer2.", # TODO: Translate last sentence "hostname-empty-error" : u"Имя пользователя не может быть пустым.", "empty-error" : u"{} не может быть пустым.", # Configuration "media-player-error" : u"Ошибка проигрывателя: \"{}\"", # Error line @@ -120,7 +121,7 @@ ru = { "unable-to-start-client-error" : u"Невозможно запустить клиент", - "player-path-config-error": u"Путь к проигрывателю установлен неверно. Supported players are: mpv, VLC, MPC-HC and mplayer2", # To do: Translate end + "player-path-config-error": u"Путь к проигрывателю установлен неверно. Supported players are: mpv, VLC, MPC-HC, MPC-BE and mplayer2", # To do: Translate end "no-file-path-config-error" : u"Файл должен быть указан до включения проигрывателя", "no-hostname-config-error": u"Имя сервера не может быть пустым", "invalid-port-config-error" : u"Неверный номер порта", @@ -157,7 +158,7 @@ ru = { "failed-to-load-server-list-error" : u"Не удалось загрузить список публичных серверов. Откройте http://www.syncplay.pl/ через браузер.", # Client arguments - "argument-description" : u'Решение для синхронного воспроизведения в VLC, MPlayer или MPC-HC через Интернет.', + "argument-description" : u'Решение для синхронного воспроизведения в VLC, MPlayer или MPC-HC/BE через Интернет.', "argument-epilog" : u'Если параметр не будет передан, то будет использоваться значение, указанное в _config.', "nogui-argument" : u'не использовать GUI', "host-argument" : u'адрес сервера', @@ -201,7 +202,7 @@ ru = { "filename-privacy-label" : u"Имя файла:", "filesize-privacy-label" : u"Размер файла:", "checkforupdatesautomatically-label" : u"Проверять обновления автоматически", - "slowondesync-label" : u"Замедлять при небольших рассинхронизациях (не поддерживаетя в MPC-HC)", + "slowondesync-label" : u"Замедлять при небольших рассинхронизациях (не поддерживаетя в MPC-HC/BE)", "rewindondesync-label" : u"Перемотка при больших рассинхронизациях (настоятельно рекомендуется)", "dontslowdownwithme-label" : u"Никогда не замедлять и не перематывать видео другим (функция тестируется)", "pausing-title" : u"Приостановка", @@ -348,7 +349,7 @@ ru = { "password-tooltip" : u"Пароли нужны для подключения к приватным серверам.", "room-tooltip" : u"Комната, в которую Вы попадете сразу после подключения. Синхронизация возможна только между людьми в одной и той же комнате.", - "executable-path-tooltip" : u"Расположение Вашего видеопроигрывателя (MPC-HC, VLC, mplayer2 или mpv).", + "executable-path-tooltip" : u"Расположение Вашего видеопроигрывателя (MPC-HC, MPC-BE, VLC, mplayer2 или mpv).", "media-path-tooltip" : u"Расположение видеофайла или потока для просмотра. Обязательно для mplayer2.", # TODO: Confirm translation "player-arguments-tooltip" : u"Передавать дополнительные аргументы командной строки этому проигрывателю.", "mediasearcdirectories-arguments-tooltip" : u"Папки, где Syncplay будет искать медиа файлы, включая подпапки.", @@ -360,7 +361,7 @@ ru = { "privacy-sendhashed-tooltip" : u"Отправляет хэш-сумму этой информации, делая ее невидимой для других пользователей.", "privacy-dontsend-tooltip" : u"Не отправлять эту информацию на сервер. Предоставляет наибольшую приватность.", "checkforupdatesautomatically-tooltip" : u"Syncplay будет регулярно заходить на сайт и проверять наличие новых версий.", - "slowondesync-tooltip" : u"Временно уменьшить скорость воспроизведения в целях синхронизации с другими зрителями. Не поддерживается в MPC-HC.", + "slowondesync-tooltip" : u"Временно уменьшить скорость воспроизведения в целях синхронизации с другими зрителями. Не поддерживается в MPC-HC/BE.", "dontslowdownwithme-tooltip" : u"Ваши лаги не будут влиять на других зрителей.", "pauseonleave-tooltip" : u"Приостановить воспроизведение, если Вы покинули комнату или кто-то из зрителей отключился от сервера.", "readyatstart-tooltip" : u"Отметить Вас готовым к просмотру сразу же (по умолчанию Вы отмечены не готовым)", @@ -424,7 +425,7 @@ ru = { "no-salt-notification" : u"ВНИМАНИЕ: Чтобы сгенерированные сервером пароли операторов комнат работали после перезагрузки сервера, необходимо указать следующий аргумент командной строки при запуске сервера Syncplay: --salt {}", #Salt # Server arguments - "server-argument-description" : u'Решение для синхронного воспроизведения в VLC, MPlayer или MPC-HC через Интернет. Серверная часть', + "server-argument-description" : u'Решение для синхронного воспроизведения в VLC, MPlayer или MPC-HC/BE через Интернет. Серверная часть', "server-argument-epilog" : u'Если параметр не будет передан, то будет использоваться значение, указанное в _config.', "server-port-argument" : u'номер TCP порта сервера', "server-password-argument" : u'пароль к серверу', diff --git a/syncplay/players/__init__.py b/syncplay/players/__init__.py index a1afcb4..710bfe1 100644 --- a/syncplay/players/__init__.py +++ b/syncplay/players/__init__.py @@ -6,6 +6,11 @@ try: except ImportError: from syncplay.players.basePlayer import DummyPlayer MPCHCAPIPlayer = DummyPlayer +try: + from syncplay.players.mpcbe import MpcBePlayer +except ImportError: + from syncplay.players.basePlayer import DummyPlayer + MpcBePlayer = DummyPlayer def getAvailablePlayers(): - return [MPCHCAPIPlayer, MplayerPlayer, MpvPlayer, VlcPlayer] + return [MPCHCAPIPlayer, MplayerPlayer, MpvPlayer, VlcPlayer, MpcBePlayer] diff --git a/syncplay/players/mpc.py b/syncplay/players/mpc.py index 4282ad0..e4d2810 100644 --- a/syncplay/players/mpc.py +++ b/syncplay/players/mpc.py @@ -328,6 +328,10 @@ class MPCHCAPIPlayer(BasePlayer): self.__versionUpdate = threading.Event() self.__fileUpdate = threading.RLock() self.__versionUpdate.clear() + + @staticmethod + def getMinVersionErrorMessage(): + return getMessage("mpc-version-insufficient-error").format(constants.MPC_MIN_VER) def drop(self): self.__preventAsking.set() @@ -366,7 +370,7 @@ class MPCHCAPIPlayer(BasePlayer): def __dropIfNotSufficientVersion(self): self._mpcApi.askForVersion() if not self.__versionUpdate.wait(0.1) or not self._mpcApi.version: - self.reactor.callFromThread(self.__client.ui.showErrorMessage, getMessage("mpc-version-insufficient-error").format(constants.MPC_MIN_VER), True) + self.reactor.callFromThread(self.__client.ui.showErrorMessage, self.getMinVersionErrorMessage(), True) self.reactor.callFromThread(self.__client.stop, True) def __testMpcReady(self): @@ -383,7 +387,7 @@ class MPCHCAPIPlayer(BasePlayer): self.reactor.callFromThread(self.__client.ui.showErrorMessage, err.message, True) self.reactor.callFromThread(self.__client.stop) - def initPlayer(self, filePath): + def initPlayer(self, filePath): self.__dropIfNotSufficientVersion() if not self._mpcApi.version: return diff --git a/syncplay/players/mpcbe.py b/syncplay/players/mpcbe.py new file mode 100644 index 0000000..68b2074 --- /dev/null +++ b/syncplay/players/mpcbe.py @@ -0,0 +1,50 @@ +from syncplay import constants +import os.path +from syncplay.messages import getMessage +from syncplay.players.mpc import MPCHCAPIPlayer + +class MpcBePlayer(MPCHCAPIPlayer): + @staticmethod + def run(client, playerPath, filePath, args): + args.extend(['/open', '/new']) + mpc = MpcBePlayer(client) + mpc._mpcApi.callbacks.onConnected = lambda: mpc.initPlayer(filePath if filePath else None) + mpc._mpcApi.startMpc(MpcBePlayer.getExpandedPath(playerPath), args) + client.initPlayer(mpc) + return mpc + + @staticmethod + def getDefaultPlayerPathsList(): + return constants.MPC_BE_PATHS + + @staticmethod + def getIconPath(path): + return constants.MPC_BE_ICONPATH + + @staticmethod + def isValidPlayerPath(path): + if MpcBePlayer.getExpandedPath(path): + return True + return False + + @staticmethod + def getExpandedPath(path): + if os.path.isfile(path): + if path.lower().endswith(u'mpc-be.exe'.lower()) or path.lower().endswith(u'mpc-be64.exe'.lower()): + return path + if os.path.isfile(path + u"mpc-be.exe"): + path += u"mpc-be.exe" + return path + if os.path.isfile(path + u"\\mpc-be.exe"): + path += u"\\mpc-be.exe" + return path + if os.path.isfile(path + u"mpc-be64.exe"): + path += u"mpc-be64.exe" + return path + if os.path.isfile(path + u"\\mpc-be64.exe"): + path += u"\\mpc-be64.exe" + return path + + @staticmethod + def getMinVersionErrorMessage(): + return getMessage("mpc-be-version-insufficient-error").format(constants.MPC_BE_MIN_VER) diff --git a/syncplay/players/mplayer.py b/syncplay/players/mplayer.py index e34aa77..3b414e2 100644 --- a/syncplay/players/mplayer.py +++ b/syncplay/players/mplayer.py @@ -6,6 +6,7 @@ from syncplay.players.basePlayer import BasePlayer from syncplay import constants, utils from syncplay.messages import getMessage import os, sys +from syncplay.utils import isWindows class MplayerPlayer(BasePlayer): speedSupported = True @@ -305,7 +306,7 @@ class MplayerPlayer(BasePlayer): call = [playerPath] if filePath: - if sys.platform.startswith('win') and not utils.isASCII(filePath): + if isWindows() and not utils.isASCII(filePath): self.__playerController.delayedFilePath = filePath filePath = None else: diff --git a/syncplay/players/vlc.py b/syncplay/players/vlc.py index d55b8d4..eb7e247 100755 --- a/syncplay/players/vlc.py +++ b/syncplay/players/vlc.py @@ -11,6 +11,7 @@ import asynchat, asyncore import urllib import time from syncplay.messages import getMessage +from syncplay.utils import isBSD, isLinux, isWindows, isMacOS class VlcPlayer(BasePlayer): speedSupported = True @@ -21,10 +22,10 @@ class VlcPlayer(BasePlayer): RE_ANSWER = re.compile(constants.VLC_ANSWER_REGEX) SLAVE_ARGS = constants.VLC_SLAVE_ARGS - if sys.platform.startswith('darwin'): - SLAVE_ARGS.extend(constants.VLC_SLAVE_OSX_ARGS) + if isMacOS(): + SLAVE_ARGS.extend(constants.VLC_SLAVE_MACOS_ARGS) else: - SLAVE_ARGS.extend(constants.VLC_SLAVE_NONOSX_ARGS) + SLAVE_ARGS.extend(constants.VLC_SLAVE_NONMACOS_ARGS) vlcport = random.randrange(constants.VLC_MIN_PORT, constants.VLC_MAX_PORT) if (constants.VLC_MIN_PORT < constants.VLC_MAX_PORT) else constants.VLC_MIN_PORT def __init__(self, client, playerPath, filePath, args): @@ -147,7 +148,7 @@ class VlcPlayer(BasePlayer): fileURL = fileURL.replace(u'\\', u'/') fileURL = fileURL.encode('utf8') fileURL = urllib.quote_plus(fileURL) - if sys.platform.startswith('win'): + if isWindows(): fileURL = "file:///" + fileURL else: fileURL = "file://" + fileURL @@ -332,13 +333,13 @@ class VlcPlayer(BasePlayer): return False playerController._client.ui.showErrorMessage(getMessage("vlc-interface-not-installed")) return False - if sys.platform.startswith('linux'): + if isLinux(): playerController.vlcIntfPath = "/usr/lib/vlc/lua/intf/" playerController.vlcIntfUserPath = os.path.join(os.getenv('HOME', '.'), ".local/share/vlc/lua/intf/") - elif sys.platform.startswith('darwin'): + elif isMacOS(): playerController.vlcIntfPath = "/Applications/VLC.app/Contents/MacOS/share/lua/intf/" playerController.vlcIntfUserPath = os.path.join(os.getenv('HOME', '.'), "Library/Application Support/org.videolan.vlc/lua/intf/") - elif 'bsd' in sys.platform or sys.platform.startswith('dragonfly'): + elif isBSD(): # *BSD ports/pkgs install to /usr/local by default. # This should also work for all the other BSDs, such as OpenBSD or DragonFly. playerController.vlcIntfPath = "/usr/local/lib/vlc/lua/intf/" @@ -350,7 +351,7 @@ class VlcPlayer(BasePlayer): if _usevlcintf(playerController.vlcIntfPath, playerController.vlcIntfUserPath): playerController.SLAVE_ARGS.append('--lua-config=syncplay={{port=\"{}\"}}'.format(str(playerController.vlcport))) else: - if sys.platform.startswith('linux'): + if isLinux(): playerController.vlcDataPath = "/usr/lib/syncplay/resources" else: playerController.vlcDataPath = utils.findWorkingDir() + "\\resources" @@ -388,7 +389,7 @@ class VlcPlayer(BasePlayer): playerController._client.ui.showErrorMessage( getMessage("media-player-error").format(line), True) break - if not sys.platform.startswith('darwin'): + if not isMacOS(): self.__process.stderr = None else: vlcoutputthread = threading.Thread(target = self.handle_vlcoutput, args=()) @@ -402,7 +403,7 @@ class VlcPlayer(BasePlayer): self._sendingData = threading.Lock() def _shouldListenForSTDOUT(self): - if sys.platform.startswith('win'): + if isWindows(): return False # Due to VLC3 not using STDOUT/STDERR else: return True diff --git a/syncplay/ui/ConfigurationGetter.py b/syncplay/ui/ConfigurationGetter.py index 2c4634a..5855194 100755 --- a/syncplay/ui/ConfigurationGetter.py +++ b/syncplay/ui/ConfigurationGetter.py @@ -6,6 +6,7 @@ import ast from syncplay import constants, utils, version, milestone from syncplay.messages import getMessage, setLanguage, isValidLanguage from syncplay.players.playerFactory import PlayerFactory +from syncplay.utils import isMacOS import codecs import re @@ -469,7 +470,7 @@ class ConfigurationGetter(object): if QCoreApplication.instance() is None: self.app = QtWidgets.QApplication(sys.argv) qt5reactor.install() - if sys.platform.startswith('darwin'): + if isMacOS(): import appnope appnope.nope() except ImportError: diff --git a/syncplay/ui/GuiConfiguration.py b/syncplay/ui/GuiConfiguration.py index 577dbea..c20ea34 100644 --- a/syncplay/ui/GuiConfiguration.py +++ b/syncplay/ui/GuiConfiguration.py @@ -12,7 +12,8 @@ import sys import threading from syncplay.messages import getMessage, getLanguages, setLanguage, getInitialLanguage from syncplay import constants - +from syncplay.utils import isBSD, isLinux, isMacOS +from syncplay.utils import resourcespath, posixresourcespath class GuiConfiguration: def __init__(self, config, error=None, defaultConfig=None): self.defaultConfig = defaultConfig @@ -185,12 +186,12 @@ class ConfigDialog(QtWidgets.QDialog): def _updateExecutableIcon(self, iconpath, playerpath): if iconpath is not None and iconpath != "": if iconpath.endswith('.mng'): - movie = QtGui.QMovie(self.resourcespath + iconpath) + movie = QtGui.QMovie(resourcespath + iconpath) movie.setCacheMode(QtGui.QMovie.CacheMode.CacheAll) self.executableiconLabel.setMovie(movie) movie.start() else: - self.executableiconImage.load(self.resourcespath + iconpath) + self.executableiconImage.load(resourcespath + iconpath) self.executableiconLabel.setPixmap(QtGui.QPixmap.fromImage(self.executableiconImage)) else: self.executableiconLabel.setPixmap(QtGui.QPixmap.fromImage(QtGui.QImage())) @@ -238,11 +239,11 @@ class ConfigDialog(QtWidgets.QDialog): defaultdirectory = os.environ["ProgramFiles"] elif "PROGRAMW6432" in os.environ: defaultdirectory = os.environ["ProgramW6432"] - elif sys.platform.startswith('linux'): + elif isLinux(): defaultdirectory = "/usr/bin" - elif sys.platform.startswith('darwin'): + elif isMacOS(): defaultdirectory = "/Applications/" - elif "bsd" in sys.platform or sys.platform.startswith('dragonfly'): + elif isBSD(): defaultdirectory = "/usr/local/bin" fileName, filtr = QtWidgets.QFileDialog.getOpenFileName(self, @@ -250,7 +251,7 @@ class ConfigDialog(QtWidgets.QDialog): defaultdirectory, browserfilter, "", options) if fileName: - if sys.platform.startswith('darwin') and fileName.endswith('.app'): # see GitHub issue #91 + if isMacOS() and fileName.endswith('.app'): # see GitHub issue #91 # Mac OS X application bundles contain a Info.plist in the Contents subdirectory of the .app. # This plist file includes the 'CFBundleExecutable' key, which specifies the name of the # executable. I would have used plistlib here, but since the version of this library in @@ -375,7 +376,7 @@ class ConfigDialog(QtWidgets.QDialog): elif os.path.isdir(QStandardPaths.standardLocations(QStandardPaths.HomeLocation)[0]): defaultdirectory = QStandardPaths.standardLocations(QStandardPaths.HomeLocation)[0] else: - defaultdirectory = "" + defaultdirectory = "" browserfilter = "All files (*)" fileName, filtr = QtWidgets.QFileDialog.getOpenFileName(self, "Browse for media files", defaultdirectory, browserfilter, "", options) @@ -530,7 +531,6 @@ class ConfigDialog(QtWidgets.QDialog): def addBasicTab(self): config = self.config playerpaths = self.playerpaths - resourcespath = self.resourcespath error = self.error if self.datacleared == True: error = constants.ERROR_MESSAGE_MARKER + "{}".format(getMessage("gui-data-cleared-notification")) @@ -701,22 +701,22 @@ class ConfigDialog(QtWidgets.QDialog): self.readyUnpauseButtonGroup = QButtonGroup() self.unpauseIfAlreadyReadyOption = QRadioButton(getMessage("unpause-ifalreadyready-option")) self.readyUnpauseButtonGroup.addButton(self.unpauseIfAlreadyReadyOption) - self.unpauseIfAlreadyReadyOption.setStyleSheet(constants.STYLE_SUBCHECKBOX.format(self.posixresourcespath + "chevrons_right.png")) + self.unpauseIfAlreadyReadyOption.setStyleSheet(constants.STYLE_SUBCHECKBOX.format(posixresourcespath + "chevrons_right.png")) self.unpauseIfAlreadyReadyOption.setObjectName("unpause-ifalreadyready" + constants.CONFIG_NAME_MARKER + "unpauseAction" + constants.CONFIG_VALUE_MARKER + constants.UNPAUSE_IFALREADYREADY_MODE) self.readyUnpauseLayout.addWidget(self.unpauseIfAlreadyReadyOption) self.unpauseIfOthersReadyOption = QRadioButton(getMessage("unpause-ifothersready-option")) self.readyUnpauseButtonGroup.addButton(self.unpauseIfOthersReadyOption) - self.unpauseIfOthersReadyOption.setStyleSheet(constants.STYLE_SUBCHECKBOX.format(self.posixresourcespath + "chevrons_right.png")) + self.unpauseIfOthersReadyOption.setStyleSheet(constants.STYLE_SUBCHECKBOX.format(posixresourcespath + "chevrons_right.png")) self.unpauseIfOthersReadyOption.setObjectName("unpause-ifothersready" + constants.CONFIG_NAME_MARKER + "unpauseAction" + constants.CONFIG_VALUE_MARKER + constants.UNPAUSE_IFOTHERSREADY_MODE) self.readyUnpauseLayout.addWidget(self.unpauseIfOthersReadyOption) self.unpauseIfMinUsersReadyOption = QRadioButton(getMessage("unpause-ifminusersready-option")) self.readyUnpauseButtonGroup.addButton(self.unpauseIfMinUsersReadyOption) - self.unpauseIfMinUsersReadyOption.setStyleSheet(constants.STYLE_SUBCHECKBOX.format(self.posixresourcespath + "chevrons_right.png")) + self.unpauseIfMinUsersReadyOption.setStyleSheet(constants.STYLE_SUBCHECKBOX.format(posixresourcespath + "chevrons_right.png")) self.unpauseIfMinUsersReadyOption.setObjectName("unpause-ifminusersready" + constants.CONFIG_NAME_MARKER + "unpauseAction" + constants.CONFIG_VALUE_MARKER + constants.UNPAUSE_IFMINUSERSREADY_MODE) self.readyUnpauseLayout.addWidget(self.unpauseIfMinUsersReadyOption) self.unpauseAlwaysUnpauseOption = QRadioButton(getMessage("unpause-always")) self.readyUnpauseButtonGroup.addButton(self.unpauseAlwaysUnpauseOption) - self.unpauseAlwaysUnpauseOption.setStyleSheet(constants.STYLE_SUBCHECKBOX.format(self.posixresourcespath + "chevrons_right.png")) + self.unpauseAlwaysUnpauseOption.setStyleSheet(constants.STYLE_SUBCHECKBOX.format(posixresourcespath + "chevrons_right.png")) self.unpauseAlwaysUnpauseOption.setObjectName("unpause-always" + constants.CONFIG_NAME_MARKER + "unpauseAction" + constants.CONFIG_VALUE_MARKER + constants.UNPAUSE_ALWAYS_MODE) self.readyUnpauseLayout.addWidget(self.unpauseAlwaysUnpauseOption) self.readyLayout.addWidget(self.readyUnpauseGroup) @@ -1028,27 +1028,27 @@ class ConfigDialog(QtWidgets.QDialog): self.showSameRoomOSDCheckbox = QCheckBox(getMessage("showsameroomosd-label")) self.showSameRoomOSDCheckbox.setObjectName("showSameRoomOSD") - self.showSameRoomOSDCheckbox.setStyleSheet(constants.STYLE_SUBCHECKBOX.format(self.posixresourcespath + u"chevrons_right.png")) + self.showSameRoomOSDCheckbox.setStyleSheet(constants.STYLE_SUBCHECKBOX.format(posixresourcespath + u"chevrons_right.png")) self.osdSettingsLayout.addWidget(self.showSameRoomOSDCheckbox) self.showNonControllerOSDCheckbox = QCheckBox(getMessage("shownoncontrollerosd-label")) self.showNonControllerOSDCheckbox.setObjectName("showNonControllerOSD") - self.showNonControllerOSDCheckbox.setStyleSheet(constants.STYLE_SUBCHECKBOX.format(self.posixresourcespath + u"chevrons_right.png")) + self.showNonControllerOSDCheckbox.setStyleSheet(constants.STYLE_SUBCHECKBOX.format(posixresourcespath + u"chevrons_right.png")) self.osdSettingsLayout.addWidget(self.showNonControllerOSDCheckbox) self.showDifferentRoomOSDCheckbox = QCheckBox(getMessage("showdifferentroomosd-label")) self.showDifferentRoomOSDCheckbox.setObjectName("showDifferentRoomOSD") - self.showDifferentRoomOSDCheckbox.setStyleSheet(constants.STYLE_SUBCHECKBOX.format(self.posixresourcespath + u"chevrons_right.png")) + self.showDifferentRoomOSDCheckbox.setStyleSheet(constants.STYLE_SUBCHECKBOX.format(posixresourcespath + u"chevrons_right.png")) self.osdSettingsLayout.addWidget(self.showDifferentRoomOSDCheckbox) self.slowdownOSDCheckbox = QCheckBox(getMessage("showslowdownosd-label")) self.slowdownOSDCheckbox.setObjectName("showSlowdownOSD") - self.slowdownOSDCheckbox.setStyleSheet(constants.STYLE_SUBCHECKBOX.format(self.posixresourcespath + u"chevrons_right.png")) + self.slowdownOSDCheckbox.setStyleSheet(constants.STYLE_SUBCHECKBOX.format(posixresourcespath + u"chevrons_right.png")) self.osdSettingsLayout.addWidget(self.slowdownOSDCheckbox) self.showOSDWarningsCheckbox = QCheckBox(getMessage("showosdwarnings-label")) self.showOSDWarningsCheckbox.setObjectName("showOSDWarnings") - self.showOSDWarningsCheckbox.setStyleSheet(constants.STYLE_SUBCHECKBOX.format(self.posixresourcespath + u"chevrons_right.png")) + self.showOSDWarningsCheckbox.setStyleSheet(constants.STYLE_SUBCHECKBOX.format(posixresourcespath + u"chevrons_right.png")) self.osdSettingsLayout.addWidget(self.showOSDWarningsCheckbox) self.subitems['showOSD'] = ["showSameRoomOSD", "showDifferentRoomOSD", "showSlowdownOSD", "showOSDWarnings", "showNonControllerOSD"] @@ -1104,11 +1104,10 @@ class ConfigDialog(QtWidgets.QDialog): def addBottomLayout(self): config = self.config - resourcespath = self.resourcespath self.bottomButtonFrame = QtWidgets.QFrame() self.bottomButtonLayout = QtWidgets.QHBoxLayout() - self.helpButton = QtWidgets.QPushButton(QtGui.QIcon(self.resourcespath + u'help.png'), getMessage("help-label")) + self.helpButton = QtWidgets.QPushButton(QtGui.QIcon(resourcespath + u'help.png'), getMessage("help-label")) self.helpButton.setObjectName("help") self.helpButton.setMaximumSize(self.helpButton.sizeHint()) self.helpButton.released.connect(self.openHelp) @@ -1151,12 +1150,12 @@ class ConfigDialog(QtWidgets.QDialog): self.tabListLayout = QtWidgets.QHBoxLayout() self.tabListFrame = QtWidgets.QFrame() self.tabListWidget = QtWidgets.QListWidget() - self.tabListWidget.addItem(QtWidgets.QListWidgetItem(QtGui.QIcon(self.resourcespath + u"house.png"),getMessage("basics-label"))) - self.tabListWidget.addItem(QtWidgets.QListWidgetItem(QtGui.QIcon(self.resourcespath + u"control_pause_blue.png"),getMessage("readiness-label"))) - self.tabListWidget.addItem(QtWidgets.QListWidgetItem(QtGui.QIcon(self.resourcespath + u"film_link.png"),getMessage("sync-label"))) - self.tabListWidget.addItem(QtWidgets.QListWidgetItem(QtGui.QIcon(self.resourcespath + u"user_comment.png"), getMessage("chat-label"))) - self.tabListWidget.addItem(QtWidgets.QListWidgetItem(QtGui.QIcon(self.resourcespath + u"error.png"),getMessage("messages-label"))) - self.tabListWidget.addItem(QtWidgets.QListWidgetItem(QtGui.QIcon(self.resourcespath + u"cog.png"),getMessage("misc-label"))) + self.tabListWidget.addItem(QtWidgets.QListWidgetItem(QtGui.QIcon(resourcespath + u"house.png"),getMessage("basics-label"))) + self.tabListWidget.addItem(QtWidgets.QListWidgetItem(QtGui.QIcon(resourcespath + u"control_pause_blue.png"),getMessage("readiness-label"))) + self.tabListWidget.addItem(QtWidgets.QListWidgetItem(QtGui.QIcon(resourcespath + u"film_link.png"),getMessage("sync-label"))) + self.tabListWidget.addItem(QtWidgets.QListWidgetItem(QtGui.QIcon(resourcespath + u"user_comment.png"), getMessage("chat-label"))) + self.tabListWidget.addItem(QtWidgets.QListWidgetItem(QtGui.QIcon(resourcespath + u"error.png"),getMessage("messages-label"))) + self.tabListWidget.addItem(QtWidgets.QListWidgetItem(QtGui.QIcon(resourcespath + u"cog.png"),getMessage("misc-label"))) self.tabListLayout.addWidget(self.tabListWidget) self.tabListFrame.setLayout(self.tabListLayout) self.tabListFrame.setFixedWidth(self.tabListFrame.minimumSizeHint().width() + constants.TAB_PADDING) @@ -1255,12 +1254,6 @@ class ConfigDialog(QtWidgets.QDialog): self.QtWidgets = QtWidgets self.QtGui = QtGui self.error = error - if sys.platform.startswith('win'): - resourcespath = utils.findWorkingDir() + "\\resources\\" - else: - resourcespath = utils.findWorkingDir() + u"/resources/" - self.posixresourcespath = utils.findWorkingDir().replace(u"\\","/") + u"/resources/" - self.resourcespath = resourcespath super(ConfigDialog, self).__init__() diff --git a/syncplay/ui/gui.py b/syncplay/ui/gui.py index cad8096..1f46845 100644 --- a/syncplay/ui/gui.py +++ b/syncplay/ui/gui.py @@ -5,17 +5,19 @@ if IsPySide2: from PySide2.QtCore import QStandardPaths from syncplay import utils, constants, version, release_number from syncplay.messages import getMessage +from syncplay.utils import resourcespath import sys import time import urllib from datetime import datetime +from syncplay.utils import isLinux, isWindows, isMacOS import re import os from syncplay.utils import formatTime, sameFilename, sameFilesize, sameFileduration, RoomPasswordProvider, formatSize, isURL from functools import wraps from twisted.internet import task from syncplay.ui.consoleUI import ConsoleUI -if sys.platform.startswith('darwin') and IsPySide: +if isMacOS() and IsPySide: from Foundation import NSURL lastCheckedForUpdates = None @@ -51,10 +53,6 @@ class UserlistItemDelegate(QtWidgets.QStyledItemDelegate): if column == constants.USERLIST_GUI_USERNAME_COLUMN: currentQAbstractItemModel = indexQModelIndex.model() itemQModelIndex = currentQAbstractItemModel.index(indexQModelIndex.row(), constants.USERLIST_GUI_USERNAME_COLUMN, indexQModelIndex.parent()) - if sys.platform.startswith('win'): - resourcespath = utils.findWorkingDir() + u"\\resources\\" - else: - resourcespath = utils.findWorkingDir() + u"/resources/" controlIconQPixmap = QtGui.QPixmap(resourcespath + u"user_key.png") tickIconQPixmap = QtGui.QPixmap(resourcespath + u"tick.png") crossIconQPixmap = QtGui.QPixmap(resourcespath + u"cross.png") @@ -82,10 +80,6 @@ class UserlistItemDelegate(QtWidgets.QStyledItemDelegate): if isUserRow: optionQStyleOptionViewItem.rect.setX(optionQStyleOptionViewItem.rect.x()+constants.USERLIST_GUI_USERNAME_OFFSET) if column == constants.USERLIST_GUI_FILENAME_COLUMN: - if sys.platform.startswith('win'): - resourcespath = utils.findWorkingDir() + u"\\resources\\" - else: - resourcespath = utils.findWorkingDir() + u"/resources/" currentQAbstractItemModel = indexQModelIndex.model() itemQModelIndex = currentQAbstractItemModel.index(indexQModelIndex.row(), constants.USERLIST_GUI_FILENAME_COLUMN, indexQModelIndex.parent()) fileSwitchRole = currentQAbstractItemModel.data(itemQModelIndex, Qt.UserRole + constants.FILEITEM_SWITCH_ROLE) @@ -107,28 +101,23 @@ class UserlistItemDelegate(QtWidgets.QStyledItemDelegate): QtWidgets.QStyledItemDelegate.paint(self, itemQPainter, optionQStyleOptionViewItem, indexQModelIndex) class AboutDialog(QtWidgets.QDialog): - if sys.platform.startswith('win'): - resourcespath = utils.findWorkingDir() + u"\\resources\\" - else: - resourcespath = utils.findWorkingDir() + u"/resources/" - - def __init__(self, parent=None): + def __init__(self, parent=None): super(AboutDialog, self).__init__(parent) - if sys.platform.startswith('darwin'): + if isMacOS(): self.setWindowTitle("") else: self.setWindowTitle(getMessage("about-dialog-title")) - if sys.platform.startswith('win'): - self.setWindowFlags(self.windowFlags() & ~Qt.WindowContextHelpButtonHint) + if isWindows(): + self.setWindowFlags(self.windowFlags() & ~Qt.WindowContextHelpButtonHint) nameLabel = QtWidgets.QLabel("
Syncplay
") nameLabel.setFont(QtGui.QFont("Helvetica", 20)) linkLabel = QtWidgets.QLabel("
syncplay.pl
") linkLabel.setOpenExternalLinks(True) versionLabel = QtWidgets.QLabel("
" + getMessage("about-dialog-release").format(version, release_number, __binding__) + "
") licenseLabel = QtWidgets.QLabel("

Copyright © 2017 Syncplay

" + getMessage("about-dialog-license-text") + "

") - aboutIconPixmap = QtGui.QPixmap(self.resourcespath + u"syncplay.png") + aboutIconPixmap = QtGui.QPixmap(resourcespath + u"syncplay.png") aboutIconLabel = QtWidgets.QLabel() - aboutIconLabel.setPixmap(aboutIconPixmap.scaled(120, 120, Qt.KeepAspectRatio)) + aboutIconLabel.setPixmap(aboutIconPixmap.scaled(120, 120, Qt.KeepAspectRatio)) aboutLayout = QtWidgets.QGridLayout() aboutLayout.addWidget(aboutIconLabel, 0, 0, 4, 2) aboutLayout.addWidget(nameLabel, 0, 2, 1, 2) @@ -148,16 +137,16 @@ class AboutDialog(QtWidgets.QDialog): self.setLayout(aboutLayout) def openLicense(self): - if sys.platform.startswith('win'): - QtGui.QDesktopServices.openUrl(QUrl("file:///" + self.resourcespath + u"license.rtf")) + if isWindows(): + QtGui.QDesktopServices.openUrl(QUrl("file:///" + resourcespath + u"license.rtf")) else: - QtGui.QDesktopServices.openUrl(QUrl("file://" + self.resourcespath + u"license.rtf")) + QtGui.QDesktopServices.openUrl(QUrl("file://" + resourcespath + u"license.rtf")) def openDependencies(self): - if sys.platform.startswith('win'): - QtGui.QDesktopServices.openUrl(QUrl("file:///" + self.resourcespath + u"third-party-notices.rtf")) + if isWindows(): + QtGui.QDesktopServices.openUrl(QUrl("file:///" + resourcespath + u"third-party-notices.rtf")) else: - QtGui.QDesktopServices.openUrl(QUrl("file://" + self.resourcespath + u"third-party-notices.rtf")) + QtGui.QDesktopServices.openUrl(QUrl("file://" + resourcespath + u"third-party-notices.rtf")) class MainWindow(QtWidgets.QMainWindow): insertPosition = None @@ -177,10 +166,6 @@ class MainWindow(QtWidgets.QMainWindow): itemQPainter.save() currentQAbstractItemModel = indexQModelIndex.model() currentlyPlayingFile = currentQAbstractItemModel.data(indexQModelIndex, Qt.UserRole + constants.PLAYLISTITEM_CURRENTLYPLAYING_ROLE) - if sys.platform.startswith('win'): - resourcespath = utils.findWorkingDir() + u"\\resources\\" - else: - resourcespath = utils.findWorkingDir() + u"/resources/" if currentlyPlayingFile: currentlyplayingIconQPixmap = QtGui.QPixmap(resourcespath + u"bullet_right_grey.png") midY = int((optionQStyleOptionViewItem.rect.y() + optionQStyleOptionViewItem.rect.bottomLeft().y()) / 2) @@ -236,10 +221,10 @@ class MainWindow(QtWidgets.QMainWindow): indexRow = window.playlist.count() if window.clearedPlaylistNote else 0 for url in urls[::-1]: - if sys.platform.startswith('darwin') and IsPySide: + if isMacOS() and IsPySide: dropfilepath = os.path.abspath(NSURL.URLWithString_(str(url.toString())).filePathURL().path()) else: - dropfilepath = os.path.abspath(unicode(url.toLocalFile())) + dropfilepath = os.path.abspath(unicode(url.toLocalFile())) if os.path.isfile(dropfilepath): window.addFileToPlaylist(dropfilepath, indexRow) elif os.path.isdir(dropfilepath): @@ -341,10 +326,10 @@ class MainWindow(QtWidgets.QMainWindow): if indexRow == -1: indexRow = window.playlist.count() for url in urls[::-1]: - if sys.platform.startswith('darwin') and IsPySide: + if isMacOS() and IsPySide: dropfilepath = os.path.abspath(NSURL.URLWithString_(str(url.toString())).filePathURL().path()) else: - dropfilepath = os.path.abspath(unicode(url.toLocalFile())) + dropfilepath = os.path.abspath(unicode(url.toLocalFile())) if os.path.isfile(dropfilepath): window.addFileToPlaylist(dropfilepath, indexRow) elif os.path.isdir(dropfilepath): @@ -492,11 +477,11 @@ class MainWindow(QtWidgets.QMainWindow): if isControlledRoom: if room == currentUser.room and currentUser.isController(): - roomitem.setIcon(QtGui.QPixmap(self.resourcespath + 'lock_open.png')) + roomitem.setIcon(QtGui.QPixmap(resourcespath + 'lock_open.png')) else: - roomitem.setIcon(QtGui.QPixmap(self.resourcespath + 'lock.png')) + roomitem.setIcon(QtGui.QPixmap(resourcespath + 'lock.png')) else: - roomitem.setIcon(QtGui.QPixmap(self.resourcespath + 'chevrons_right.png')) + roomitem.setIcon(QtGui.QPixmap(resourcespath + 'chevrons_right.png')) for user in rooms[room]: useritem = QtGui.QStandardItem(user.username) @@ -586,10 +571,6 @@ class MainWindow(QtWidgets.QMainWindow): @needsClient def openPlaylistMenu(self, position): indexes = self.playlist.selectedIndexes() - if sys.platform.startswith('win'): - resourcespath = utils.findWorkingDir() + u"\\resources\\" - else: - resourcespath = utils.findWorkingDir() + u"/resources/" if len(indexes) > 0: item = self.playlist.selectedIndexes()[0] else: @@ -628,10 +609,6 @@ class MainWindow(QtWidgets.QMainWindow): def openRoomMenu(self, position): # TODO: Deselect items after right click indexes = self.listTreeView.selectedIndexes() - if sys.platform.startswith('win'): - resourcespath = utils.findWorkingDir() + u"\\resources\\" - else: - resourcespath = utils.findWorkingDir() + u"/resources/" if len(indexes) > 0: item = self.listTreeView.selectedIndexes()[0] else: @@ -689,18 +666,18 @@ class MainWindow(QtWidgets.QMainWindow): self.listTreeView.header().setSectionResizeMode(0, QtWidgets.QHeaderView.ResizeToContents) self.listTreeView.header().setSectionResizeMode(1, QtWidgets.QHeaderView.ResizeToContents) self.listTreeView.header().setSectionResizeMode(2, QtWidgets.QHeaderView.ResizeToContents) - self.listTreeView.header().setSectionResizeMode(3, QtWidgets.QHeaderView.ResizeToContents) + self.listTreeView.header().setSectionResizeMode(3, QtWidgets.QHeaderView.ResizeToContents) if IsPySide: self.listTreeView.header().setResizeMode(0, QtWidgets.QHeaderView.ResizeToContents) self.listTreeView.header().setResizeMode(1, QtWidgets.QHeaderView.ResizeToContents) self.listTreeView.header().setResizeMode(2, QtWidgets.QHeaderView.ResizeToContents) - self.listTreeView.header().setResizeMode(3, QtWidgets.QHeaderView.ResizeToContents) + self.listTreeView.header().setResizeMode(3, QtWidgets.QHeaderView.ResizeToContents) NarrowTabsWidth = self.listTreeView.header().sectionSize(0)+self.listTreeView.header().sectionSize(1)+self.listTreeView.header().sectionSize(2) if self.listTreeView.header().width() < (NarrowTabsWidth+self.listTreeView.header().sectionSize(3)): self.listTreeView.header().resizeSection(3,self.listTreeView.header().width()-NarrowTabsWidth) else: if IsPySide2: - self.listTreeView.header().setSectionResizeMode(3, QtWidgets.QHeaderView.Stretch) + self.listTreeView.header().setSectionResizeMode(3, QtWidgets.QHeaderView.Stretch) if IsPySide: self.listTreeView.header().setResizeMode(3, QtWidgets.QHeaderView.Stretch) self.listTreeView.expandAll() @@ -871,7 +848,7 @@ class MainWindow(QtWidgets.QMainWindow): defaultdirectory = QtGui.QDesktopServices.storageLocation(QtGui.QDesktopServices.HomeLocation) else: defaultdirectory = "" - elif IsPySide2: + elif IsPySide2: if self.config["mediaSearchDirectories"] and os.path.isdir(self.config["mediaSearchDirectories"][0]) and includeUserSpecifiedDirectories: defaultdirectory = self.config["mediaSearchDirectories"][0] elif includeUserSpecifiedDirectories and os.path.isdir(self.mediadirectory): @@ -881,7 +858,7 @@ class MainWindow(QtWidgets.QMainWindow): elif os.path.isdir(QStandardPaths.standardLocations(QStandardPaths.HomeLocation)[0]): defaultdirectory = QStandardPaths.standardLocations(QStandardPaths.HomeLocation)[0] else: - defaultdirectory = "" + defaultdirectory = "" return defaultdirectory @needsClient @@ -891,7 +868,7 @@ class MainWindow(QtWidgets.QMainWindow): return self.loadMediaBrowseSettings() - if sys.platform.startswith('darwin') and IsPySide: + if isMacOS() and IsPySide: options = QtWidgets.QFileDialog.Options(QtWidgets.QFileDialog.DontUseNativeDialog) else: options = QtWidgets.QFileDialog.Options() @@ -905,7 +882,7 @@ class MainWindow(QtWidgets.QMainWindow): fileName, filtr = QtWidgets.QFileDialog.getOpenFileName(self, getMessage("browseformedia-label"), defaultdirectory, browserfilter, "", options) if fileName: - if sys.platform.startswith('win'): + if isWindows(): fileName = fileName.replace("/", "\\") self.mediadirectory = os.path.dirname(fileName) self._syncplayClient.fileSwitch.setCurrentDirectory(self.mediadirectory) @@ -919,7 +896,7 @@ class MainWindow(QtWidgets.QMainWindow): return self.loadMediaBrowseSettings() - if sys.platform.startswith('darwin') and IsPySide: + if isMacOS() and IsPySide: options = QtWidgets.QFileDialog.Options(QtWidgets.QFileDialog.DontUseNativeDialog) else: options = QtWidgets.QFileDialog.Options() @@ -935,7 +912,7 @@ class MainWindow(QtWidgets.QMainWindow): self.updatingPlaylist = True if fileNames: for fileName in fileNames: - if sys.platform.startswith('win'): + if isWindows(): fileName = fileName.replace("/", "\\") self.mediadirectory = os.path.dirname(fileName) self._syncplayClient.fileSwitch.setCurrentDirectory(self.mediadirectory) @@ -1070,12 +1047,12 @@ class MainWindow(QtWidgets.QMainWindow): @needsClient def openAddMediaDirectoryDialog(self, MediaDirectoriesTextbox, MediaDirectoriesDialog): - if sys.platform.startswith('darwin') and IsPySide: + if isMacOS() and IsPySide: options = QtWidgets.QFileDialog.Options(QtWidgets.QFileDialog.ShowDirsOnly | QtWidgets.QFileDialog.DontUseNativeDialog) else: - options = QtWidgets.QFileDialog.Options(QtWidgets.QFileDialog.ShowDirsOnly) + options = QtWidgets.QFileDialog.Options(QtWidgets.QFileDialog.ShowDirsOnly) folderName = unicode(QtWidgets.QFileDialog.getExistingDirectory(self,None,self.getInitialMediaDirectory(includeUserSpecifiedDirectories=False),options)) - + if folderName: existingMediaDirs = MediaDirectoriesTextbox.toPlainText() if existingMediaDirs == "": @@ -1140,9 +1117,9 @@ class MainWindow(QtWidgets.QMainWindow): self.showErrorMessage(getMessage("invalid-offset-value")) def openUserGuide(self): - if sys.platform.startswith('linux'): + if isLinux(): self.QtGui.QDesktopServices.openUrl(QUrl("http://syncplay.pl/guide/linux/")) - elif sys.platform.startswith('win'): + elif isWindows(): self.QtGui.QDesktopServices.openUrl(QUrl("http://syncplay.pl/guide/windows/")) else: self.QtGui.QDesktopServices.openUrl(QUrl("http://syncplay.pl/guide/")) @@ -1202,7 +1179,7 @@ class MainWindow(QtWidgets.QMainWindow): window.chatInput = QtWidgets.QLineEdit() window.chatInput.setMaxLength(constants.MAX_CHAT_MESSAGE_LENGTH) window.chatInput.returnPressed.connect(self.sendChatMessage) - window.chatButton = QtWidgets.QPushButton(QtGui.QPixmap(self.resourcespath + 'email_go.png'), + window.chatButton = QtWidgets.QPushButton(QtGui.QPixmap(resourcespath + 'email_go.png'), getMessage("sendmessage-label")) window.chatButton.pressed.connect(self.sendChatMessage) window.chatLayout = QtWidgets.QHBoxLayout() @@ -1257,7 +1234,7 @@ class MainWindow(QtWidgets.QMainWindow): window.roomInput = QtWidgets.QLineEdit() window.roomInput.setMaxLength(constants.MAX_ROOM_NAME_LENGTH) window.roomInput.returnPressed.connect(self.joinRoom) - window.roomButton = QtWidgets.QPushButton(QtGui.QPixmap(self.resourcespath + 'door_in.png'), + window.roomButton = QtWidgets.QPushButton(QtGui.QPixmap(resourcespath + 'door_in.png'), getMessage("joinroom-label")) window.roomButton.pressed.connect(self.joinRoom) window.roomLayout = QtWidgets.QHBoxLayout() @@ -1379,24 +1356,24 @@ class MainWindow(QtWidgets.QMainWindow): window.playbackFrame.setLayout(window.playbackLayout) window.seekInput = QtWidgets.QLineEdit() window.seekInput.returnPressed.connect(self.seekFromButton) - window.seekButton = QtWidgets.QPushButton(QtGui.QPixmap(self.resourcespath + u'clock_go.png'), "") + window.seekButton = QtWidgets.QPushButton(QtGui.QPixmap(resourcespath + u'clock_go.png'), "") window.seekButton.setToolTip(getMessage("seektime-menu-label")) window.seekButton.pressed.connect(self.seekFromButton) window.seekInput.setText("0:00") window.seekInput.setFixedWidth(60) window.playbackLayout.addWidget(window.seekInput) window.playbackLayout.addWidget(window.seekButton) - window.unseekButton = QtWidgets.QPushButton(QtGui.QPixmap(self.resourcespath + u'arrow_undo.png'), "") + window.unseekButton = QtWidgets.QPushButton(QtGui.QPixmap(resourcespath + u'arrow_undo.png'), "") window.unseekButton.setToolTip(getMessage("undoseek-menu-label")) window.unseekButton.pressed.connect(self.undoSeek) window.miscLayout = QtWidgets.QHBoxLayout() window.playbackLayout.addWidget(window.unseekButton) - window.playButton = QtWidgets.QPushButton(QtGui.QPixmap(self.resourcespath + u'control_play_blue.png'), "") + window.playButton = QtWidgets.QPushButton(QtGui.QPixmap(resourcespath + u'control_play_blue.png'), "") window.playButton.setToolTip(getMessage("play-menu-label")) window.playButton.pressed.connect(self.play) window.playbackLayout.addWidget(window.playButton) - window.pauseButton = QtWidgets.QPushButton(QtGui.QPixmap(self.resourcespath + 'control_pause_blue.png'), "") + window.pauseButton = QtWidgets.QPushButton(QtGui.QPixmap(resourcespath + 'control_pause_blue.png'), "") window.pauseButton.setToolTip(getMessage("pause-menu-label")) window.pauseButton.pressed.connect(self.pause) window.playbackLayout.addWidget(window.pauseButton) @@ -1410,18 +1387,18 @@ class MainWindow(QtWidgets.QMainWindow): # File menu window.fileMenu = QtWidgets.QMenu(getMessage("file-menu-label"), self) - window.openAction = window.fileMenu.addAction(QtGui.QPixmap(self.resourcespath + 'folder_explore.png'), + window.openAction = window.fileMenu.addAction(QtGui.QPixmap(resourcespath + 'folder_explore.png'), getMessage("openmedia-menu-label")) window.openAction.triggered.connect(self.browseMediapath) - window.openAction = window.fileMenu.addAction(QtGui.QPixmap(self.resourcespath + 'world_explore.png'), + window.openAction = window.fileMenu.addAction(QtGui.QPixmap(resourcespath + 'world_explore.png'), getMessage("openstreamurl-menu-label")) window.openAction.triggered.connect(self.promptForStreamURL) - window.openAction = window.fileMenu.addAction(QtGui.QPixmap(self.resourcespath + 'film_folder_edit.png'), + window.openAction = window.fileMenu.addAction(QtGui.QPixmap(resourcespath + 'film_folder_edit.png'), getMessage("setmediadirectories-menu-label")) window.openAction.triggered.connect(self.openSetMediaDirectoriesDialog) - window.exitAction = window.fileMenu.addAction(QtGui.QPixmap(self.resourcespath + 'cross.png'), + window.exitAction = window.fileMenu.addAction(QtGui.QPixmap(resourcespath + 'cross.png'), getMessage("exit-menu-label")) window.exitAction.triggered.connect(self.exitSyncplay) window.menuBar.addMenu(window.fileMenu) @@ -1429,13 +1406,13 @@ class MainWindow(QtWidgets.QMainWindow): # Playback menu window.playbackMenu = QtWidgets.QMenu(getMessage("playback-menu-label"), self) - window.playAction = window.playbackMenu.addAction(QtGui.QPixmap(self.resourcespath + 'control_play_blue.png'), getMessage("play-menu-label")) + window.playAction = window.playbackMenu.addAction(QtGui.QPixmap(resourcespath + 'control_play_blue.png'), getMessage("play-menu-label")) window.playAction.triggered.connect(self.play) - window.pauseAction = window.playbackMenu.addAction(QtGui.QPixmap(self.resourcespath + 'control_pause_blue.png'), getMessage("pause-menu-label")) + window.pauseAction = window.playbackMenu.addAction(QtGui.QPixmap(resourcespath + 'control_pause_blue.png'), getMessage("pause-menu-label")) window.pauseAction.triggered.connect(self.pause) - window.seekAction = window.playbackMenu.addAction(QtGui.QPixmap(self.resourcespath + 'clock_go.png'), getMessage("seektime-menu-label")) + window.seekAction = window.playbackMenu.addAction(QtGui.QPixmap(resourcespath + 'clock_go.png'), getMessage("seektime-menu-label")) window.seekAction.triggered.connect(self.seekPositionDialog) - window.unseekAction = window.playbackMenu.addAction(QtGui.QPixmap(self.resourcespath + 'arrow_undo.png'), getMessage("undoseek-menu-label")) + window.unseekAction = window.playbackMenu.addAction(QtGui.QPixmap(resourcespath + 'arrow_undo.png'), getMessage("undoseek-menu-label")) window.unseekAction.triggered.connect(self.undoSeek) window.menuBar.addMenu(window.playbackMenu) @@ -1443,16 +1420,16 @@ class MainWindow(QtWidgets.QMainWindow): # Advanced menu window.advancedMenu = QtWidgets.QMenu(getMessage("advanced-menu-label"), self) - window.setoffsetAction = window.advancedMenu.addAction(QtGui.QPixmap(self.resourcespath + 'timeline_marker.png'), + window.setoffsetAction = window.advancedMenu.addAction(QtGui.QPixmap(resourcespath + 'timeline_marker.png'), getMessage("setoffset-menu-label")) window.setoffsetAction.triggered.connect(self.setOffset) - window.setTrustedDomainsAction = window.advancedMenu.addAction(QtGui.QPixmap(self.resourcespath + 'shield_edit.png'), + window.setTrustedDomainsAction = window.advancedMenu.addAction(QtGui.QPixmap(resourcespath + 'shield_edit.png'), getMessage("settrusteddomains-menu-label")) window.setTrustedDomainsAction.triggered.connect(self.openSetTrustedDomainsDialog) window.createcontrolledroomAction = window.advancedMenu.addAction( - QtGui.QPixmap(self.resourcespath + 'page_white_key.png'), getMessage("createcontrolledroom-menu-label")) + QtGui.QPixmap(resourcespath + 'page_white_key.png'), getMessage("createcontrolledroom-menu-label")) window.createcontrolledroomAction.triggered.connect(self.createControlledRoom) - window.identifyascontroller = window.advancedMenu.addAction(QtGui.QPixmap(self.resourcespath + 'key_go.png'), + window.identifyascontroller = window.advancedMenu.addAction(QtGui.QPixmap(resourcespath + 'key_go.png'), getMessage("identifyascontroller-menu-label")) window.identifyascontroller.triggered.connect(self.identifyAsController) @@ -1475,30 +1452,30 @@ class MainWindow(QtWidgets.QMainWindow): # Help menu window.helpMenu = QtWidgets.QMenu(getMessage("help-menu-label"), self) - - window.userguideAction = window.helpMenu.addAction(QtGui.QPixmap(self.resourcespath + 'help.png'), + + window.userguideAction = window.helpMenu.addAction(QtGui.QPixmap(resourcespath + 'help.png'), getMessage("userguide-menu-label")) window.userguideAction.triggered.connect(self.openUserGuide) - window.updateAction = window.helpMenu.addAction(QtGui.QPixmap(self.resourcespath + 'application_get.png'), + window.updateAction = window.helpMenu.addAction(QtGui.QPixmap(resourcespath + 'application_get.png'), getMessage("update-menu-label")) window.updateAction.triggered.connect(self.userCheckForUpdates) - - if not sys.platform.startswith('darwin'): + + if not isMacOS(): window.helpMenu.addSeparator() - window.about = window.helpMenu.addAction(QtGui.QPixmap(self.resourcespath + 'syncplay.png'), + window.about = window.helpMenu.addAction(QtGui.QPixmap(resourcespath + 'syncplay.png'), getMessage("about-menu-label")) else: window.about = window.helpMenu.addAction("&About") window.about.triggered.connect(self.openAbout) window.menuBar.addMenu(window.helpMenu) - if not sys.platform.startswith('darwin'): + if not isMacOS(): window.mainLayout.setMenuBar(window.menuBar) def openAbout(self): aboutMsgBox = AboutDialog() aboutMsgBox.exec_() - + def addMainFrame(self, window): window.mainFrame = QtWidgets.QFrame() window.mainFrame.setLineWidth(0) @@ -1560,16 +1537,16 @@ class MainWindow(QtWidgets.QMainWindow): def updateReadyIcon(self): ready = self.readyPushButton.isChecked() if ready: - self.readyPushButton.setIcon(QtGui.QPixmap(self.resourcespath + 'tick_checkbox.png')) + self.readyPushButton.setIcon(QtGui.QPixmap(resourcespath + 'tick_checkbox.png')) else: - self.readyPushButton.setIcon(QtGui.QPixmap(self.resourcespath + 'empty_checkbox.png')) + self.readyPushButton.setIcon(QtGui.QPixmap(resourcespath + 'empty_checkbox.png')) def updateAutoPlayIcon(self): ready = self.autoplayPushButton.isChecked() if ready: - self.autoplayPushButton.setIcon(QtGui.QPixmap(self.resourcespath + 'tick_checkbox.png')) + self.autoplayPushButton.setIcon(QtGui.QPixmap(resourcespath + 'tick_checkbox.png')) else: - self.autoplayPushButton.setIcon(QtGui.QPixmap(self.resourcespath + 'empty_checkbox.png')) + self.autoplayPushButton.setIcon(QtGui.QPixmap(resourcespath + 'empty_checkbox.png')) def automaticUpdateCheck(self): currentDateTimeValue = QDateTime.currentDateTime() @@ -1628,7 +1605,8 @@ class MainWindow(QtWidgets.QMainWindow): data = event.mimeData() urls = data.urls() if urls and urls[0].scheme() == 'file': - if sys.platform.startswith('darwin') and IsPySide: + url = event.mimeData().urls()[0] + if isMacOS() and IsPySide: dropfilepath = os.path.abspath(NSURL.URLWithString_(str(url.toString())).filePathURL().path()) else: dropfilepath = os.path.abspath(unicode(url.toLocalFile())) @@ -1765,11 +1743,7 @@ class MainWindow(QtWidgets.QMainWindow): self._syncplayClient = None self.folderSearchEnabled = True self.QtGui = QtGui - if sys.platform.startswith('win'): - self.resourcespath = utils.findWorkingDir() + u"\\resources\\" - else: - self.resourcespath = utils.findWorkingDir() + u"/resources/" - if sys.platform.startswith('darwin'): + if isMacOS(): self.setWindowFlags(self.windowFlags()) else: self.setWindowFlags(self.windowFlags() & Qt.AA_DontUseNativeMenuBar) @@ -1780,7 +1754,7 @@ class MainWindow(QtWidgets.QMainWindow): self.addMenubar(self) self.addMainFrame(self) self.loadSettings() - self.setWindowIcon(QtGui.QPixmap(self.resourcespath + u"syncplay.png")) + self.setWindowIcon(QtGui.QPixmap(resourcespath + u"syncplay.png")) self.setWindowFlags(self.windowFlags() & Qt.WindowCloseButtonHint & Qt.AA_DontUseNativeMenuBar & Qt.WindowMinimizeButtonHint & ~Qt.WindowContextHelpButtonHint) self.show() self.setAcceptDrops(True) diff --git a/syncplay/utils.py b/syncplay/utils.py index 4a35da9..72fa947 100644 --- a/syncplay/utils.py +++ b/syncplay/utils.py @@ -17,6 +17,18 @@ import subprocess folderSearchEnabled = True +def isWindows(): + return sys.platform.startswith(constants.OS_WINDOWS) + +def isLinux(): + return sys.platform.startswith(constants.OS_LINUX) + +def isMacOS(): + return sys.platform.startswith(constants.OS_MACOS) + +def isBSD(): + return constants.OS_BSD in sys.platform or sys.platform.startswith(constants.OS_DRAGONFLY) + def retry(ExceptionToCheck, tries=4, delay=3, backoff=2, logger=None): """Retry calling the decorated function using an exponential backoff. @@ -132,11 +144,21 @@ def findWorkingDir(): elif frozen in ('dll', 'console_exe', 'windows_exe'): path = os.path.dirname(os.path.dirname(os.path.dirname(os.path.dirname(__file__)))) elif frozen in ('macosx_app'): - path = os.path.dirname(os.path.dirname(os.path.dirname(os.path.dirname(os.path.dirname(__file__))))) + path = os.path.dirname(os.path.dirname(os.path.dirname(os.path.dirname(os.path.dirname(__file__))))) else: path = "" return path +def getResourcesPath(): + + if isWindows(): + return findWorkingDir() + u"\\resources\\" + else: + return findWorkingDir() + u"/resources/" + +resourcespath = getResourcesPath() +posixresourcespath = findWorkingDir().replace(u"\\","/") + u"/resources/" + def getDefaultMonospaceFont(): if platform.system() == "Windows": return constants.DEFAULT_WINDOWS_MONOSPACE_FONT