From 308c2ce1f25d695ab357256de6c146a9eb984a65 Mon Sep 17 00:00:00 2001 From: MaFo-28 Date: Sat, 14 Feb 2026 13:59:47 +0100 Subject: [PATCH 1/4] Add TileSizeManager and improve dynamic tile sizing --- .../tempo/ui/adapter/AlbumAdapter.java | 12 ++ .../tempo/ui/adapter/ArtistAdapter.java | 11 ++ .../ui/adapter/ArtistSimilarAdapter.java | 12 ++ .../tempo/ui/adapter/DiscoverSongAdapter.java | 13 ++ .../ui/fragment/AlbumCatalogueFragment.java | 13 +- .../ui/fragment/ArtistCatalogueFragment.java | 11 +- .../tempo/ui/fragment/ArtistPageFragment.java | 12 +- .../ui/fragment/GenreCatalogueFragment.java | 11 +- .../ui/fragment/HomeTabMusicFragment.java | 6 + .../tempo/util/Preferences.kt | 11 +- app/src/main/res/layout/item_home_year.xml | 8 +- .../main/res/layout/item_library_genre.xml | 2 +- app/src/main/res/values-fr/arrays.xml | 16 ++ app/src/main/res/values-fr/strings.xml | 3 +- app/src/main/res/values/arrays.xml | 16 ++ app/src/main/res/values/strings.xml | 1 + app/src/main/res/xml/global_preferences.xml | 18 +- .../tempo/util/TileSizeManager.java | 176 ++++++++++++++++++ 18 files changed, 316 insertions(+), 36 deletions(-) create mode 100644 app/src/tempus/java/com/cappielloantonio/tempo/util/TileSizeManager.java diff --git a/app/src/main/java/com/cappielloantonio/tempo/ui/adapter/AlbumAdapter.java b/app/src/main/java/com/cappielloantonio/tempo/ui/adapter/AlbumAdapter.java index 498bf2378..d6e417460 100644 --- a/app/src/main/java/com/cappielloantonio/tempo/ui/adapter/AlbumAdapter.java +++ b/app/src/main/java/com/cappielloantonio/tempo/ui/adapter/AlbumAdapter.java @@ -13,6 +13,7 @@ import com.cappielloantonio.tempo.subsonic.models.AlbumID3; import com.cappielloantonio.tempo.util.Constants; import com.cappielloantonio.tempo.util.MusicUtil; +import com.cappielloantonio.tempo.util.TileSizeManager; import java.util.Collections; import java.util.List; @@ -22,6 +23,8 @@ public class AlbumAdapter extends RecyclerView.Adapter private List albums; + private int sizePx = 400; + public AlbumAdapter(ClickCallback click) { this.click = click; this.albums = Collections.emptyList(); @@ -31,11 +34,20 @@ public AlbumAdapter(ClickCallback click) { @Override public ViewHolder onCreateViewHolder(@NonNull ViewGroup parent, int viewType) { ItemLibraryAlbumBinding view = ItemLibraryAlbumBinding.inflate(LayoutInflater.from(parent.getContext()), parent, false); + + TileSizeManager.getInstance().calculateTileSize(parent.getContext()); + sizePx = TileSizeManager.getInstance().getTileSizePx(parent.getContext()); + return new ViewHolder(view); } @Override public void onBindViewHolder(ViewHolder holder, int position) { + ViewGroup.LayoutParams lp = holder.item.albumCoverImageView.getLayoutParams(); + lp.width = sizePx; + lp.height = sizePx; + holder.item.albumCoverImageView.setLayoutParams(lp); + AlbumID3 album = albums.get(position); holder.item.albumNameLabel.setText(album.getName()); diff --git a/app/src/main/java/com/cappielloantonio/tempo/ui/adapter/ArtistAdapter.java b/app/src/main/java/com/cappielloantonio/tempo/ui/adapter/ArtistAdapter.java index 44e8402c0..29bd773fd 100644 --- a/app/src/main/java/com/cappielloantonio/tempo/ui/adapter/ArtistAdapter.java +++ b/app/src/main/java/com/cappielloantonio/tempo/ui/adapter/ArtistAdapter.java @@ -14,6 +14,7 @@ import com.cappielloantonio.tempo.subsonic.models.ArtistID3; import com.cappielloantonio.tempo.util.Constants; import com.cappielloantonio.tempo.util.MusicUtil; +import com.cappielloantonio.tempo.util.TileSizeManager; import java.util.Collections; import java.util.List; @@ -24,6 +25,7 @@ public class ArtistAdapter extends RecyclerView.Adapter artists; public ArtistAdapter(ClickCallback click, Boolean mix, Boolean bestOf) { @@ -37,11 +39,20 @@ public ArtistAdapter(ClickCallback click, Boolean mix, Boolean bestOf) { @Override public ViewHolder onCreateViewHolder(@NonNull ViewGroup parent, int viewType) { ItemLibraryArtistBinding view = ItemLibraryArtistBinding.inflate(LayoutInflater.from(parent.getContext()), parent, false); + + TileSizeManager.getInstance().calculateTileSize(parent.getContext()); + sizePx = TileSizeManager.getInstance().getTileSizePx(parent.getContext()); + return new ViewHolder(view); } @Override public void onBindViewHolder(ViewHolder holder, int position) { + ViewGroup.LayoutParams lp = holder.item.artistCoverImageView.getLayoutParams(); + lp.width = sizePx; + lp.height = sizePx; + holder.item.artistCoverImageView.setLayoutParams(lp); + ArtistID3 artist = artists.get(position); holder.item.artistNameLabel.setText(artist.getName()); diff --git a/app/src/main/java/com/cappielloantonio/tempo/ui/adapter/ArtistSimilarAdapter.java b/app/src/main/java/com/cappielloantonio/tempo/ui/adapter/ArtistSimilarAdapter.java index 4e8dffe53..8596b5992 100644 --- a/app/src/main/java/com/cappielloantonio/tempo/ui/adapter/ArtistSimilarAdapter.java +++ b/app/src/main/java/com/cappielloantonio/tempo/ui/adapter/ArtistSimilarAdapter.java @@ -13,6 +13,7 @@ import com.cappielloantonio.tempo.subsonic.models.SimilarArtistID3; import com.cappielloantonio.tempo.util.Constants; import com.cappielloantonio.tempo.util.MusicUtil; +import com.cappielloantonio.tempo.util.TileSizeManager; import java.util.Collections; import java.util.List; @@ -22,6 +23,8 @@ public class ArtistSimilarAdapter extends RecyclerView.Adapter artists; + private int sizePx = 400; + public ArtistSimilarAdapter(ClickCallback click) { this.click = click; this.artists = Collections.emptyList(); @@ -31,11 +34,20 @@ public ArtistSimilarAdapter(ClickCallback click) { @Override public ViewHolder onCreateViewHolder(@NonNull ViewGroup parent, int viewType) { ItemLibrarySimilarArtistBinding view = ItemLibrarySimilarArtistBinding.inflate(LayoutInflater.from(parent.getContext()), parent, false); + + TileSizeManager.getInstance().calculateTileSize(parent.getContext()); + sizePx = TileSizeManager.getInstance().getTileSizePx(parent.getContext()); + return new ViewHolder(view); } @Override public void onBindViewHolder(ViewHolder holder, int position) { + ViewGroup.LayoutParams lp = holder.item.similarArtistCoverImageView.getLayoutParams(); + lp.width = sizePx; + lp.height = sizePx; + holder.item.similarArtistCoverImageView.setLayoutParams(lp); + SimilarArtistID3 artist = artists.get(position); holder.item.artistNameLabel.setText(artist.getName()); diff --git a/app/src/main/java/com/cappielloantonio/tempo/ui/adapter/DiscoverSongAdapter.java b/app/src/main/java/com/cappielloantonio/tempo/ui/adapter/DiscoverSongAdapter.java index c9b21d883..120a4f679 100644 --- a/app/src/main/java/com/cappielloantonio/tempo/ui/adapter/DiscoverSongAdapter.java +++ b/app/src/main/java/com/cappielloantonio/tempo/ui/adapter/DiscoverSongAdapter.java @@ -2,6 +2,7 @@ import android.os.Bundle; import android.view.LayoutInflater; +import android.view.View; import android.view.ViewGroup; import android.view.animation.AccelerateDecelerateInterpolator; @@ -14,6 +15,7 @@ import com.cappielloantonio.tempo.subsonic.models.Child; import com.cappielloantonio.tempo.util.Constants; import com.cappielloantonio.tempo.util.MusicUtil; +import com.cappielloantonio.tempo.util.TileSizeManager; import java.util.Collections; import java.util.List; @@ -32,6 +34,17 @@ public DiscoverSongAdapter(ClickCallback click) { @Override public ViewHolder onCreateViewHolder(@NonNull ViewGroup parent, int viewType) { ItemHomeDiscoverSongBinding view = ItemHomeDiscoverSongBinding.inflate(LayoutInflater.from(parent.getContext()), parent, false); + + TileSizeManager.getInstance().calculateDiscoverSize(parent.getContext()); + View root = view.getRoot(); + root.post(() -> { + ViewGroup.LayoutParams lp = root.getLayoutParams(); + if (lp != null) { + lp.width = TileSizeManager.getInstance().getDiscoverWidthPx(parent.getContext());; + root.setLayoutParams(lp); + } + }); + return new ViewHolder(view); } diff --git a/app/src/main/java/com/cappielloantonio/tempo/ui/fragment/AlbumCatalogueFragment.java b/app/src/main/java/com/cappielloantonio/tempo/ui/fragment/AlbumCatalogueFragment.java index 08c5b8fe5..e4e95c5f0 100644 --- a/app/src/main/java/com/cappielloantonio/tempo/ui/fragment/AlbumCatalogueFragment.java +++ b/app/src/main/java/com/cappielloantonio/tempo/ui/fragment/AlbumCatalogueFragment.java @@ -35,6 +35,7 @@ import com.cappielloantonio.tempo.ui.adapter.AlbumCatalogueAdapter; import com.cappielloantonio.tempo.util.Constants; import com.cappielloantonio.tempo.util.Preferences; +import com.cappielloantonio.tempo.util.TileSizeManager; import com.cappielloantonio.tempo.viewmodel.AlbumCatalogueViewModel; import java.util.ArrayList; @@ -48,9 +49,9 @@ public class AlbumCatalogueFragment extends Fragment implements ClickCallback { private FragmentAlbumCatalogueBinding bind; private MainActivity activity; private AlbumCatalogueViewModel albumCatalogueViewModel; - - private AlbumCatalogueAdapter albumAdapter; private int spanCount = 2; + private int tileSpacing = 20; + private AlbumCatalogueAdapter albumAdapter; private String currentSortOrder; private List originalAlbums; @@ -92,9 +93,9 @@ public View onCreateView(@NonNull LayoutInflater inflater, ViewGroup container, bind = FragmentAlbumCatalogueBinding.inflate(inflater, container, false); View view = bind.getRoot(); - if (getResources().getConfiguration().orientation == Configuration.ORIENTATION_LANDSCAPE) { - spanCount = Preferences.getLandscapeItemsPerRow(); - } + TileSizeManager.getInstance().calculateTileSize( requireContext() ); + spanCount = TileSizeManager.getInstance().getTileSpanCount( requireContext() ); + tileSpacing = TileSizeManager.getInstance().getTileSpacing( requireContext() ); initAppBar(); initAlbumCatalogueView(); @@ -140,7 +141,7 @@ private void initAppBar() { @SuppressLint("ClickableViewAccessibility") private void initAlbumCatalogueView() { bind.albumCatalogueRecyclerView.setLayoutManager(new GridLayoutManager(requireContext(), spanCount)); - bind.albumCatalogueRecyclerView.addItemDecoration(new GridItemDecoration(spanCount, 20, false)); + bind.albumCatalogueRecyclerView.addItemDecoration(new GridItemDecoration(spanCount, tileSpacing, false)); bind.albumCatalogueRecyclerView.setHasFixedSize(true); albumAdapter = new AlbumCatalogueAdapter(this, true); diff --git a/app/src/main/java/com/cappielloantonio/tempo/ui/fragment/ArtistCatalogueFragment.java b/app/src/main/java/com/cappielloantonio/tempo/ui/fragment/ArtistCatalogueFragment.java index 5a2aa1ee1..0df3b4323 100644 --- a/app/src/main/java/com/cappielloantonio/tempo/ui/fragment/ArtistCatalogueFragment.java +++ b/app/src/main/java/com/cappielloantonio/tempo/ui/fragment/ArtistCatalogueFragment.java @@ -36,6 +36,7 @@ import com.cappielloantonio.tempo.ui.adapter.ArtistCatalogueAdapter; import com.cappielloantonio.tempo.util.Constants; import com.cappielloantonio.tempo.util.Preferences; +import com.cappielloantonio.tempo.util.TileSizeManager; import com.cappielloantonio.tempo.viewmodel.ArtistCatalogueViewModel; import com.cappielloantonio.tempo.subsonic.models.ArtistID3; @@ -51,7 +52,9 @@ public class ArtistCatalogueFragment extends Fragment implements ClickCallback { private ArtistCatalogueViewModel artistCatalogueViewModel; private ArtistCatalogueAdapter artistAdapter; + private int spanCount = 2; + private int tileSpacing = 20; @Override public void onCreate(@Nullable Bundle savedInstanceState) { @@ -68,9 +71,9 @@ public View onCreateView(@NonNull LayoutInflater inflater, ViewGroup container, bind = FragmentArtistCatalogueBinding.inflate(inflater, container, false); View view = bind.getRoot(); - if (getResources().getConfiguration().orientation == Configuration.ORIENTATION_LANDSCAPE) { - spanCount = Preferences.getLandscapeItemsPerRow(); - } + TileSizeManager.getInstance().calculateTileSize( requireContext() ); + spanCount = TileSizeManager.getInstance().getTileSpanCount( requireContext() ); + tileSpacing = TileSizeManager.getInstance().getTileSpacing( requireContext() ); initAppBar(); initArtistCatalogueView(); @@ -115,7 +118,7 @@ private void initAppBar() { @SuppressLint("ClickableViewAccessibility") private void initArtistCatalogueView() { bind.artistCatalogueRecyclerView.setLayoutManager(new GridLayoutManager(requireContext(), spanCount)); - bind.artistCatalogueRecyclerView.addItemDecoration(new GridItemDecoration(spanCount, 20, false)); + bind.artistCatalogueRecyclerView.addItemDecoration(new GridItemDecoration(spanCount, tileSpacing, false)); bind.artistCatalogueRecyclerView.setHasFixedSize(true); artistAdapter = new ArtistCatalogueAdapter(this); diff --git a/app/src/main/java/com/cappielloantonio/tempo/ui/fragment/ArtistPageFragment.java b/app/src/main/java/com/cappielloantonio/tempo/ui/fragment/ArtistPageFragment.java index e995d209f..74e3a44ef 100644 --- a/app/src/main/java/com/cappielloantonio/tempo/ui/fragment/ArtistPageFragment.java +++ b/app/src/main/java/com/cappielloantonio/tempo/ui/fragment/ArtistPageFragment.java @@ -43,6 +43,7 @@ import com.cappielloantonio.tempo.util.Constants; import com.cappielloantonio.tempo.util.MusicUtil; import com.cappielloantonio.tempo.util.Preferences; +import com.cappielloantonio.tempo.util.TileSizeManager; import com.cappielloantonio.tempo.viewmodel.ArtistPageViewModel; import com.cappielloantonio.tempo.viewmodel.PlaybackViewModel; import com.google.common.util.concurrent.ListenableFuture; @@ -65,6 +66,7 @@ public class ArtistPageFragment extends Fragment implements ClickCallback { private ListenableFuture mediaBrowserListenableFuture; private int spanCount = 2; + private int tileSpacing = 20; @Override public View onCreateView(@NonNull LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) { @@ -75,9 +77,9 @@ public View onCreateView(@NonNull LayoutInflater inflater, ViewGroup container, artistPageViewModel = new ViewModelProvider(requireActivity()).get(ArtistPageViewModel.class); playbackViewModel = new ViewModelProvider(requireActivity()).get(PlaybackViewModel.class); - if (getResources().getConfiguration().orientation == Configuration.ORIENTATION_LANDSCAPE) { - spanCount = Preferences.getLandscapeItemsPerRow(); - } + TileSizeManager.getInstance().calculateTileSize( requireContext() ); + spanCount = TileSizeManager.getInstance().getTileSpanCount( requireContext() ); + tileSpacing = TileSizeManager.getInstance().getTileSpacing( requireContext() ); init(view); initAppBar(); @@ -285,7 +287,7 @@ private void initTopSongsView() { private void initAlbumsView() { bind.albumsRecyclerView.setLayoutManager(new GridLayoutManager(requireContext(), spanCount)); - bind.albumsRecyclerView.addItemDecoration(new GridItemDecoration(spanCount, 20, false)); + bind.albumsRecyclerView.addItemDecoration(new GridItemDecoration(spanCount, tileSpacing, false)); bind.albumsRecyclerView.setHasFixedSize(true); albumCatalogueAdapter = new AlbumCatalogueAdapter(this, false); @@ -304,7 +306,7 @@ private void initAlbumsView() { private void initSimilarArtistsView() { bind.similarArtistsRecyclerView.setLayoutManager(new GridLayoutManager(requireContext(), spanCount)); - bind.similarArtistsRecyclerView.addItemDecoration(new GridItemDecoration(spanCount, 20, false)); + bind.similarArtistsRecyclerView.addItemDecoration(new GridItemDecoration(spanCount, tileSpacing, false)); bind.similarArtistsRecyclerView.setHasFixedSize(true); artistCatalogueAdapter = new ArtistCatalogueAdapter(this); diff --git a/app/src/main/java/com/cappielloantonio/tempo/ui/fragment/GenreCatalogueFragment.java b/app/src/main/java/com/cappielloantonio/tempo/ui/fragment/GenreCatalogueFragment.java index 52e8b825d..f421878c5 100644 --- a/app/src/main/java/com/cappielloantonio/tempo/ui/fragment/GenreCatalogueFragment.java +++ b/app/src/main/java/com/cappielloantonio/tempo/ui/fragment/GenreCatalogueFragment.java @@ -34,6 +34,7 @@ import com.cappielloantonio.tempo.ui.adapter.GenreCatalogueAdapter; import com.cappielloantonio.tempo.util.Constants; import com.cappielloantonio.tempo.util.Preferences; +import com.cappielloantonio.tempo.util.TileSizeManager; import com.cappielloantonio.tempo.viewmodel.GenreCatalogueViewModel; @OptIn(markerClass = UnstableApi.class) @@ -43,7 +44,9 @@ public class GenreCatalogueFragment extends Fragment implements ClickCallback { private GenreCatalogueViewModel genreCatalogueViewModel; private GenreCatalogueAdapter genreCatalogueAdapter; + private int spanCount = 2; + private int tileSpacing = 20; @Override public void onCreate(@Nullable Bundle savedInstanceState) { @@ -59,9 +62,9 @@ public View onCreateView(@NonNull LayoutInflater inflater, ViewGroup container, View view = bind.getRoot(); genreCatalogueViewModel = new ViewModelProvider(requireActivity()).get(GenreCatalogueViewModel.class); - if (getResources().getConfiguration().orientation == Configuration.ORIENTATION_LANDSCAPE) { - spanCount = Preferences.getLandscapeItemsPerRow(); - } + TileSizeManager.getInstance().calculateGenreSize( requireContext() ); + spanCount = TileSizeManager.getInstance().getGenreSpanCount( requireContext() ); + tileSpacing = TileSizeManager.getInstance().getGenreSpacing( requireContext() ); init(); initAppBar(); @@ -105,7 +108,7 @@ private void initAppBar() { @SuppressLint("ClickableViewAccessibility") private void initGenreCatalogueView() { bind.genreCatalogueRecyclerView.setLayoutManager(new GridLayoutManager(requireContext(), spanCount)); - bind.genreCatalogueRecyclerView.addItemDecoration(new GridItemDecoration(spanCount, 16, false)); + bind.genreCatalogueRecyclerView.addItemDecoration(new GridItemDecoration(spanCount, tileSpacing, false)); bind.genreCatalogueRecyclerView.setHasFixedSize(true); genreCatalogueAdapter = new GenreCatalogueAdapter(this); diff --git a/app/src/main/java/com/cappielloantonio/tempo/ui/fragment/HomeTabMusicFragment.java b/app/src/main/java/com/cappielloantonio/tempo/ui/fragment/HomeTabMusicFragment.java index b2bc5ee3a..d8626c45b 100644 --- a/app/src/main/java/com/cappielloantonio/tempo/ui/fragment/HomeTabMusicFragment.java +++ b/app/src/main/java/com/cappielloantonio/tempo/ui/fragment/HomeTabMusicFragment.java @@ -64,6 +64,7 @@ import com.cappielloantonio.tempo.util.MappingUtil; import com.cappielloantonio.tempo.util.MusicUtil; import com.cappielloantonio.tempo.util.Preferences; +import com.cappielloantonio.tempo.util.TileSizeManager; import com.cappielloantonio.tempo.util.UIUtil; import com.cappielloantonio.tempo.viewmodel.HomeViewModel; import com.cappielloantonio.tempo.viewmodel.PlaybackViewModel; @@ -684,6 +685,11 @@ private void initDiscoverSongSlideView() { bind.discoverSongViewPager.setOrientation(ViewPager2.ORIENTATION_HORIZONTAL); + TileSizeManager.getInstance().calculateDiscoverSize(requireContext()); + ViewGroup.LayoutParams lp = bind.discoverSongViewPager.getLayoutParams(); + lp.height = TileSizeManager.getInstance().getDiscoverHeightPx(requireContext()); + bind.discoverSongViewPager.setLayoutParams(lp); + discoverSongAdapter = new DiscoverSongAdapter(this); bind.discoverSongViewPager.setAdapter(discoverSongAdapter); bind.discoverSongViewPager.setOffscreenPageLimit(1); diff --git a/app/src/main/java/com/cappielloantonio/tempo/util/Preferences.kt b/app/src/main/java/com/cappielloantonio/tempo/util/Preferences.kt index a95c84ae1..a1857d658 100644 --- a/app/src/main/java/com/cappielloantonio/tempo/util/Preferences.kt +++ b/app/src/main/java/com/cappielloantonio/tempo/util/Preferences.kt @@ -88,8 +88,9 @@ object Preferences { private const val ARTIST_DISPLAY_BIOGRAPHY= "artist_display_biography" private const val NETWORK_PING_TIMEOUT = "network_ping_timeout_base" - - @JvmStatic + private const val TILE_SIZE = "tile_size" + + @JvmStatic fun getServer(): String? { return App.getInstance().preferences.getString(SERVER, null) } @@ -724,4 +725,10 @@ object Preferences { fun setArtistDisplayBiography(displayBiographyEnabled: Boolean) { App.getInstance().preferences.edit().putBoolean(ARTIST_DISPLAY_BIOGRAPHY, displayBiographyEnabled).apply() } + + @JvmStatic + fun getTileSize(): Int { + return App.getInstance().preferences.getString(TILE_SIZE, "2")!!.toInt() + } + } \ No newline at end of file diff --git a/app/src/main/res/layout/item_home_year.xml b/app/src/main/res/layout/item_home_year.xml index 702c10745..bbc5c7219 100644 --- a/app/src/main/res/layout/item_home_year.xml +++ b/app/src/main/res/layout/item_home_year.xml @@ -4,13 +4,13 @@ android:layout_width="wrap_content" android:layout_height="wrap_content" android:orientation="vertical" - android:paddingEnd="12dp" - android:paddingBottom="8dp"> + android:paddingEnd="8dp" + android:paddingBottom="4dp"> 3 4 + + + Très petite + Petite + Moyenne + Large + Très Large + + + 6 + 5 + 4 + 3 + 2 + + diff --git a/app/src/main/res/values-fr/strings.xml b/app/src/main/res/values-fr/strings.xml index dd9e51a44..f26139014 100644 --- a/app/src/main/res/values-fr/strings.xml +++ b/app/src/main/res/values-fr/strings.xml @@ -404,6 +404,7 @@ Si activé, les pistes favorites seront téléchargées pour l\'écoute hors-ligne. Synchronisation des pistes favorites pour écoute hors-ligne Thème + Taille des vignettes Données Géneral Playlist @@ -463,7 +464,7 @@ Téléchargé Titres les plus joués Titres ajoutés récemment - Titrés joués récemment + Titres joués récemment Titres favoris Les meilleurs titres de %1$s Année %1$d diff --git a/app/src/main/res/values/arrays.xml b/app/src/main/res/values/arrays.xml index 49aef94e2..dd80e9877 100644 --- a/app/src/main/res/values/arrays.xml +++ b/app/src/main/res/values/arrays.xml @@ -278,4 +278,20 @@ 6 7 + + + Xtra Small + Small + Medium + Large + Xtra Large + + + 6 + 5 + 4 + 3 + 2 + + \ No newline at end of file diff --git a/app/src/main/res/values/strings.xml b/app/src/main/res/values/strings.xml index 88c11fb77..13295f136 100644 --- a/app/src/main/res/values/strings.xml +++ b/app/src/main/res/values/strings.xml @@ -413,6 +413,7 @@ If enabled, starred tracks will be downloaded for offline use. Sync starred tracks for offline use Theme + Tiles size Data General Playlist diff --git a/app/src/main/res/xml/global_preferences.xml b/app/src/main/res/xml/global_preferences.xml index 4ee034e53..9d339bb5a 100644 --- a/app/src/main/res/xml/global_preferences.xml +++ b/app/src/main/res/xml/global_preferences.xml @@ -54,6 +54,15 @@ android:defaultValue="false" android:key="always_on_display" /> + + - - diff --git a/app/src/tempus/java/com/cappielloantonio/tempo/util/TileSizeManager.java b/app/src/tempus/java/com/cappielloantonio/tempo/util/TileSizeManager.java new file mode 100644 index 000000000..1f4153192 --- /dev/null +++ b/app/src/tempus/java/com/cappielloantonio/tempo/util/TileSizeManager.java @@ -0,0 +1,176 @@ +package com.cappielloantonio.tempo.util; + +import android.content.Context; +import android.util.DisplayMetrics; + +public class TileSizeManager { + + private static TileSizeManager instance; + + private int tileSizePx; + private int tileSpanCount; + private int tileSpacing; + private int genreSizePx; + private int genreSpanCount; + private int genreSpacing; + private int GenreSpacing; + private int discoverWidthPx; + private int discoverHeightPx; + private boolean tileIsInitialized; + private boolean genreIsInitialized; + private boolean discoverIsInitialized; + + private TileSizeManager() { + } + + public static TileSizeManager getInstance() { + if (instance == null) { + instance = new TileSizeManager(); + } + return instance; + } + + public int getTileSizePx(Context context) { + if( !tileIsInitialized ) + calculateTileSize(context); + return tileSizePx; + } + public int getTileSpanCount(Context context) { + if( !tileIsInitialized ) + calculateTileSize(context); + return tileSpanCount; + } + public int getTileSpacing(Context context) { + if( !tileIsInitialized ) + calculateTileSize(context); + return tileSpacing; + } + public int getGenreSizePx(Context context) { + if( !genreIsInitialized ) + calculateGenreSize(context); + return genreSizePx; + } + public int getGenreSpanCount(Context context) { + if( !genreIsInitialized ) + calculateGenreSize(context); + return genreSpanCount; + } + public int getGenreSpacing(Context context) { + if( !genreIsInitialized ) + calculateGenreSize(context); + return genreSpacing; + } + public int getDiscoverWidthPx(Context context) { + if( !discoverIsInitialized ) + calculateTileSize(context); + return discoverWidthPx; + } + public int getDiscoverHeightPx(Context context) { + if( !discoverIsInitialized ) + calculateTileSize(context); + return discoverHeightPx; + } + + public void calculateTileSize(Context context) { + DisplayMetrics metrics = context.getResources().getDisplayMetrics(); + float screenWidth = metrics.widthPixels; + float screenHeight = metrics.heightPixels; + + // retrieve the divisor in the preferences + int userTileSize = Preferences.getTileSize(); + float divisor = (float)userTileSize; + + // little pading = 10 + tileSizePx = Math.round(Math.min(screenWidth, screenHeight) / divisor) - 10; + tileSpanCount = Math.max(2, Math.round(screenWidth / (float)tileSizePx) ); + + switch (userTileSize) { + default: + case 2: // XL + tileSpacing = 20; + break; + case 3: // L + tileSpacing = 15; + break; + case 4: // M + tileSpacing = 10; + break; + case 5: // S + tileSpacing = 6; + break; + case 6: // SX + tileSpacing = 2; + break; + } + tileIsInitialized = true; + } + + public void calculateGenreSize(Context context) { + DisplayMetrics metrics = context.getResources().getDisplayMetrics(); + float screenWidth = metrics.widthPixels; + float screenHeight = metrics.heightPixels; + + // retrieve the divisor in the preferences + int userTileSize = Preferences.getTileSize(); + if(userTileSize>3) + userTileSize=3; + float divisor = (float)userTileSize; + + // little pading = 10 + genreSizePx = Math.round(Math.min(screenWidth, screenHeight) / divisor) - 10; + genreSpanCount = Math.max(2, Math.round(screenWidth / (float)genreSizePx) ); + + switch (userTileSize) { + default: + case 2: // XL + genreSpacing = 20; + break; + case 3: // L + genreSpacing = 15; + break; + case 4: // M + genreSpacing = 10; + break; + case 5: // S + genreSpacing = 6; + break; + case 6: // XS + genreSpacing = 2; + break; + } + genreIsInitialized = true; + } + + public void calculateDiscoverSize(Context context) { + DisplayMetrics metrics = context.getResources().getDisplayMetrics(); + float screenWidth = metrics.widthPixels; + float screenHeight = metrics.heightPixels; + float discoverDivisor; + + // retrieve the divisor in the preferences + int userTileSize = Preferences.getTileSize(); + + switch (userTileSize) { + default: + case 2: // XL + discoverDivisor = 1.0f; + break; + case 3: // L + discoverDivisor = 1.25f; + break; + case 4: // M + discoverDivisor = 1.5f; + break; + case 5: // S + discoverDivisor = 1.75f; + break; + case 6: // XS + discoverDivisor = 2.0f; + break; + } + + discoverWidthPx = Math.round(Math.min(screenWidth, screenHeight) / discoverDivisor); + discoverHeightPx = Math.round((float)discoverWidthPx * 0.6f); + discoverIsInitialized = true; + } +} From bea399ad30014f6c9676f2edd6822d8f62e521bf Mon Sep 17 00:00:00 2001 From: MaFo-28 Date: Sat, 14 Feb 2026 18:44:19 +0100 Subject: [PATCH 2/4] Improve scale labels --- app/src/main/res/values-fr/arrays.xml | 4 ++-- app/src/main/res/values/arrays.xml | 4 ++-- 2 files changed, 4 insertions(+), 4 deletions(-) diff --git a/app/src/main/res/values-fr/arrays.xml b/app/src/main/res/values-fr/arrays.xml index 2f7c4de27..27ff3ee29 100644 --- a/app/src/main/res/values-fr/arrays.xml +++ b/app/src/main/res/values-fr/arrays.xml @@ -256,11 +256,11 @@ - Très petite + Minuscule Petite Moyenne Large - Très Large + Défaut 6 diff --git a/app/src/main/res/values/arrays.xml b/app/src/main/res/values/arrays.xml index dd80e9877..c9f11f9fc 100644 --- a/app/src/main/res/values/arrays.xml +++ b/app/src/main/res/values/arrays.xml @@ -280,11 +280,11 @@ - Xtra Small + Tiny Small Medium Large - Xtra Large + Default 6 From c9179c98f083539cd117dfab6e5821f8af80eacd Mon Sep 17 00:00:00 2001 From: MaFo-28 Date: Sat, 14 Feb 2026 20:34:32 +0100 Subject: [PATCH 3/4] Add protection against invalid tile size preferences --- .../java/com/cappielloantonio/tempo/util/Preferences.kt | 7 ++++--- .../com/cappielloantonio/tempo/util/TileSizeManager.java | 8 +++----- 2 files changed, 7 insertions(+), 8 deletions(-) diff --git a/app/src/main/java/com/cappielloantonio/tempo/util/Preferences.kt b/app/src/main/java/com/cappielloantonio/tempo/util/Preferences.kt index a1857d658..82d17cb5b 100644 --- a/app/src/main/java/com/cappielloantonio/tempo/util/Preferences.kt +++ b/app/src/main/java/com/cappielloantonio/tempo/util/Preferences.kt @@ -725,10 +725,11 @@ object Preferences { fun setArtistDisplayBiography(displayBiographyEnabled: Boolean) { App.getInstance().preferences.edit().putBoolean(ARTIST_DISPLAY_BIOGRAPHY, displayBiographyEnabled).apply() } - + @JvmStatic fun getTileSize(): Int { - return App.getInstance().preferences.getString(TILE_SIZE, "2")!!.toInt() + val parsed = App.getInstance().preferences.getString(TILE_SIZE, "2")?.toIntOrNull() + return parsed?.takeIf { it in 2..6 } ?: 2 + //return App.getInstance().preferences.getString(TILE_SIZE, "2")!!.toInt() } - } \ No newline at end of file diff --git a/app/src/tempus/java/com/cappielloantonio/tempo/util/TileSizeManager.java b/app/src/tempus/java/com/cappielloantonio/tempo/util/TileSizeManager.java index 1f4153192..fe03f6dfc 100644 --- a/app/src/tempus/java/com/cappielloantonio/tempo/util/TileSizeManager.java +++ b/app/src/tempus/java/com/cappielloantonio/tempo/util/TileSizeManager.java @@ -77,7 +77,7 @@ public void calculateTileSize(Context context) { float screenHeight = metrics.heightPixels; // retrieve the divisor in the preferences - int userTileSize = Preferences.getTileSize(); + int userTileSize = Math.max(2, Math.min(6, Preferences.getTileSize())); float divisor = (float)userTileSize; // little pading = 10 @@ -111,9 +111,7 @@ public void calculateGenreSize(Context context) { float screenHeight = metrics.heightPixels; // retrieve the divisor in the preferences - int userTileSize = Preferences.getTileSize(); - if(userTileSize>3) - userTileSize=3; + int userTileSize = Math.max(2, Math.min(3, Preferences.getTileSize())); float divisor = (float)userTileSize; // little pading = 10 @@ -148,7 +146,7 @@ public void calculateDiscoverSize(Context context) { float discoverDivisor; // retrieve the divisor in the preferences - int userTileSize = Preferences.getTileSize(); + int userTileSize = Math.max(2, Math.min(6, Preferences.getTileSize())); switch (userTileSize) { default: From 1c7dc8a2d8e3cc47153eebcda04d5420a73c65dd Mon Sep 17 00:00:00 2001 From: MaFo-28 Date: Sun, 15 Feb 2026 16:42:49 +0100 Subject: [PATCH 4/4] Fix DiscoverSongAdapter & move TileSizeManager --- .../tempo/ui/adapter/DiscoverSongAdapter.java | 18 +++++---- .../ui/fragment/HomeTabMusicFragment.java | 14 ++----- .../tempo/util/Preferences.kt | 1 - .../tempo/util/TileSizeManager.java | 2 +- .../res/layout/fragment_home_tab_music.xml | 8 ++-- app/src/main/res/layout/fragment_library.xml | 1 - .../res/layout/item_home_discover_song.xml | 39 +++++++++++-------- 7 files changed, 41 insertions(+), 42 deletions(-) rename app/src/{tempus => main}/java/com/cappielloantonio/tempo/util/TileSizeManager.java (99%) diff --git a/app/src/main/java/com/cappielloantonio/tempo/ui/adapter/DiscoverSongAdapter.java b/app/src/main/java/com/cappielloantonio/tempo/ui/adapter/DiscoverSongAdapter.java index 120a4f679..c30ddd6b0 100644 --- a/app/src/main/java/com/cappielloantonio/tempo/ui/adapter/DiscoverSongAdapter.java +++ b/app/src/main/java/com/cappielloantonio/tempo/ui/adapter/DiscoverSongAdapter.java @@ -25,6 +25,9 @@ public class DiscoverSongAdapter extends RecyclerView.Adapter songs; + private int widthPx = 800; + private int heightPx = 400; + public DiscoverSongAdapter(ClickCallback click) { this.click = click; this.songs = Collections.emptyList(); @@ -36,20 +39,19 @@ public ViewHolder onCreateViewHolder(@NonNull ViewGroup parent, int viewType) { ItemHomeDiscoverSongBinding view = ItemHomeDiscoverSongBinding.inflate(LayoutInflater.from(parent.getContext()), parent, false); TileSizeManager.getInstance().calculateDiscoverSize(parent.getContext()); - View root = view.getRoot(); - root.post(() -> { - ViewGroup.LayoutParams lp = root.getLayoutParams(); - if (lp != null) { - lp.width = TileSizeManager.getInstance().getDiscoverWidthPx(parent.getContext());; - root.setLayoutParams(lp); - } - }); + widthPx = TileSizeManager.getInstance().getDiscoverWidthPx(parent.getContext());; + heightPx = TileSizeManager.getInstance().getDiscoverHeightPx(parent.getContext());; return new ViewHolder(view); } @Override public void onBindViewHolder(ViewHolder holder, int position) { + ViewGroup.LayoutParams lp = holder.item.discoverSongCoverImageView.getLayoutParams(); + lp.width = widthPx; + lp.height = heightPx; + holder.item.discoverSongCoverImageView.setLayoutParams(lp); + Child song = songs.get(position); holder.item.titleDiscoverSongLabel.setText(song.getTitle()); diff --git a/app/src/main/java/com/cappielloantonio/tempo/ui/fragment/HomeTabMusicFragment.java b/app/src/main/java/com/cappielloantonio/tempo/ui/fragment/HomeTabMusicFragment.java index d8626c45b..e745cdf4b 100644 --- a/app/src/main/java/com/cappielloantonio/tempo/ui/fragment/HomeTabMusicFragment.java +++ b/app/src/main/java/com/cappielloantonio/tempo/ui/fragment/HomeTabMusicFragment.java @@ -683,16 +683,12 @@ public void onChanged(List allSongs) { private void initDiscoverSongSlideView() { if (homeViewModel.checkHomeSectorVisibility(Constants.HOME_SECTOR_DISCOVERY)) return; - bind.discoverSongViewPager.setOrientation(ViewPager2.ORIENTATION_HORIZONTAL); - - TileSizeManager.getInstance().calculateDiscoverSize(requireContext()); - ViewGroup.LayoutParams lp = bind.discoverSongViewPager.getLayoutParams(); - lp.height = TileSizeManager.getInstance().getDiscoverHeightPx(requireContext()); - bind.discoverSongViewPager.setLayoutParams(lp); + bind.discoverSongRecyclerView.setLayoutManager(new LinearLayoutManager(requireContext(), LinearLayoutManager.HORIZONTAL, false)); + bind.discoverSongRecyclerView.setHasFixedSize(true); discoverSongAdapter = new DiscoverSongAdapter(this); - bind.discoverSongViewPager.setAdapter(discoverSongAdapter); - bind.discoverSongViewPager.setOffscreenPageLimit(1); + bind.discoverSongRecyclerView.setAdapter(discoverSongAdapter); + homeViewModel.getDiscoverSongSample(getViewLifecycleOwner()).observe(getViewLifecycleOwner(), songs -> { MusicUtil.ratingFilter(songs); @@ -705,8 +701,6 @@ private void initDiscoverSongSlideView() { discoverSongAdapter.setItems(songs); } }); - - setSlideViewOffset(bind.discoverSongViewPager, 20, 16); } private void initSimilarSongView() { diff --git a/app/src/main/java/com/cappielloantonio/tempo/util/Preferences.kt b/app/src/main/java/com/cappielloantonio/tempo/util/Preferences.kt index 82d17cb5b..fcbf32744 100644 --- a/app/src/main/java/com/cappielloantonio/tempo/util/Preferences.kt +++ b/app/src/main/java/com/cappielloantonio/tempo/util/Preferences.kt @@ -730,6 +730,5 @@ object Preferences { fun getTileSize(): Int { val parsed = App.getInstance().preferences.getString(TILE_SIZE, "2")?.toIntOrNull() return parsed?.takeIf { it in 2..6 } ?: 2 - //return App.getInstance().preferences.getString(TILE_SIZE, "2")!!.toInt() } } \ No newline at end of file diff --git a/app/src/tempus/java/com/cappielloantonio/tempo/util/TileSizeManager.java b/app/src/main/java/com/cappielloantonio/tempo/util/TileSizeManager.java similarity index 99% rename from app/src/tempus/java/com/cappielloantonio/tempo/util/TileSizeManager.java rename to app/src/main/java/com/cappielloantonio/tempo/util/TileSizeManager.java index fe03f6dfc..a7ee7745c 100644 --- a/app/src/tempus/java/com/cappielloantonio/tempo/util/TileSizeManager.java +++ b/app/src/main/java/com/cappielloantonio/tempo/util/TileSizeManager.java @@ -167,7 +167,7 @@ public void calculateDiscoverSize(Context context) { break; } - discoverWidthPx = Math.round(Math.min(screenWidth, screenHeight) / discoverDivisor); + discoverWidthPx = Math.round(Math.min(screenWidth, screenHeight) / discoverDivisor) - 50; discoverHeightPx = Math.round((float)discoverWidthPx * 0.6f); discoverIsInitialized = true; } diff --git a/app/src/main/res/layout/fragment_home_tab_music.xml b/app/src/main/res/layout/fragment_home_tab_music.xml index e698b31c5..88cb21435 100644 --- a/app/src/main/res/layout/fragment_home_tab_music.xml +++ b/app/src/main/res/layout/fragment_home_tab_music.xml @@ -330,13 +330,13 @@ - + android:paddingBottom="8dp" /> diff --git a/app/src/main/res/layout/fragment_library.xml b/app/src/main/res/layout/fragment_library.xml index c96fadaf3..d8240c48e 100644 --- a/app/src/main/res/layout/fragment_library.xml +++ b/app/src/main/res/layout/fragment_library.xml @@ -30,7 +30,6 @@ android:layout_width="match_parent" android:layout_height="wrap_content" android:orientation="vertical" - android:paddingBottom="8dp" android:visibility="gone" tools:visibility="visible"> diff --git a/app/src/main/res/layout/item_home_discover_song.xml b/app/src/main/res/layout/item_home_discover_song.xml index 6e4ccee2e..a3df84d76 100644 --- a/app/src/main/res/layout/item_home_discover_song.xml +++ b/app/src/main/res/layout/item_home_discover_song.xml @@ -1,13 +1,14 @@ - + - \ No newline at end of file + \ No newline at end of file