Fixed going to album in offline mode

This commit is contained in:
Sumner Evans
2020-05-25 22:30:01 -06:00
parent e584b181b5
commit 3498a06e61
5 changed files with 54 additions and 44 deletions

View File

@@ -31,34 +31,41 @@ Features
@samsartor for contributing the SVGs!
* A new icon for indicating the connection state to the Subsonic server.
Contributed by @samsartor.
* A new icon for that data wasn't able to be loaded due to being offline.
Contributed by @samsartor.
**Settings**
**Application Menus**
* Settings are now in the popup under the gear icon rather than in a separate
popup window.
* The music provider configuration has gotten a major revamp.
* You can now clear the cache via an option in the Downloads popup. There are
options for removing the entire cache and removing just the song file cache.
.. * The music provider configuration has gotten a major revamp.
.. * The Downloads popup shows the songs that are currently being downloaded.
.. *
**Offline Mode**
* You can enable *Offline Mode* from the server menu.
* Features that require network access are disabled in offline mode.
* You can still browse anything that is already cached offline.
.. MENTION man page
**Other Features**
.. * A man page has been added. Contributed by @baldurmen.
Under The Hood
--------------
This release has a ton of under-the-hood changes to make things more robust
and performant.
This release has a ton of under-the-hood changes to make things more robust
and performant.
* The cache is now stored in a SQLite database.
* The cache no longer gets corrupted when Sublime Music fails to write to
disk.
* A generic `Adapter API`_ has been created which means that Sublime Music is
no longer reliant on Subsonic and in the future, more backends can be added.
* The cache is now stored in a SQLite database.
* The cache no longer gets corrupted when Sublime Music fails to write to disk.
* A generic `Adapter API`_ has been created which means that Sublime Music is no
longer reliant on Subsonic. This means that in the future, more backends can
be added.
.. _Adapter API: https://sumner.gitlab.io/sublime-music/adapter-api.html

View File

@@ -114,15 +114,15 @@ class AlbumSearchQuery:
... AlbumSearchQuery.Type.YEAR_RANGE, year_range=(2018, 2019)
... )
>>> query.strhash()
'a6571bb7be65984c6627f545cab9fc767fce6d07'
'5b0724ae23acd58bc2f9187617712775670e0b98'
"""
if not self._strhash:
self._strhash = hashlib.sha1(
bytes(
json.dumps((self.type.value, self.year_range, self.genre.name)),
"utf8",
)
).hexdigest()
hash_tuple: Tuple[Any, ...] = (self.type.value,)
if self.type.value == AlbumSearchQuery.Type.YEAR_RANGE:
hash_tuple += (self.year_range,)
elif self.type.value == AlbumSearchQuery.Type.GENRE:
hash_tuple += (self.genre.name,)
self._strhash = hashlib.sha1(bytes(str(hash_tuple), "utf8")).hexdigest()
return self._strhash

View File

@@ -653,7 +653,7 @@ class SublimeMusicApp(Gtk.Application):
self.app_config.state.current_tab = "albums"
self.app_config.state.selected_album_id = album_id.get_string()
self.update_window(force=True)
self.update_window()
def on_go_to_artist(self, action: Any, artist_id: GLib.Variant):
self.app_config.state.current_tab = "artists"

View File

@@ -554,7 +554,7 @@ class AlbumsGrid(Gtk.Overlay):
halign=Gtk.Align.CENTER,
selection_mode=Gtk.SelectionMode.SINGLE,
)
flowbox.set_max_children_per_line(10)
flowbox.set_max_children_per_line(7)
return flowbox
self.grid_top = create_flowbox()
@@ -658,11 +658,9 @@ class AlbumsGrid(Gtk.Overlay):
if self.sort_dir == "descending" and selected_index:
selected_index = len(self.current_models) - selected_index - 1
selection_changed = selected_index != self.currently_selected_index
self.currently_selected_index = selected_index
self.reflow_grids(
force_reload_from_master=force_grid_reload_from_master,
selection_changed=selection_changed,
selected_index=selected_index,
models=self.current_models,
)
self.spinner.hide()
@@ -703,7 +701,10 @@ class AlbumsGrid(Gtk.Overlay):
for c in self.error_container.get_children():
self.error_container.remove(c)
if is_partial and self.current_query.type != AlbumSearchQuery.Type.RANDOM:
if is_partial and (
len(albums) == 0
or self.current_query.type != AlbumSearchQuery.Type.RANDOM
):
load_error = LoadError(
"Album list",
"load albums",
@@ -779,14 +780,17 @@ class AlbumsGrid(Gtk.Overlay):
# add extra padding.
# 200 + (10 * 2) + (5 * 2) = 230
# picture + (padding * 2) + (margin * 2)
new_items_per_row = min((rect.width // 230), 10)
new_items_per_row = min((rect.width // 230), 7)
if new_items_per_row != self.items_per_row:
self.items_per_row = new_items_per_row
self.detail_box_inner.set_size_request(
self.items_per_row * 230 - 10, -1,
)
self.reflow_grids(force_reload_from_master=True)
self.reflow_grids(
force_reload_from_master=True,
selected_index=self.currently_selected_index,
)
# Helper Methods
# =========================================================================
@@ -846,17 +850,18 @@ class AlbumsGrid(Gtk.Overlay):
def reflow_grids(
self,
force_reload_from_master: bool = False,
selection_changed: bool = False,
selected_index: int = None,
models: List[_AlbumModel] = None,
):
# Calculate the page that the currently_selected_index is in. If it's a
# different page, then update the window.
page_changed = False
if self.currently_selected_index is not None:
page_of_selected_index = self.currently_selected_index // self.page_size
if selected_index is not None:
page_of_selected_index = selected_index // self.page_size
if page_of_selected_index != self.page:
page_changed = True
self.page = page_of_selected_index
self.emit(
"refresh-window", {"album_page": page_of_selected_index}, False
)
return
page_offset = self.page_size * self.page
# Calculate the look-at window.
@@ -874,14 +879,14 @@ class AlbumsGrid(Gtk.Overlay):
# Determine where the cuttoff is between the top and bottom grids.
entries_before_fold = self.page_size
if self.currently_selected_index is not None and self.items_per_row:
relative_selected_index = self.currently_selected_index - page_offset
if selected_index is not None and self.items_per_row:
relative_selected_index = selected_index - page_offset
entries_before_fold = (
(relative_selected_index // self.items_per_row) + 1
) * self.items_per_row
# Unreveal the current album details first
if self.currently_selected_index is None:
if selected_index is None:
self.detail_box_revealer.set_reveal_child(False)
if force_reload_from_master:
@@ -893,7 +898,7 @@ class AlbumsGrid(Gtk.Overlay):
self.list_store_bottom.splice(
0, len(self.list_store_bottom), window[entries_before_fold:],
)
elif self.currently_selected_index or entries_before_fold != self.page_size:
elif selected_index or entries_before_fold != self.page_size:
# This case handles when the selection changes and the entries need to be
# re-allocated to the top and bottom grids
# Move entries between the two stores.
@@ -913,14 +918,14 @@ class AlbumsGrid(Gtk.Overlay):
self.list_store_bottom.splice(0, 0, self.list_store_top[-diff:])
self.list_store_top.splice(top_store_len - diff, diff, [])
if self.currently_selected_index is not None:
relative_selected_index = self.currently_selected_index - page_offset
if selected_index is not None:
relative_selected_index = selected_index - page_offset
to_select = self.grid_top.get_child_at_index(relative_selected_index)
if not to_select:
return
self.grid_top.select_child(to_select)
if not selection_changed:
if self.currently_selected_index == selected_index:
return
for c in self.detail_box_inner.get_children():
@@ -944,9 +949,4 @@ class AlbumsGrid(Gtk.Overlay):
self.grid_top.unselect_all()
self.grid_bottom.unselect_all()
# If we had to change the page to select the index, then update the window. It
# should basically be a no-op.
if page_changed:
self.emit(
"refresh-window", {"album_page": self.page}, False,
)
self.currently_selected_index = selected_index

View File

@@ -556,6 +556,9 @@ class PlaylistDetailPanel(Gtk.Overlay):
# and the expensive parts of the second loop are avoided if the IDs haven't
# changed.
song_ids, songs = [], []
if len(self._current_song_ids) != len(playlist.songs):
force = True
for i, c in enumerate(playlist.songs):
if i >= len(self._current_song_ids) or c.id != self._current_song_ids[i]:
force = True