From 537478430cc79c1e5b85162642623a00996db2b0 Mon Sep 17 00:00:00 2001 From: Nite Date: Sat, 31 Oct 2020 08:51:43 +0100 Subject: [PATCH] Fixed null checks in SongView Migrated SongView to Kotlin --- .../org/moire/ultrasonic/view/SongView.java | 475 ------------------ .../org/moire/ultrasonic/view/SongView.kt | 395 +++++++++++++++ 2 files changed, 395 insertions(+), 475 deletions(-) delete mode 100644 ultrasonic/src/main/java/org/moire/ultrasonic/view/SongView.java create mode 100644 ultrasonic/src/main/kotlin/org/moire/ultrasonic/view/SongView.kt diff --git a/ultrasonic/src/main/java/org/moire/ultrasonic/view/SongView.java b/ultrasonic/src/main/java/org/moire/ultrasonic/view/SongView.java deleted file mode 100644 index 4bc45828..00000000 --- a/ultrasonic/src/main/java/org/moire/ultrasonic/view/SongView.java +++ /dev/null @@ -1,475 +0,0 @@ -/* - This file is part of Subsonic. - - Subsonic is free software: you can redistribute it and/or modify - it under the terms of the GNU General Public License as published by - the Free Software Foundation, either version 3 of the License, or - (at your option) any later version. - - Subsonic is distributed in the hope that it will be useful, - but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - GNU General Public License for more details. - - You should have received a copy of the GNU General Public License - along with Subsonic. If not, see . - - Copyright 2009 (C) Sindre Mehus - */ -package org.moire.ultrasonic.view; - -import android.content.Context; -import android.graphics.drawable.AnimationDrawable; -import android.graphics.drawable.Drawable; -import android.text.TextUtils; -import timber.log.Timber; -import android.view.LayoutInflater; -import android.view.View; -import android.widget.Checkable; -import android.widget.CheckedTextView; -import android.widget.ImageView; -import android.widget.LinearLayout; -import android.widget.TextView; - -import org.koin.java.KoinJavaComponent; -import org.moire.ultrasonic.R; -import org.moire.ultrasonic.data.ActiveServerProvider; -import org.moire.ultrasonic.domain.MusicDirectory.Entry; -import org.moire.ultrasonic.featureflags.Feature; -import org.moire.ultrasonic.featureflags.FeatureStorage; -import org.moire.ultrasonic.service.DownloadFile; -import org.moire.ultrasonic.service.MediaPlayerController; -import org.moire.ultrasonic.service.MusicService; -import org.moire.ultrasonic.service.MusicServiceFactory; -import org.moire.ultrasonic.util.Util; -import org.moire.ultrasonic.util.VideoPlayerType; - -import java.io.File; - -import kotlin.Lazy; - -import static org.koin.java.KoinJavaComponent.inject; - -/** - * Used to display songs in a {@code ListView}. - * - * @author Sindre Mehus - */ -public class SongView extends UpdateView implements Checkable -{ - private static Drawable starHollowDrawable; - private static Drawable starDrawable; - private static Drawable pinImage; - private static Drawable downloadedImage; - private static Drawable downloadingImage; - private static Drawable playingImage; - private static String theme; - private static LayoutInflater inflater; - - private Entry song; - private Context context; - private Drawable leftImage; - private ImageType previousLeftImageType; - private ImageType previousRightImageType; - private ImageType leftImageType; - private DownloadFile downloadFile; - private boolean playing; - private EntryAdapter.SongViewHolder viewHolder; - private boolean maximized = false; - private boolean useFiveStarRating; - - private Lazy mediaPlayerControllerLazy = inject(MediaPlayerController.class); - - public SongView(Context context) - { - super(context); - this.context = context; - - useFiveStarRating = KoinJavaComponent.get(FeatureStorage.class).isFeatureEnabled(Feature.FIVE_STAR_RATING); - - String theme = Util.getTheme(context); - boolean themesMatch = theme.equals(SongView.theme); - inflater = LayoutInflater.from(this.context); - - if (!themesMatch) - { - SongView.theme = theme; - } - - if (starHollowDrawable == null || !themesMatch) - { - starHollowDrawable = Util.getDrawableFromAttribute(context, R.attr.star_hollow); - } - - if (starDrawable == null || !themesMatch) - { - starDrawable = Util.getDrawableFromAttribute(context, R.attr.star_full); - } - - if (pinImage == null || !themesMatch) - { - pinImage = Util.getDrawableFromAttribute(context, R.attr.pin); - } - - if (downloadedImage == null || !themesMatch) - { - downloadedImage = Util.getDrawableFromAttribute(context, R.attr.downloaded); - } - - if (downloadingImage == null || !themesMatch) - { - downloadingImage = Util.getDrawableFromAttribute(context, R.attr.downloading); - } - - if (playingImage == null || !themesMatch) - { - playingImage = Util.getDrawableFromAttribute(context, R.attr.media_play_small); - } - } - - public void setLayout(final Entry song) - { - inflater.inflate(song.isVideo() ? R.layout.video_list_item : R.layout.song_list_item, this, true); - viewHolder = new EntryAdapter.SongViewHolder(); - viewHolder.check = findViewById(R.id.song_check); - viewHolder.rating = findViewById(R.id.song_rating); - viewHolder.fiveStar1 = findViewById(R.id.song_five_star_1); - viewHolder.fiveStar2 = findViewById(R.id.song_five_star_2); - viewHolder.fiveStar3 = findViewById(R.id.song_five_star_3); - viewHolder.fiveStar4 = findViewById(R.id.song_five_star_4); - viewHolder.fiveStar5 = findViewById(R.id.song_five_star_5); - viewHolder.star = findViewById(R.id.song_star); - viewHolder.drag = findViewById(R.id.song_drag); - viewHolder.track = findViewById(R.id.song_track); - viewHolder.title = findViewById(R.id.song_title); - viewHolder.artist = findViewById(R.id.song_artist); - viewHolder.duration = findViewById(R.id.song_duration); - viewHolder.status = findViewById(R.id.song_status); - setTag(viewHolder); - } - - public void setViewHolder(EntryAdapter.SongViewHolder viewHolder) - { - this.viewHolder = viewHolder; - setTag(this.viewHolder); - } - - public Entry getEntry() - { - return this.song; - } - - protected void setSong(final Entry song, boolean checkable, boolean draggable) - { - updateBackground(); - - this.song = song; - - this.downloadFile = mediaPlayerControllerLazy.getValue().getDownloadFileForSong(song); - - StringBuilder artist = new StringBuilder(60); - - String bitRate = null; - - if (song.getBitRate() != null) - { - bitRate = String.format(this.context.getString(R.string.song_details_kbps), song.getBitRate()); - } - - String fileFormat; - String suffix = song.getSuffix(); - String transcodedSuffix = song.getTranscodedSuffix(); - - fileFormat = TextUtils.isEmpty(transcodedSuffix) || - transcodedSuffix.equals(suffix) || - (song.isVideo() && Util.getVideoPlayerType(this.context) != VideoPlayerType.FLASH) ? - suffix : String.format("%s > %s", suffix, transcodedSuffix); - - String artistName = song.getArtist(); - - if (artistName != null) - { - if (Util.shouldDisplayBitrateWithArtist(this.context)) - { - artist.append(artistName).append(" (").append(String.format(this.context.getString(R.string.song_details_all), bitRate == null ? "" : String.format("%s ", bitRate), fileFormat)).append(')'); - } - else - { - artist.append(artistName); - } - } - - int trackNumber = (song.getTrack() == null) ? 0 : song.getTrack(); - - if (viewHolder.track != null) - { - if (Util.shouldShowTrackNumber(this.context) && trackNumber != 0) - { - viewHolder.track.setText(String.format("%02d.", trackNumber)); - } - else - { - viewHolder.track.setVisibility(View.GONE); - } - } - - StringBuilder title = new StringBuilder(60); - title.append(song.getTitle()); - - if (song.isVideo() && Util.shouldDisplayBitrateWithArtist(this.context)) - { - title.append(" (").append(String.format(this.context.getString(R.string.song_details_all), bitRate == null ? "" : String.format("%s ", bitRate), fileFormat)).append(')'); - } - - viewHolder.title.setText(title); - - if (viewHolder.artist != null) - { - viewHolder.artist.setText(artist); - } - - Integer duration = song.getDuration(); - - if (duration != null) - { - viewHolder.duration.setText(Util.formatTotalDuration(duration)); - } - - if (viewHolder.check != null) - { - viewHolder.check.setVisibility(checkable && !song.isVideo() ? View.VISIBLE : View.GONE); - } - - if (viewHolder.drag != null) - { - viewHolder.drag.setVisibility(draggable ? View.VISIBLE : View.GONE); - } - - if (ActiveServerProvider.Companion.isOffline(this.context)) - { - viewHolder.star.setVisibility(View.GONE); - viewHolder.rating.setVisibility(View.GONE); - } - else - { - if (useFiveStarRating) - { - viewHolder.star.setVisibility(View.GONE); - - int rating = song.getUserRating() == null ? 0 : song.getUserRating(); - viewHolder.fiveStar1.setImageDrawable(rating > 0 ? starDrawable : starHollowDrawable); - viewHolder.fiveStar2.setImageDrawable(rating > 1 ? starDrawable : starHollowDrawable); - viewHolder.fiveStar3.setImageDrawable(rating > 2 ? starDrawable : starHollowDrawable); - viewHolder.fiveStar4.setImageDrawable(rating > 3 ? starDrawable : starHollowDrawable); - viewHolder.fiveStar5.setImageDrawable(rating > 4 ? starDrawable : starHollowDrawable); - - } - else { - viewHolder.rating.setVisibility(View.GONE); - viewHolder.star.setImageDrawable(song.getStarred() ? starDrawable : starHollowDrawable); - - viewHolder.star.setOnClickListener(new View.OnClickListener() { - @Override - public void onClick(View view) { - final boolean isStarred = song.getStarred(); - final String id = song.getId(); - - if (!isStarred) { - viewHolder.star.setImageDrawable(starDrawable); - song.setStarred(true); - } else { - viewHolder.star.setImageDrawable(starHollowDrawable); - song.setStarred(false); - } - - new Thread(new Runnable() { - @Override - public void run() { - MusicService musicService = MusicServiceFactory.getMusicService(SongView.this.context); - - try { - if (!isStarred) { - musicService.star(id, null, null, SongView.this.context, null); - } else { - musicService.unstar(id, null, null, SongView.this.context, null); - } - } catch (Exception e) { - Timber.e(e); - } - } - }).start(); - } - }); - } - } - - update(); - } - - @Override - protected void updateBackground() - { - } - - @Override - protected void update() - { - updateBackground(); - - downloadFile = mediaPlayerControllerLazy.getValue().getDownloadFileForSong(this.song); - File partialFile = downloadFile.getPartialFile(); - - if (downloadFile.isWorkDone()) - { - ImageType newLeftImageType = downloadFile.isSaved() ? ImageType.pin : ImageType.downloaded; - - if (this.leftImageType != newLeftImageType) - { - this.leftImage = downloadFile.isSaved() ? pinImage : downloadedImage; - this.leftImageType = newLeftImageType; - } - } - else - { - this.leftImageType = ImageType.none; - this.leftImage = null; - } - - ImageType rightImageType; - Drawable rightImage; - if (downloadFile.isDownloading() && !downloadFile.isDownloadCancelled() && partialFile.exists()) - { - if (this.viewHolder.status != null) - { - this.viewHolder.status.setText(Util.formatLocalizedBytes(partialFile.length(), this.context)); - } - - rightImageType = ImageType.downloading; - rightImage = downloadingImage; - } - else - { - rightImageType = ImageType.none; - rightImage = null; - - if (this.viewHolder.status != null) - { - CharSequence statusText = this.viewHolder.status.getText(); - - if (statusText != "" || statusText != null) - { - this.viewHolder.status.setText(null); - } - } - } - - if (this.previousLeftImageType != leftImageType || this.previousRightImageType != rightImageType) - { - this.previousLeftImageType = leftImageType; - this.previousRightImageType = rightImageType; - - if (this.viewHolder.status != null) - { - this.viewHolder.status.setCompoundDrawablesWithIntrinsicBounds(leftImage, null, rightImage, null); - - if (rightImage == downloadingImage) - { - AnimationDrawable frameAnimation = (AnimationDrawable) rightImage; - frameAnimation.setVisible(true, true); - frameAnimation.start(); - } - } - } - - if (!song.getStarred()) - { - if (viewHolder.star != null) - { - if (viewHolder.star.getDrawable() != starHollowDrawable) - { - viewHolder.star.setImageDrawable(starHollowDrawable); - } - } - } - else - { - if (viewHolder.star != null) - { - if (viewHolder.star.getDrawable() != starDrawable) - { - viewHolder.star.setImageDrawable(starDrawable); - } - } - } - - int rating = song.getUserRating() == null ? 0 : song.getUserRating(); - viewHolder.fiveStar1.setImageDrawable(rating > 0 ? starDrawable : starHollowDrawable); - viewHolder.fiveStar2.setImageDrawable(rating > 1 ? starDrawable : starHollowDrawable); - viewHolder.fiveStar3.setImageDrawable(rating > 2 ? starDrawable : starHollowDrawable); - viewHolder.fiveStar4.setImageDrawable(rating > 3 ? starDrawable : starHollowDrawable); - viewHolder.fiveStar5.setImageDrawable(rating > 4 ? starDrawable : starHollowDrawable); - - boolean playing = mediaPlayerControllerLazy.getValue().getCurrentPlaying() == downloadFile; - - if (playing) - { - if (!this.playing) - { - this.playing = true; - viewHolder.title.setCompoundDrawablesWithIntrinsicBounds(playingImage, null, null, null); - } - } - else - { - if (this.playing) - { - this.playing = false; - viewHolder.title.setCompoundDrawablesWithIntrinsicBounds(0, 0, 0, 0); - } - } - } - - @Override - public void setChecked(boolean b) - { - viewHolder.check.setChecked(b); - } - - @Override - public boolean isChecked() - { - return viewHolder.check.isChecked(); - } - - @Override - public void toggle() - { - viewHolder.check.toggle(); - } - - public boolean isMaximized() { - return maximized; - } - - public void maximizeOrMinimize() { - if (maximized) { - maximized = false; - } else { - maximized = true; - } - if (this.viewHolder.title != null) { - this.viewHolder.title.setSingleLine(!maximized); - } - if (this.viewHolder.artist != null) { - this.viewHolder.artist.setSingleLine(!maximized); - } - } - - public enum ImageType - { - none, - pin, - downloaded, - downloading - } -} diff --git a/ultrasonic/src/main/kotlin/org/moire/ultrasonic/view/SongView.kt b/ultrasonic/src/main/kotlin/org/moire/ultrasonic/view/SongView.kt new file mode 100644 index 00000000..eca7ceda --- /dev/null +++ b/ultrasonic/src/main/kotlin/org/moire/ultrasonic/view/SongView.kt @@ -0,0 +1,395 @@ +/* + This file is part of Subsonic. + + Subsonic is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + Subsonic is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with Subsonic. If not, see . + + Copyright 2009 (C) Sindre Mehus + */ +package org.moire.ultrasonic.view + +import android.content.Context +import android.graphics.drawable.AnimationDrawable +import android.graphics.drawable.Drawable +import android.text.TextUtils +import android.view.LayoutInflater +import android.widget.Checkable +import org.koin.java.KoinJavaComponent.get +import org.koin.java.KoinJavaComponent.inject +import org.moire.ultrasonic.R +import org.moire.ultrasonic.data.ActiveServerProvider.Companion.isOffline +import org.moire.ultrasonic.domain.MusicDirectory +import org.moire.ultrasonic.featureflags.Feature +import org.moire.ultrasonic.featureflags.FeatureStorage +import org.moire.ultrasonic.service.DownloadFile +import org.moire.ultrasonic.service.MediaPlayerController +import org.moire.ultrasonic.service.MusicServiceFactory.getMusicService +import org.moire.ultrasonic.util.Util +import org.moire.ultrasonic.util.VideoPlayerType +import org.moire.ultrasonic.view.EntryAdapter.SongViewHolder +import timber.log.Timber + +/** + * Used to display songs in a `ListView`. + * + * @author Sindre Mehus + */ +class SongView(context: Context) : UpdateView(context), Checkable { + + var entry: MusicDirectory.Entry? = null + private set + + private var isMaximized = false + private var leftImage: Drawable? = null + private var previousLeftImageType: ImageType? = null + private var previousRightImageType: ImageType? = null + private var leftImageType: ImageType? = null + private var downloadFile: DownloadFile? = null + private var playing = false + private var viewHolder: SongViewHolder? = null + + private val useFiveStarRating: Boolean = + get(FeatureStorage::class.java).isFeatureEnabled(Feature.FIVE_STAR_RATING) + private val mediaPlayerControllerLazy = inject(MediaPlayerController::class.java) + + fun setLayout(song: MusicDirectory.Entry) { + + inflater?.inflate( + if (song.isVideo) R.layout.video_list_item + else R.layout.song_list_item, + this, + true + ) + + viewHolder = SongViewHolder() + viewHolder!!.check = findViewById(R.id.song_check) + viewHolder!!.rating = findViewById(R.id.song_rating) + viewHolder!!.fiveStar1 = findViewById(R.id.song_five_star_1) + viewHolder!!.fiveStar2 = findViewById(R.id.song_five_star_2) + viewHolder!!.fiveStar3 = findViewById(R.id.song_five_star_3) + viewHolder!!.fiveStar4 = findViewById(R.id.song_five_star_4) + viewHolder!!.fiveStar5 = findViewById(R.id.song_five_star_5) + viewHolder!!.star = findViewById(R.id.song_star) + viewHolder!!.drag = findViewById(R.id.song_drag) + viewHolder!!.track = findViewById(R.id.song_track) + viewHolder!!.title = findViewById(R.id.song_title) + viewHolder!!.artist = findViewById(R.id.song_artist) + viewHolder!!.duration = findViewById(R.id.song_duration) + viewHolder!!.status = findViewById(R.id.song_status) + tag = viewHolder + } + + fun setViewHolder(viewHolder: SongViewHolder?) { + this.viewHolder = viewHolder + tag = this.viewHolder + } + + fun setSong(song: MusicDirectory.Entry, checkable: Boolean, draggable: Boolean) { + updateBackground() + + entry = song + downloadFile = mediaPlayerControllerLazy.value.getDownloadFileForSong(song) + + val artist = StringBuilder(60) + var bitRate: String? = null + + if (song.bitRate != null) + bitRate = String.format( + this.context.getString(R.string.song_details_kbps), song.bitRate + ) + + val fileFormat: String? + val suffix = song.suffix + val transcodedSuffix = song.transcodedSuffix + + fileFormat = if ( + TextUtils.isEmpty(transcodedSuffix) || transcodedSuffix == suffix || + song.isVideo && Util.getVideoPlayerType(this.context) !== VideoPlayerType.FLASH + ) suffix else String.format("%s > %s", suffix, transcodedSuffix) + + val artistName = song.artist + + if (artistName != null) { + if (Util.shouldDisplayBitrateWithArtist(this.context)) { + artist.append(artistName).append(" (").append( + String.format( + this.context.getString(R.string.song_details_all), + if (bitRate == null) "" else String.format("%s ", bitRate), fileFormat + ) + ).append(')') + } else { + artist.append(artistName) + } + } + + val trackNumber = song.track ?: 0 + + if (Util.shouldShowTrackNumber(this.context) && trackNumber != 0) { + viewHolder?.track?.text = String.format("%02d.", trackNumber) + } else { + viewHolder?.track?.visibility = GONE + } + + val title = StringBuilder(60) + title.append(song.title) + + if (song.isVideo && Util.shouldDisplayBitrateWithArtist(this.context)) { + title.append(" (").append( + String.format( + this.context.getString(R.string.song_details_all), + if (bitRate == null) "" else String.format("%s ", bitRate), fileFormat + ) + ).append(')') + } + + viewHolder?.title?.text = title + viewHolder?.artist?.text = artist + + val duration = song.duration + if (duration != null) { + viewHolder?.duration?.text = Util.formatTotalDuration(duration.toLong()) + } + + viewHolder?.check?.visibility = if (checkable && !song.isVideo) VISIBLE else GONE + viewHolder?.drag?.visibility = if (draggable) VISIBLE else GONE + + if (isOffline(this.context)) { + viewHolder?.star?.visibility = GONE + viewHolder?.rating?.visibility = GONE + } else { + if (useFiveStarRating) { + viewHolder?.star?.visibility = GONE + val rating = if (song.userRating == null) 0 else song.userRating!! + viewHolder?.fiveStar1?.setImageDrawable( + if (rating > 0) starDrawable else starHollowDrawable + ) + viewHolder?.fiveStar2?.setImageDrawable( + if (rating > 1) starDrawable else starHollowDrawable + ) + viewHolder?.fiveStar3?.setImageDrawable( + if (rating > 2) starDrawable else starHollowDrawable + ) + viewHolder?.fiveStar4?.setImageDrawable( + if (rating > 3) starDrawable else starHollowDrawable + ) + viewHolder?.fiveStar5?.setImageDrawable( + if (rating > 4) starDrawable else starHollowDrawable + ) + } else { + viewHolder?.rating?.visibility = GONE + viewHolder?.star?.setImageDrawable( + if (song.starred) starDrawable else starHollowDrawable + ) + + viewHolder?.star?.setOnClickListener { + val isStarred = song.starred + val id = song.id + + if (!isStarred) { + viewHolder?.star?.setImageDrawable(starDrawable) + song.starred = true + } else { + viewHolder?.star?.setImageDrawable(starHollowDrawable) + song.starred = false + } + Thread { + val musicService = getMusicService(this@SongView.context) + try { + if (!isStarred) { + musicService.star(id, null, null, this@SongView.context, null) + } else { + musicService.unstar(id, null, null, this@SongView.context, null) + } + } catch (e: Exception) { + Timber.e(e) + } + }.start() + } + } + } + update() + } + + override fun updateBackground() {} + + public override fun update() { + updateBackground() + + downloadFile = mediaPlayerControllerLazy.value.getDownloadFileForSong(entry) + + val partialFile = downloadFile!!.partialFile + + if (downloadFile!!.isWorkDone) { + val newLeftImageType = + if (downloadFile!!.isSaved) ImageType.Pin else ImageType.Downloaded + + if (leftImageType != newLeftImageType) { + leftImage = if (downloadFile!!.isSaved) pinImage else downloadedImage + leftImageType = newLeftImageType + } + } else { + leftImageType = ImageType.None + leftImage = null + } + + val rightImageType: ImageType + val rightImage: Drawable? + + if ( + downloadFile!!.isDownloading && + !downloadFile!!.isDownloadCancelled && + partialFile.exists() + ) { + viewHolder?.status?.text = Util.formatLocalizedBytes( + partialFile.length(), this.context + ) + + rightImageType = ImageType.Downloading + rightImage = downloadingImage + } else { + rightImageType = ImageType.None + rightImage = null + + val statusText = viewHolder?.status?.text + if (!statusText.isNullOrEmpty()) viewHolder?.status?.text = null + } + if (previousLeftImageType != leftImageType || previousRightImageType != rightImageType) { + previousLeftImageType = leftImageType + previousRightImageType = rightImageType + + if (viewHolder?.status != null) { + viewHolder?.status?.setCompoundDrawablesWithIntrinsicBounds( + leftImage, null, rightImage, null + ) + + if (rightImage === downloadingImage) { + val frameAnimation = rightImage as AnimationDrawable? + + frameAnimation!!.setVisible(true, true) + frameAnimation.start() + } + } + } + + if (entry?.starred != true) { + if (viewHolder?.star?.drawable !== starHollowDrawable) { + viewHolder?.star?.setImageDrawable(starHollowDrawable) + } + } else { + if (viewHolder?.star?.drawable !== starDrawable) { + viewHolder?.star?.setImageDrawable(starDrawable) + } + } + + val rating = entry?.userRating ?: 0 + viewHolder?.fiveStar1?.setImageDrawable( + if (rating > 0) starDrawable else starHollowDrawable + ) + viewHolder?.fiveStar2?.setImageDrawable( + if (rating > 1) starDrawable else starHollowDrawable + ) + viewHolder?.fiveStar3?.setImageDrawable( + if (rating > 2) starDrawable else starHollowDrawable + ) + viewHolder?.fiveStar4?.setImageDrawable( + if (rating > 3) starDrawable else starHollowDrawable + ) + viewHolder?.fiveStar5?.setImageDrawable( + if (rating > 4) starDrawable else starHollowDrawable + ) + + val playing = mediaPlayerControllerLazy.value.currentPlaying === downloadFile + + if (playing) { + if (!this.playing) { + this.playing = true + viewHolder?.title?.setCompoundDrawablesWithIntrinsicBounds( + playingImage, null, null, null + ) + } + } else { + if (this.playing) { + this.playing = false + viewHolder?.title?.setCompoundDrawablesWithIntrinsicBounds( + 0, 0, 0, 0 + ) + } + } + } + + override fun setChecked(b: Boolean) { + viewHolder?.check?.isChecked = b + } + + override fun isChecked(): Boolean { + return viewHolder?.check?.isChecked ?: false + } + + override fun toggle() { + viewHolder?.check?.toggle() + } + + fun maximizeOrMinimize() { + isMaximized = !isMaximized + + viewHolder?.title?.setSingleLine(!isMaximized) + viewHolder?.artist?.setSingleLine(!isMaximized) + } + + enum class ImageType { + None, Pin, Downloaded, Downloading + } + + companion object { + private var starHollowDrawable: Drawable? = null + private var starDrawable: Drawable? = null + private var pinImage: Drawable? = null + private var downloadedImage: Drawable? = null + private var downloadingImage: Drawable? = null + private var playingImage: Drawable? = null + private var theme: String? = null + private var inflater: LayoutInflater? = null + } + + init { + val theme = Util.getTheme(context) + val themesMatch = theme == Companion.theme + inflater = LayoutInflater.from(this.context) + + if (!themesMatch) Companion.theme = theme + + if (starHollowDrawable == null || !themesMatch) { + starHollowDrawable = Util.getDrawableFromAttribute(context, R.attr.star_hollow) + } + + if (starDrawable == null || !themesMatch) { + starDrawable = Util.getDrawableFromAttribute(context, R.attr.star_full) + } + + if (pinImage == null || !themesMatch) { + pinImage = Util.getDrawableFromAttribute(context, R.attr.pin) + } + + if (downloadedImage == null || !themesMatch) { + downloadedImage = Util.getDrawableFromAttribute(context, R.attr.downloaded) + } + + if (downloadingImage == null || !themesMatch) { + downloadingImage = Util.getDrawableFromAttribute(context, R.attr.downloading) + } + + if (playingImage == null || !themesMatch) { + playingImage = Util.getDrawableFromAttribute(context, R.attr.media_play_small) + } + } +}