From 971ead90c1a03141082ee6429863e84be57adf66 Mon Sep 17 00:00:00 2001 From: The Wobbler Date: Tue, 4 Mar 2025 19:29:24 +0100 Subject: [PATCH] Implemented caching of title, artist and album of a track as WOBUZZM3U parameters. --- wobuzz/player/playlist.py | 41 ++++++++++++++++++++++++++++++--------- wobuzz/player/track.py | 32 +++++++++++++++++++++++++----- 2 files changed, 59 insertions(+), 14 deletions(-) diff --git a/wobuzz/player/playlist.py b/wobuzz/player/playlist.py index 3cb4388..c93ba9e 100644 --- a/wobuzz/player/playlist.py +++ b/wobuzz/player/playlist.py @@ -5,7 +5,7 @@ import threading from PyQt6.QtCore import Qt from PyQt6.QtWidgets import QAbstractItemView -from .track import Track +from .track import Track, TrackMetadata class Playlist: @@ -38,9 +38,7 @@ class Playlist: self.loaded = False self.loading = False - self.path = os.path.expanduser( - f"{app.settings.library_path}/playlists/{self.title.replace(" ", "_")}.wbz.m3u" - ) + self.path = self.path_from_title(title) def clear(self): self.sorting: list[Qt.SortOrder] | None = None @@ -162,6 +160,8 @@ class Playlist: lambda: i ) + track_metadata = TrackMetadata() # cached track metadata from WOBUZZM3U + while i < num_lines: line = lines[i] @@ -177,16 +177,30 @@ class Playlist: # convert these from strings back to int and bool and append them to the sorting self.sorting.append((int(sorting[0]), sorting[1] == "True")) + elif line.startswith("#TRACK_TITLE: "): + track_metadata.title = line[14:] + + elif line.startswith("#TRACK_ARTIST: "): + track_metadata.artist = line[15:] + + elif line.startswith("#TRACK_ALBUM: "): + track_metadata.album = line[14:] + i += 1 continue - elif line.startswith("http"): # filter out urls + elif line.startswith("http"): # ignore urls i += 1 continue - self.append_track(Track(self.app, line, cache=i == 0)) # first track is cached + track_metadata.path = line + track_metadata.add_missing() + + self.append_track(Track(self.app, line, cache=i == 0, metadata=track_metadata)) # first track is cached + + track_metadata = TrackMetadata() # metadata for next track i += 1 @@ -275,6 +289,11 @@ class Playlist: wbz_data += f"#SORT: {sort_column}, {order}\n" for track in self.tracks: + # cache track metadata + wbz_data += f"#TRACK_TITLE: {track.metadata.title}\n" + wbz_data += f"#TRACK_ARTIST: {track.metadata.artist}\n" + wbz_data += f"#TRACK_ALBUM: {track.metadata.album}\n" + wbz_data += f"{track.path}\n" wbz = open(self.path, "w") @@ -288,9 +307,7 @@ class Playlist: old_title = self.title self.title = self.app.utils.unique_name(title, ignore=old_title) - self.path = os.path.expanduser( - f"{self.app.settings.library_path}/playlists/{self.title.replace(" ", "_")}.wbz.m3u" - ) + self.path = self.path_from_title(self.title) # make sure the playlist is not referenced anymore as the temporary playlist if self == self.app.library.temporary_playlist: @@ -334,3 +351,9 @@ class Playlist: if len(self.tracks) > 1: return self.tracks[-2] + def path_from_title(self, title): + path = os.path.expanduser( + f"{self.app.settings.library_path}/playlists/{title.replace(" ", "_")}.wbz.m3u" + ) + + return path diff --git a/wobuzz/player/track.py b/wobuzz/player/track.py index 0b11411..66bd26a 100644 --- a/wobuzz/player/track.py +++ b/wobuzz/player/track.py @@ -9,11 +9,33 @@ from dataclasses import dataclass @dataclass class TrackMetadata: - title: str - artist: str - album: str + path: str | None=None + title: str | None=None + artist: str | None=None + album: str | None=None images: TTImages | None=None # tinytag images + def add_missing(self): + # Make the album be an empty string instead of "None" + if self.title == "None": + self.title = "" + + if self.artist == "None": + self.artist = "" + + if self.album == "None": + self.album = "" + + if self.path is None: # can't add missing information without a path + return + + if self.title is None or self.artist is None or self.album is None: + tags = TinyTag.get(self.path, ignore_errors=True, duration=False) + + self.title = tags.title + self.artist = tags.artist + self.album = tags.album + class Track: """ @@ -26,9 +48,9 @@ class Track: if metadata is None: # load metadata from audio file - tags = TinyTag.get(self.path, ignore_errors=True, duration=False) + tags = TinyTag.get(path, ignore_errors=True, duration=False) - self.metadata = TrackMetadata(tags.title, tags.artist, tags.album) + self.metadata = TrackMetadata(path, tags.title, tags.artist, tags.album) else: self.metadata = metadata