Merge pull request #22 from jaime-grj/samplerate-bitdepth

feat: show sampling rate and bit depth if available
This commit is contained in:
eddyizm 2025-08-06 18:50:33 -07:00 committed by GitHub
commit ab0e58b506
No known key found for this signature in database
GPG key ID: B5690EEEBB952194
11 changed files with 93 additions and 3 deletions

View file

@ -28,9 +28,9 @@ import com.cappielloantonio.tempo.subsonic.models.Playlist;
@UnstableApi @UnstableApi
@Database( @Database(
version = 10, version = 11,
entities = {Queue.class, Server.class, RecentSearch.class, Download.class, Chronology.class, Favorite.class, SessionMediaItem.class, Playlist.class}, entities = {Queue.class, Server.class, RecentSearch.class, Download.class, Chronology.class, Favorite.class, SessionMediaItem.class, Playlist.class},
autoMigrations = {@AutoMigration(from = 9, to = 10)} autoMigrations = {@AutoMigration(from = 10, to = 11)}
) )
@TypeConverters({DateConverters.class}) @TypeConverters({DateConverters.class})
public abstract class AppDatabase extends RoomDatabase { public abstract class AppDatabase extends RoomDatabase {

View file

@ -37,6 +37,8 @@ class Chronology(@PrimaryKey override val id: String) : Child(id) {
transcodedSuffix = mediaItem.mediaMetadata.extras!!.getString("transcodedSuffix") transcodedSuffix = mediaItem.mediaMetadata.extras!!.getString("transcodedSuffix")
duration = mediaItem.mediaMetadata.extras!!.getInt("duration") duration = mediaItem.mediaMetadata.extras!!.getInt("duration")
bitrate = mediaItem.mediaMetadata.extras!!.getInt("bitrate") bitrate = mediaItem.mediaMetadata.extras!!.getInt("bitrate")
samplingRate = mediaItem.mediaMetadata.extras!!.getInt("samplingRate")
bitDepth = mediaItem.mediaMetadata.extras!!.getInt("bitDepth")
path = mediaItem.mediaMetadata.extras!!.getString("path") path = mediaItem.mediaMetadata.extras!!.getString("path")
isVideo = mediaItem.mediaMetadata.extras!!.getBoolean("isVideo") isVideo = mediaItem.mediaMetadata.extras!!.getBoolean("isVideo")
userRating = mediaItem.mediaMetadata.extras!!.getInt("userRating") userRating = mediaItem.mediaMetadata.extras!!.getInt("userRating")

View file

@ -41,6 +41,8 @@ class Queue(override val id: String) : Child(id) {
transcodedSuffix = child.transcodedSuffix transcodedSuffix = child.transcodedSuffix
duration = child.duration duration = child.duration
bitrate = child.bitrate bitrate = child.bitrate
samplingRate = child.samplingRate
bitDepth = child.bitDepth
path = child.path path = child.path
isVideo = child.isVideo isVideo = child.isVideo
userRating = child.userRating userRating = child.userRating

View file

@ -50,6 +50,12 @@ open class Child(
@ColumnInfo("bitrate") @ColumnInfo("bitrate")
@SerializedName("bitRate") @SerializedName("bitRate")
var bitrate: Int? = null, var bitrate: Int? = null,
@ColumnInfo("sampling_rate")
@SerializedName("samplingRate")
var samplingRate: Int? = null,
@ColumnInfo("bit_depth")
@SerializedName("bitDepth")
var bitDepth: Int? = null,
@ColumnInfo @ColumnInfo
var path: String? = null, var path: String? = null,
@ColumnInfo(name = "is_video") @ColumnInfo(name = "is_video")

View file

@ -72,6 +72,8 @@ public class TrackInfoDialog extends DialogFragment {
bind.transcodedSuffixValueSector.setText(mediaMetadata.extras.getString("transcodedSuffix", getString(R.string.label_placeholder))); bind.transcodedSuffixValueSector.setText(mediaMetadata.extras.getString("transcodedSuffix", getString(R.string.label_placeholder)));
bind.durationValueSector.setText(MusicUtil.getReadableDurationString(mediaMetadata.extras.getInt("duration", 0), false)); bind.durationValueSector.setText(MusicUtil.getReadableDurationString(mediaMetadata.extras.getInt("duration", 0), false));
bind.bitrateValueSector.setText(mediaMetadata.extras.getInt("bitrate", 0) + " kbps"); bind.bitrateValueSector.setText(mediaMetadata.extras.getInt("bitrate", 0) + " kbps");
bind.samplingRateValueSector.setText(mediaMetadata.extras.getInt("samplingRate", 0) != 0 ? mediaMetadata.extras.getInt("samplingRate", 0) + " Hz" : getString(R.string.label_placeholder));
bind.bitDepthValueSector.setText(mediaMetadata.extras.getInt("bitDepth", 0) != 0 ? mediaMetadata.extras.getInt("bitDepth", 0) + " bits" : getString(R.string.label_placeholder));
bind.pathValueSector.setText(mediaMetadata.extras.getString("path", getString(R.string.label_placeholder))); bind.pathValueSector.setText(mediaMetadata.extras.getString("path", getString(R.string.label_placeholder)));
bind.discNumberValueSector.setText(String.valueOf(mediaMetadata.extras.getInt("discNumber", 0))); bind.discNumberValueSector.setText(String.valueOf(mediaMetadata.extras.getInt("discNumber", 0)));
} }

View file

@ -2,6 +2,7 @@ package com.cappielloantonio.tempo.ui.fragment;
import android.content.ComponentName; import android.content.ComponentName;
import android.os.Bundle; import android.os.Bundle;
import android.text.TextUtils;
import android.view.LayoutInflater; import android.view.LayoutInflater;
import android.view.View; import android.view.View;
import android.view.ViewGroup; import android.view.ViewGroup;
@ -40,6 +41,9 @@ import com.google.android.material.elevation.SurfaceColors;
import com.google.common.util.concurrent.ListenableFuture; import com.google.common.util.concurrent.ListenableFuture;
import com.google.common.util.concurrent.MoreExecutors; import com.google.common.util.concurrent.MoreExecutors;
import java.text.DecimalFormat;
import java.util.ArrayList;
import java.util.List;
import java.util.Objects; import java.util.Objects;
@UnstableApi @UnstableApi
@ -190,14 +194,23 @@ public class PlayerControllerFragment extends Fragment {
if (mediaMetadata.extras != null) { if (mediaMetadata.extras != null) {
String extension = mediaMetadata.extras.getString("suffix", "Unknown format"); String extension = mediaMetadata.extras.getString("suffix", "Unknown format");
String bitrate = mediaMetadata.extras.getInt("bitrate", 0) != 0 ? mediaMetadata.extras.getInt("bitrate", 0) + "kbps" : "Original"; String bitrate = mediaMetadata.extras.getInt("bitrate", 0) != 0 ? mediaMetadata.extras.getInt("bitrate", 0) + "kbps" : "Original";
String samplingRate = mediaMetadata.extras.getInt("samplingRate", 0) != 0 ? new DecimalFormat("0.#").format(mediaMetadata.extras.getInt("samplingRate", 0) / 1000.0) + "kHz" : "";
String bitDepth = mediaMetadata.extras.getInt("bitDepth", 0) != 0 ? mediaMetadata.extras.getInt("bitDepth", 0) + "b" : "";
playerMediaExtension.setText(extension); playerMediaExtension.setText(extension);
if (bitrate.equals("Original")) { if (bitrate.equals("Original")) {
playerMediaBitrate.setVisibility(View.GONE); playerMediaBitrate.setVisibility(View.GONE);
} else { } else {
List<String> mediaQualityItems = new ArrayList<>();
if (!bitrate.trim().isEmpty()) mediaQualityItems.add(bitrate);
if (!bitDepth.trim().isEmpty()) mediaQualityItems.add(bitDepth);
if (!samplingRate.trim().isEmpty()) mediaQualityItems.add(samplingRate);
String mediaQuality = TextUtils.join("", mediaQualityItems);
playerMediaBitrate.setVisibility(View.VISIBLE); playerMediaBitrate.setVisibility(View.VISIBLE);
playerMediaBitrate.setText(bitrate); playerMediaBitrate.setText(mediaQuality);
} }
} }

View file

@ -54,6 +54,8 @@ public class MappingUtil {
bundle.putString("transcodedSuffix", media.getTranscodedSuffix()); bundle.putString("transcodedSuffix", media.getTranscodedSuffix());
bundle.putInt("duration", media.getDuration() != null ? media.getDuration() : 0); bundle.putInt("duration", media.getDuration() != null ? media.getDuration() : 0);
bundle.putInt("bitrate", media.getBitrate() != null ? media.getBitrate() : 0); bundle.putInt("bitrate", media.getBitrate() != null ? media.getBitrate() : 0);
bundle.putInt("samplingRate", media.getSamplingRate() != null ? media.getSamplingRate() : 0);
bundle.putInt("bitDepth", media.getBitDepth() != null ? media.getBitDepth() : 0);
bundle.putString("path", media.getPath()); bundle.putString("path", media.getPath());
bundle.putBoolean("isVideo", media.isVideo()); bundle.putBoolean("isVideo", media.isVideo());
bundle.putInt("userRating", media.getUserRating() != null ? media.getUserRating() : 0); bundle.putInt("userRating", media.getUserRating() != null ? media.getUserRating() : 0);

View file

@ -15,6 +15,7 @@ import com.cappielloantonio.tempo.repository.DownloadRepository;
import com.cappielloantonio.tempo.subsonic.models.Child; import com.cappielloantonio.tempo.subsonic.models.Child;
import java.text.CharacterIterator; import java.text.CharacterIterator;
import java.text.DecimalFormat;
import java.text.StringCharacterIterator; import java.text.StringCharacterIterator;
import java.util.ArrayList; import java.util.ArrayList;
import java.util.List; import java.util.List;
@ -163,6 +164,12 @@ public class MusicUtil {
" " + " " +
child.getBitrate() + child.getBitrate() +
"kbps" + "kbps" +
"" +
(child.getBitDepth() != null && child.getBitDepth() != 0
? child.getBitDepth() + "/" + (child.getSamplingRate() != null ? child.getSamplingRate() / 1000 : "")
: (child.getSamplingRate() != null
? new DecimalFormat("0.#").format(child.getSamplingRate() / 1000.0) + "kHz"
: "")) +
" " + " " +
child.getSuffix(); child.getSuffix();
} }

View file

@ -391,6 +391,58 @@
android:text="@string/label_placeholder" /> android:text="@string/label_placeholder" />
</LinearLayout> </LinearLayout>
<View
style="@style/Divider"
android:layout_gravity="center_vertical"
android:layout_marginVertical="8dp" />
<LinearLayout
android:id="@+id/sampling_rate_info_sector"
android:layout_width="match_parent"
android:layout_height="wrap_content">
<TextView
android:id="@+id/sampling_rate_key_sector"
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_weight="4"
android:paddingEnd="8dp"
android:text="@string/track_info_sampling_rate" />
<TextView
android:id="@+id/sampling_rate_value_sector"
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_weight="7"
android:text="@string/label_placeholder" />
</LinearLayout>
<View
style="@style/Divider"
android:layout_gravity="center_vertical"
android:layout_marginVertical="8dp" />
<LinearLayout
android:id="@+id/bit_depth_info_sector"
android:layout_width="match_parent"
android:layout_height="wrap_content">
<TextView
android:id="@+id/bit_depth_key_sector"
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_weight="4"
android:paddingEnd="8dp"
android:text="@string/track_info_bit_depth" />
<TextView
android:id="@+id/bit_depth_value_sector"
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_weight="7"
android:text="@string/label_placeholder" />
</LinearLayout>
<View <View
style="@style/Divider" style="@style/Divider"
android:layout_gravity="center_vertical" android:layout_gravity="center_vertical"

View file

@ -312,7 +312,9 @@
<string name="streaming_cache_storage_internal_dialog_negative_button">Interno</string> <string name="streaming_cache_storage_internal_dialog_negative_button">Interno</string>
<string name="track_info_album">Álbum</string> <string name="track_info_album">Álbum</string>
<string name="track_info_artist">Artista</string> <string name="track_info_artist">Artista</string>
<string name="track_info_bit_depth">Profundidad de bits</string>
<string name="track_info_bitrate">Tasa de bits</string> <string name="track_info_bitrate">Tasa de bits</string>
<string name="track_info_sampling_rate">Tasa de muestreo</string>
<string name="track_info_content_type">Tipo de contenido</string> <string name="track_info_content_type">Tipo de contenido</string>
<string name="track_info_dialog_positive_button">Aceptar</string> <string name="track_info_dialog_positive_button">Aceptar</string>
<string name="track_info_transcoded_content_type">Tipo de contenido en la transcodificación</string> <string name="track_info_transcoded_content_type">Tipo de contenido en la transcodificación</string>

View file

@ -395,6 +395,7 @@
<string name="support_url">https://buymeacoffee.com/a.cappiello</string> <string name="support_url">https://buymeacoffee.com/a.cappiello</string>
<string name="track_info_album">Album</string> <string name="track_info_album">Album</string>
<string name="track_info_artist">Artist</string> <string name="track_info_artist">Artist</string>
<string name="track_info_bit_depth">Bit depth</string>
<string name="track_info_bitrate">Bitrate</string> <string name="track_info_bitrate">Bitrate</string>
<string name="track_info_content_type">Content Type</string> <string name="track_info_content_type">Content Type</string>
<string name="track_info_dialog_positive_button">OK</string> <string name="track_info_dialog_positive_button">OK</string>
@ -403,6 +404,7 @@
<string name="track_info_duration">Duration</string> <string name="track_info_duration">Duration</string>
<string name="track_info_genre">Genre</string> <string name="track_info_genre">Genre</string>
<string name="track_info_path">Path</string> <string name="track_info_path">Path</string>
<string name="track_info_sampling_rate">Sampling rate</string>
<string name="track_info_size">Size</string> <string name="track_info_size">Size</string>
<string name="track_info_suffix">Suffix</string> <string name="track_info_suffix">Suffix</string>
<string name="track_info_summary_downloaded_file">The file has been downloaded using the Subsonic APIs. The codec and bitrate of the file remain unchanged from the source file.</string> <string name="track_info_summary_downloaded_file">The file has been downloaded using the Subsonic APIs. The codec and bitrate of the file remain unchanged from the source file.</string>