This commit is contained in:
ocean 2024-07-02 16:17:38 +08:00
parent 207f2e32ae
commit 43399079c8
6 changed files with 139 additions and 358 deletions

View File

@ -5,14 +5,12 @@ import android.graphics.Color
import android.graphics.drawable.ColorDrawable import android.graphics.drawable.ColorDrawable
import android.view.LayoutInflater import android.view.LayoutInflater
import android.view.View import android.view.View
import android.view.animation.Animation
import android.view.animation.AnimationUtils
import android.widget.TextView import android.widget.TextView
import androidx.annotation.OptIn import androidx.annotation.OptIn
import androidx.appcompat.app.AlertDialog import androidx.appcompat.app.AlertDialog
import androidx.media3.common.util.UnstableApi import androidx.media3.common.util.UnstableApi
import androidx.media3.exoplayer.offline.Download
import androidx.recyclerview.widget.LinearLayoutManager import androidx.recyclerview.widget.LinearLayoutManager
import com.bumptech.glide.Glide
import com.gyf.immersionbar.ktx.immersionBar import com.gyf.immersionbar.ktx.immersionBar
import kotlinx.coroutines.channels.Channel import kotlinx.coroutines.channels.Channel
import kotlinx.coroutines.isActive import kotlinx.coroutines.isActive
@ -24,29 +22,33 @@ import melody.offline.music.ads.AdPlacement
import melody.offline.music.ads.LolAdWrapper import melody.offline.music.ads.LolAdWrapper
import melody.offline.music.bean.FavoriteBean import melody.offline.music.bean.FavoriteBean
import melody.offline.music.bean.OfflineBean import melody.offline.music.bean.OfflineBean
import melody.offline.music.bean.PlaylistItem
import melody.offline.music.databinding.ActivityOfflineSongsBinding import melody.offline.music.databinding.ActivityOfflineSongsBinding
import melody.offline.music.util.AnalysisUtil import melody.offline.music.util.AnalysisUtil
import melody.offline.music.util.LogTag import melody.offline.music.util.LogTag
import melody.offline.music.view.ListMoreBottomSheetDialog
import org.json.JSONObject import org.json.JSONObject
@OptIn(UnstableApi::class) @OptIn(UnstableApi::class)
class MoOfflineSongsActivity : MoBaseActivity() { class MoOfflineSongsActivity : MoBaseActivity(), ListMoreBottomSheetDialog.ListMoreViewListener,
ListMoreBottomSheetDialog.UpdateAdapterListener {
private val requests: Channel<Request> = Channel(Channel.UNLIMITED) private val requests: Channel<Request> = Channel(Channel.UNLIMITED)
sealed class Request { sealed class Request {
data object TryAgain : Request() data object TryAgain : Request()
data class OnFavorites(val bean: OfflineBean) : Request() data class OnFavorites(val bean: PlaylistItem) : Request()
data class OnDownloadRemove(val id: String) : Request() data class OnDownloadRemove(val bean: PlaylistItem) : Request()
data class UpdateFavorite(val id: String) : Request() data class UpdateFavorite(val bean: PlaylistItem) : Request()
data class OnAddPlaylist(val bean: OfflineBean) : Request() data class OnAddPlaylist(val bean: PlaylistItem) : Request()
data class OnUpdateCurrentListItem(val bean: PlaylistItem) : Request()
} }
private lateinit var binding: ActivityOfflineSongsBinding private lateinit var binding: ActivityOfflineSongsBinding
private var adapter: OfflineSongsAdapter? = null private var adapter: OfflineSongsAdapter? = null
private var offlineList: MutableList<OfflineBean> = mutableListOf()
private var myList: MutableList<PlaylistItem> = mutableListOf()
private var moreDialog: ListMoreBottomSheetDialog? = null
private var currentPosition = -1 private var currentPosition = -1
private var isAnimationRunning = false//动画是否正在进行
override suspend fun main() { override suspend fun main() {
binding = ActivityOfflineSongsBinding.inflate(layoutInflater) binding = ActivityOfflineSongsBinding.inflate(layoutInflater)
@ -89,7 +91,7 @@ class MoOfflineSongsActivity : MoBaseActivity() {
) )
val currentFavoriteBean = val currentFavoriteBean =
App.appFavoriteDBManager.getFavoriteBeanByID(it.bean.videoId) App.appFavoriteDBManager.getFavoriteBeanByID(it.bean.videoId)
if (currentFavoriteBean != null) { if (currentFavoriteBean != null) {//先获取数据库是否有这条数据
currentFavoriteBean.isFavorite = !currentFavoriteBean.isFavorite currentFavoriteBean.isFavorite = !currentFavoriteBean.isFavorite
App.appFavoriteDBManager.updateFavoriteBean(currentFavoriteBean) App.appFavoriteDBManager.updateFavoriteBean(currentFavoriteBean)
if (currentFavoriteBean.isFavorite) { if (currentFavoriteBean.isFavorite) {
@ -102,34 +104,47 @@ class MoOfflineSongsActivity : MoBaseActivity() {
) )
} }
} else { } else {
insertFavoriteData(it.bean)
insertFavoriteData(OfflineBean(
videoId = it.bean.videoId,
title = it.bean.title,
name = it.bean.name,
thumbnail = it.bean.thumbnail,
bytesDownloaded = it.bean.bytesDownloaded,
size = it.bean.size,
isOffline = it.bean.isOffline,
isFavorite = it.bean.isFavorite
))
AnalysisUtil.logEvent(AnalysisUtil.PLAYER_B_LOVE_CLICK, songMap) AnalysisUtil.logEvent(AnalysisUtil.PLAYER_B_LOVE_CLICK, songMap)
} }
requests.trySend(Request.UpdateFavorite(it.bean.videoId)) requests.trySend(Request.UpdateFavorite(it.bean))
}
is Request.OnDownloadRemove -> {
val currentOfflineBean =
App.appOfflineDBManager.getOfflineBeanByID(it.id)
if (currentOfflineBean != null) {
App.appOfflineDBManager.deleteOfflineBean(currentOfflineBean)
}
if (currentPosition >= 0) {
offlineList.remove(offlineList[currentPosition])
}
adapter?.notifyDataSetChanged()
hideBottomLayout()
} }
is Request.UpdateFavorite -> { is Request.UpdateFavorite -> {
val currentFavoriteBean = val currentFavoriteBean = App.appFavoriteDBManager.getFavoriteBeanByID(it.bean.videoId)
App.appFavoriteDBManager.getFavoriteBeanByID(it.id)
if (currentFavoriteBean != null) { if (currentFavoriteBean != null) {
updateFavoriteUi(currentFavoriteBean.isFavorite) updateFavoriteUi(currentFavoriteBean.isFavorite)
} else { } else {
updateFavoriteUi(false) updateFavoriteUi(false)
} }
requests.trySend(Request.OnUpdateCurrentListItem(it.bean))
}
is Request.OnDownloadRemove -> {
val currentOfflineBean =
App.appOfflineDBManager.getOfflineBeanByID(it.bean.videoId)
if (currentOfflineBean != null) {
App.appOfflineDBManager.deleteOfflineBean(currentOfflineBean)
}
if (currentPosition >= 0) {
myList.remove(myList[currentPosition])
}
adapter?.notifyDataSetChanged()
moreDialog?.dismiss()
requests.trySend(Request.OnUpdateCurrentListItem(it.bean))
} }
is Request.OnAddPlaylist -> { is Request.OnAddPlaylist -> {
@ -143,6 +158,10 @@ class MoOfflineSongsActivity : MoBaseActivity() {
) )
) )
} }
is Request.OnUpdateCurrentListItem -> {
updateCurrentItem(it.bean.videoId)
}
} }
} }
events.onReceive { events.onReceive {
@ -182,46 +201,27 @@ class MoOfflineSongsActivity : MoBaseActivity() {
} }
private fun initView() { private fun initView() {
binding.layoutInfo.setOnClickListener { }
binding.backBtn.setOnClickListener { binding.backBtn.setOnClickListener {
finish() finish()
} }
binding.tryAgainBtn.setOnClickListener { binding.tryAgainBtn.setOnClickListener {
requests.trySend(Request.TryAgain) requests.trySend(Request.TryAgain)
} }
binding.bottomCloseBtn.setOnClickListener {
hideBottomLayout()
}
binding.bottomBlankLayout.setOnClickListener {
hideBottomLayout()
}
binding.moreDownloadBtn.setOnClickListener {
if (currentPosition >= 0) {
val videoId = offlineList[currentPosition].videoId
showRemoveDownloadDialogHint(videoId)
}
}
binding.moreAddPlaylistBtn.setOnClickListener {
if (currentPosition >= 0) {
requests.trySend(Request.OnAddPlaylist(offlineList[currentPosition]))
hideBottomLayout()
}
}
binding.favoritesBtn.setOnClickListener {
if (currentPosition >= 0) {
requests.trySend(Request.OnFavorites(offlineList[currentPosition]))
}
}
} }
private fun initAdapter() { private fun initAdapter() {
adapter = OfflineSongsAdapter(this, offlineList) adapter = OfflineSongsAdapter(this, myList)
adapter?.setOnMoreClickListener(object : OfflineSongsAdapter.OnMoreClickListener { adapter?.setOnMoreClickListener(object : OfflineSongsAdapter.OnMoreClickListener {
override fun onMoreClick(position: Int) { override fun onMoreClick(position: Int) {
currentPosition = position currentPosition = position
if (!isAnimationRunning) { moreDialog = ListMoreBottomSheetDialog(
toggleBottomLayout(position) this@MoOfflineSongsActivity,
} myList[position],
this@MoOfflineSongsActivity,
this@MoOfflineSongsActivity
)
moreDialog?.setListMoreViewListener(this@MoOfflineSongsActivity)
moreDialog?.show()
} }
}) })
binding.rv.layoutManager = LinearLayoutManager(this, LinearLayoutManager.VERTICAL, false) binding.rv.layoutManager = LinearLayoutManager(this, LinearLayoutManager.VERTICAL, false)
@ -231,35 +231,84 @@ class MoOfflineSongsActivity : MoBaseActivity() {
@SuppressLint("NotifyDataSetChanged") @SuppressLint("NotifyDataSetChanged")
private suspend fun initData() { private suspend fun initData() {
showLoadingUi() showLoadingUi()
offlineList.clear()
val offlineBeans = App.appOfflineDBManager.getAllOfflineBeans() val offlineBeans = App.appOfflineDBManager.getAllOfflineBeans()
// 更新 if (offlineBeans.isNotEmpty()) {
offlineBeans.forEach { offlineBean -> myList.clear()
val favoriteBean = App.appFavoriteDBManager.getFavoriteBeanByID(offlineBean.videoId) offlineBeans.forEach { offlineBean ->
if (favoriteBean != null) { val favoriteItem = App.appFavoriteDBManager.getFavoriteBeanByID(offlineBean.videoId)
if (offlineBean.id == favoriteBean.id) { if (offlineBean.bytesDownloaded?.let { bytes -> bytes > 0 } == true) {
offlineBean.isFavorite = favoriteBean.isFavorite myList.add(
App.appOfflineDBManager.updateOfflineBean(offlineBean) PlaylistItem(
videoId = offlineBean.videoId,
title = offlineBean.title,
name = offlineBean.name,
thumbnail = offlineBean.thumbnail,
isOffline = offlineBean.isOffline,
isFavorite = favoriteItem?.isFavorite ?: false,
bytesDownloaded = offlineBean.bytesDownloaded,
size = offlineBean.size
)
)
} }
} }
} if (myList.size > 0) {
val filteredBeans = showDataUi()
offlineBeans.filter { it.bytesDownloaded?.let { bytes -> bytes > 0 } == true } } else {
offlineList.addAll(filteredBeans) showNoContentUi()
if (offlineList.size > 0) { }
showDataUi()
} else { } else {
showNoContentUi() showNoContentUi()
} }
if (adapter != null) { if (adapter != null) {
adapter?.notifyDataSetChanged() adapter?.notifyDataSetChanged()
} }
}
private fun updateFavoriteUi(b: Boolean) {
if (moreDialog != null) {
moreDialog?.updateFavoriteUi(b)
}
}
private suspend fun updateCurrentItem(id: String) {
//更新当前界面的数据集合
myList.forEach { item ->
if (item.videoId == id) {
val favoriteBean = App.appFavoriteDBManager.getFavoriteBeanByID(item.videoId)
val offlineBean = App.appOfflineDBManager.getOfflineBeanByID(item.videoId)
item.isFavorite = favoriteBean?.isFavorite ?: false
item.isOffline = offlineBean?.isOffline ?: false
item.bytesDownloaded = offlineBean?.bytesDownloaded
item.size = offlineBean?.size
}
}
myList.forEach { item ->
if (item.videoId == id) {
LogTag.LogD(TAG, "updateCurrentItem -> $item")
}
}
}
override fun onFavoritesClicked(playlistItem: PlaylistItem) {
requests.trySend(Request.OnFavorites(playlistItem))
}
override fun onDownloadClicked(playlistItem: PlaylistItem) {
//下载列表只有删除删除后更新adapter
showRemoveDownloadDialogHint(playlistItem)
}
override fun onAddToPlaylistClicked(playlistItem: PlaylistItem) {
requests.trySend(Request.OnAddPlaylist(playlistItem))
}
override fun onUpdateAdapterListener(download: Download, playlistItem: PlaylistItem) {
} }
private fun showRemoveDownloadDialogHint(id: String) { private fun showRemoveDownloadDialogHint(bean: PlaylistItem) {
LogTag.LogD(TAG, "showRemoveDownloadDialogHint")
val inflater = LayoutInflater.from(this) val inflater = LayoutInflater.from(this)
val dialogView = inflater.inflate(R.layout.dialog_hint, null) val dialogView = inflater.inflate(R.layout.dialog_hint, null)
val okBtn = dialogView.findViewById<TextView>(R.id.dialog_ok_btn) val okBtn = dialogView.findViewById<TextView>(R.id.dialog_ok_btn)
@ -270,93 +319,13 @@ class MoOfflineSongsActivity : MoBaseActivity() {
dialog.show() dialog.show()
okBtn.setOnClickListener { okBtn.setOnClickListener {
dialog.dismiss() dialog.dismiss()
requests.trySend(Request.OnDownloadRemove(id)) requests.trySend(Request.OnDownloadRemove(bean))
} }
cancelBtn.setOnClickListener { cancelBtn.setOnClickListener {
dialog.dismiss() dialog.dismiss()
} }
} }
private fun updateFavoriteUi(b: Boolean) {
if (b) {
binding.favoritesImg.setImageResource(R.drawable.favorited_icon)
} else {
binding.favoritesImg.setImageResource(R.drawable.not_favorited_icon)
}
}
private fun toggleBottomLayout(position: Int) {
if (binding.bottomLayout.visibility == View.VISIBLE) {
hideBottomLayout()
} else {
showBottomLayout(position)
}
}
private fun showBottomLayout(position: Int) {
val slideUpAnimation = AnimationUtils.loadAnimation(this, R.anim.slide_up)
slideUpAnimation.setAnimationListener(object : Animation.AnimationListener {
override fun onAnimationStart(animation: Animation) {
isAnimationRunning = true
// 动画开始时禁用按钮
animationLoadingNotClick(false)
}
override fun onAnimationEnd(animation: Animation) {
isAnimationRunning = false
// 动画结束时启用按钮
animationLoadingNotClick(true)
}
override fun onAnimationRepeat(animation: Animation) {
// 可选:处理动画重复的情况
}
})
binding.bottomLayout.startAnimation(slideUpAnimation)
binding.bottomLayout.visibility = View.VISIBLE
val bean = offlineList[position]
Glide.with(this).load(bean.thumbnail).into(binding.songImg)
binding.title.text = bean.title
if (bean.name.isEmpty()) {
binding.name.visibility = View.GONE
} else {
binding.name.visibility = View.VISIBLE
binding.name.text = bean.name
}
requests.trySend(Request.UpdateFavorite(bean.videoId))
}
private fun hideBottomLayout() {
val slideDownAnimation = AnimationUtils.loadAnimation(this, R.anim.slide_down)
slideDownAnimation.setAnimationListener(object : Animation.AnimationListener {
override fun onAnimationStart(animation: Animation?) {
isAnimationRunning = true
animationLoadingNotClick(false)
}
override fun onAnimationEnd(animation: Animation?) {
isAnimationRunning = false
animationLoadingNotClick(true)
}
override fun onAnimationRepeat(animation: Animation?) {
}
})
binding.bottomLayout.startAnimation(slideDownAnimation)
binding.bottomLayout.visibility = View.GONE
}
private fun animationLoadingNotClick(b: Boolean) {
binding.layoutInfo.isClickable = b
binding.bottomCloseBtn.isClickable = b
binding.bottomBlankLayout.isClickable = b
binding.moreDownloadBtn.isClickable = b
binding.moreAddPlaylistBtn.isClickable = b
binding.favoritesBtn.isClickable = b
}
private fun showDataUi() { private fun showDataUi() {
binding.loadingLayout.visibility = View.GONE binding.loadingLayout.visibility = View.GONE
binding.noContentLayout.visibility = View.GONE binding.noContentLayout.visibility = View.GONE

View File

@ -339,7 +339,8 @@ class MoPlaylistSongsActivity : MoBaseActivity(), ListMoreBottomSheetDialog.List
this@MoPlaylistSongsActivity, this@MoPlaylistSongsActivity,
playlistItems[position], playlistItems[position],
this@MoPlaylistSongsActivity, this@MoPlaylistSongsActivity,
this@MoPlaylistSongsActivity this@MoPlaylistSongsActivity,
true
) )
moreDialog?.setListMoreViewListener(this@MoPlaylistSongsActivity) moreDialog?.setListMoreViewListener(this@MoPlaylistSongsActivity)
moreDialog?.show() moreDialog?.show()

View File

@ -11,13 +11,13 @@ import com.bumptech.glide.Glide
import melody.offline.music.R import melody.offline.music.R
import melody.offline.music.activity.MoOfflineSongsActivity import melody.offline.music.activity.MoOfflineSongsActivity
import melody.offline.music.activity.MoPlayDetailsActivity import melody.offline.music.activity.MoPlayDetailsActivity
import melody.offline.music.bean.OfflineBean import melody.offline.music.bean.PlaylistItem
import melody.offline.music.databinding.OfflineListItemBinding import melody.offline.music.databinding.OfflineListItemBinding
import melody.offline.music.media.MediaControllerManager import melody.offline.music.media.MediaControllerManager
class OfflineSongsAdapter( class OfflineSongsAdapter(
private val context: Context, private val context: Context,
private val list: List<OfflineBean>, private val list: List<PlaylistItem>,
) : RecyclerView.Adapter<OfflineSongsAdapter.ViewHolder>() { ) : RecyclerView.Adapter<OfflineSongsAdapter.ViewHolder>() {
override fun onCreateViewHolder(parent: ViewGroup, viewType: Int): ViewHolder { override fun onCreateViewHolder(parent: ViewGroup, viewType: Int): ViewHolder {
@ -54,7 +54,7 @@ class OfflineSongsAdapter(
RecyclerView.ViewHolder(binding.root) { RecyclerView.ViewHolder(binding.root) {
@SuppressLint("SetTextI18n") @SuppressLint("SetTextI18n")
fun bind(bean: OfflineBean) { fun bind(bean: PlaylistItem) {
binding.apply { binding.apply {
Glide.with(context).load(bean.thumbnail).into(image) Glide.with(context).load(bean.thumbnail).into(image)

View File

@ -29,7 +29,8 @@ class ListMoreBottomSheetDialog(
private val context: Activity, private val context: Activity,
private val playlistItem: PlaylistItem, private val playlistItem: PlaylistItem,
private val lifecycleOwner: LifecycleOwner, private val lifecycleOwner: LifecycleOwner,
private val updateAdapterListener: UpdateAdapterListener private val updateAdapterListener: UpdateAdapterListener,
private val isPlayList: Boolean? = null
) : BottomSheetDialog(context) { ) : BottomSheetDialog(context) {
private var bottomDialogBottomLayout: LinearLayout? = null private var bottomDialogBottomLayout: LinearLayout? = null
private var bottomDialogBottomCloseBtn: LinearLayout? = null private var bottomDialogBottomCloseBtn: LinearLayout? = null
@ -75,6 +76,12 @@ class ListMoreBottomSheetDialog(
} }
private fun initInfoUi() { private fun initInfoUi() {
if (isPlayList == true) {//如果是playlist点击进入则为remove
bottomDialogAddPlaylistTv?.text = context.getString(R.string.remove_from_playlist)
} else {
bottomDialogAddPlaylistTv?.text = context.getString(R.string.add_to_playlist)
}
val bean = playlistItem val bean = playlistItem
Glide.with(context).load(bean.thumbnail).into(bottomDialogSongImg!!) Glide.with(context).load(bean.thumbnail).into(bottomDialogSongImg!!)
bottomDialogTitle?.text = bean.title bottomDialogTitle?.text = bean.title
@ -137,7 +144,7 @@ class ListMoreBottomSheetDialog(
} }
fun updateDownloadBtnUi(b: Boolean) { fun updateDownloadBtnUi(b: Boolean) {
LogTag.LogD(LogTag.VO_TEST_ONLY,"more dialog updateDownloadBtnUi ->$b") LogTag.LogD(LogTag.VO_TEST_ONLY, "more dialog updateDownloadBtnUi ->$b")
if (b) { if (b) {
bottomDialogDownloadLoading?.visibility = View.GONE bottomDialogDownloadLoading?.visibility = View.GONE
bottomDialogDownloadImg?.visibility = View.VISIBLE bottomDialogDownloadImg?.visibility = View.VISIBLE

View File

@ -149,200 +149,4 @@
android:orientation="vertical" /> android:orientation="vertical" />
</RelativeLayout> </RelativeLayout>
</LinearLayout> </LinearLayout>
<LinearLayout
android:id="@+id/bottom_layout"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:layout_alignParentBottom="true"
android:orientation="vertical"
android:visibility="gone">
<View
android:id="@+id/bottom_blank_layout"
android:layout_width="match_parent"
android:layout_height="0dp"
android:layout_marginTop="68dp"
android:layout_weight="3" />
<LinearLayout
android:id="@+id/layout_info"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:background="@drawable/drw_bottom_layout_bg"
android:orientation="vertical"
android:paddingBottom="32dp"
android:visibility="visible">
<LinearLayout
android:id="@+id/bottomCloseBtn"
android:layout_width="match_parent"
android:layout_height="32dp"
android:gravity="center">
<TextView
android:layout_width="30dp"
android:layout_height="4dp"
android:background="@drawable/drw_bottom_close_btn_bg"
android:gravity="center" />
</LinearLayout>
<LinearLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:orientation="vertical"
android:paddingStart="18dp"
android:paddingEnd="18dp">
<LinearLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:gravity="center_vertical"
android:orientation="horizontal">
<androidx.cardview.widget.CardView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:elevation="0dp"
app:cardBackgroundColor="@color/transparent"
app:cardCornerRadius="10dp"
app:cardElevation="0dp">
<ImageView
android:id="@+id/songImg"
android:layout_width="50dp"
android:layout_height="50dp"
android:src="@mipmap/app_logo" />
</androidx.cardview.widget.CardView>
<LinearLayout
android:layout_width="0dp"
android:layout_height="match_parent"
android:layout_marginStart="12dp"
android:layout_marginEnd="12dp"
android:layout_weight="1"
android:gravity="center_vertical"
android:orientation="vertical">
<melody.offline.music.view.MarqueeTextView
android:id="@+id/title"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:fontFamily="@font/regular_font"
android:maxLines="1"
android:text="@string/app_name"
android:textColor="@color/white"
android:textSize="14dp" />
<melody.offline.music.view.MarqueeTextView
android:id="@+id/name"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:fontFamily="@font/regular_font"
android:maxLines="1"
android:text="@string/app_name"
android:textColor="@color/white_60"
android:textSize="12dp" />
</LinearLayout>
<LinearLayout
android:id="@+id/favoritesBtn"
android:layout_width="32dp"
android:layout_height="32dp"
android:background="@drawable/drw_round_48_bg"
android:gravity="center">
<ImageView
android:id="@+id/favoritesImg"
android:layout_width="16dp"
android:layout_height="16dp"
android:src="@drawable/not_favorited_icon" />
</LinearLayout>
</LinearLayout>
<View
android:layout_width="match_parent"
android:layout_height="1dp"
android:layout_marginTop="16dp"
android:background="@color/liner_color" />
<LinearLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:orientation="vertical">
<LinearLayout
android:id="@+id/moreDownloadBtn"
android:layout_width="match_parent"
android:layout_height="48dp"
android:layout_marginTop="4dp"
android:gravity="center_vertical"
android:orientation="horizontal">
<RelativeLayout
android:layout_width="wrap_content"
android:layout_height="wrap_content">
<ImageView
android:id="@+id/downloadImg"
android:layout_width="24dp"
android:layout_height="24dp"
android:src="@drawable/more_downloaded_icon" />
<ProgressBar
android:id="@+id/downloadLoading"
android:layout_width="24dp"
android:layout_height="24dp"
android:indeterminateTint="@color/green"
android:progressBackgroundTint="@color/green"
android:progressTint="@color/green"
android:visibility="gone" />
</RelativeLayout>
<TextView
android:id="@+id/downloadTv"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_marginStart="12dp"
android:text="@string/download_remove_offline"
android:textColor="@color/white"
android:textSize="14dp" />
</LinearLayout>
<LinearLayout
android:id="@+id/moreAddPlaylistBtn"
android:layout_width="match_parent"
android:layout_height="48dp"
android:layout_marginTop="4dp"
android:gravity="center_vertical"
android:orientation="horizontal">
<ImageView
android:layout_width="24dp"
android:layout_height="24dp"
android:src="@drawable/more_add_playlist_icon" />
<TextView
android:id="@+id/addPlaylistTv"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_marginStart="12dp"
android:text="@string/add_to_playlist"
android:textColor="@color/white"
android:textSize="14dp" />
</LinearLayout>
</LinearLayout>
</LinearLayout>
</LinearLayout>
</LinearLayout>
</RelativeLayout> </RelativeLayout>

View File

@ -179,7 +179,7 @@
android:layout_width="wrap_content" android:layout_width="wrap_content"
android:layout_height="wrap_content" android:layout_height="wrap_content"
android:layout_marginStart="12dp" android:layout_marginStart="12dp"
android:text="@string/remove_from_playlist" android:text="@string/add_to_playlist"
android:textColor="@color/white" android:textColor="@color/white"
android:textSize="14dp" /> android:textSize="14dp" />