refactor: remove databinding from base_item, collection_item, episode_item, home_episode_item, person_item, season_header, user_item and user_list_item

Also completely disable databinding in app:phone
This commit is contained in:
jarnedemeulemeester 2023-08-01 09:16:04 +02:00
parent b81025b847
commit 1183ae796c
No known key found for this signature in database
GPG key ID: 1E5C6AFBD622E9F5
18 changed files with 486 additions and 592 deletions

View file

@ -70,7 +70,6 @@ android {
} }
buildFeatures { buildFeatures {
dataBinding = true
viewBinding = true viewBinding = true
} }
} }

View file

@ -3,7 +3,6 @@ package dev.jdtech.jellyfin
import android.view.View import android.view.View
import android.widget.ImageView import android.widget.ImageView
import androidx.annotation.DrawableRes import androidx.annotation.DrawableRes
import androidx.databinding.BindingAdapter
import coil.load import coil.load
import dev.jdtech.jellyfin.api.JellyfinApi import dev.jdtech.jellyfin.api.JellyfinApi
import dev.jdtech.jellyfin.models.FindroidEpisode import dev.jdtech.jellyfin.models.FindroidEpisode
@ -17,7 +16,6 @@ import org.jellyfin.sdk.model.api.ImageType
import java.util.UUID import java.util.UUID
import dev.jdtech.jellyfin.core.R as CoreR import dev.jdtech.jellyfin.core.R as CoreR
@BindingAdapter("itemImage")
fun bindItemImage(imageView: ImageView, item: BaseItemDto) { fun bindItemImage(imageView: ImageView, item: BaseItemDto) {
val itemId = val itemId =
if (item.type == BaseItemKind.EPISODE || item.type == BaseItemKind.SEASON && item.imageTags.isNullOrEmpty()) item.seriesId else item.id if (item.type == BaseItemKind.EPISODE || item.type == BaseItemKind.SEASON && item.imageTags.isNullOrEmpty()) item.seriesId else item.id
@ -27,7 +25,6 @@ fun bindItemImage(imageView: ImageView, item: BaseItemDto) {
.posterDescription(item.name) .posterDescription(item.name)
} }
@BindingAdapter("itemImage")
fun bindItemImage(imageView: ImageView, item: FindroidItem) { fun bindItemImage(imageView: ImageView, item: FindroidItem) {
val itemId = when (item) { val itemId = when (item) {
is FindroidEpisode -> item.seriesId is FindroidEpisode -> item.seriesId
@ -39,7 +36,6 @@ fun bindItemImage(imageView: ImageView, item: FindroidItem) {
.posterDescription(item.name) .posterDescription(item.name)
} }
@BindingAdapter("itemBackdropImage")
fun bindItemBackdropImage(imageView: ImageView, item: FindroidItem?) { fun bindItemBackdropImage(imageView: ImageView, item: FindroidItem?) {
if (item == null) return if (item == null) return
@ -48,19 +44,16 @@ fun bindItemBackdropImage(imageView: ImageView, item: FindroidItem?) {
.backdropDescription(item.name) .backdropDescription(item.name)
} }
@BindingAdapter("itemBackdropById")
fun bindItemBackdropById(imageView: ImageView, itemId: UUID) { fun bindItemBackdropById(imageView: ImageView, itemId: UUID) {
imageView.loadImage("/items/$itemId/Images/${ImageType.BACKDROP}") imageView.loadImage("/items/$itemId/Images/${ImageType.BACKDROP}")
} }
@BindingAdapter("personImage")
fun bindPersonImage(imageView: ImageView, person: BaseItemPerson) { fun bindPersonImage(imageView: ImageView, person: BaseItemPerson) {
imageView imageView
.loadImage("/items/${person.id}/Images/${ImageType.PRIMARY}", placeholderId = CoreR.drawable.person_placeholder) .loadImage("/items/${person.id}/Images/${ImageType.PRIMARY}", placeholderId = CoreR.drawable.person_placeholder)
.posterDescription(person.name) .posterDescription(person.name)
} }
@BindingAdapter("cardItemImage")
fun bindCardItemImage(imageView: ImageView, item: FindroidItem) { fun bindCardItemImage(imageView: ImageView, item: FindroidItem) {
val imageType = when (item) { val imageType = when (item) {
is FindroidMovie -> ImageType.BACKDROP is FindroidMovie -> ImageType.BACKDROP
@ -72,12 +65,10 @@ fun bindCardItemImage(imageView: ImageView, item: FindroidItem) {
.posterDescription(item.name) .posterDescription(item.name)
} }
@BindingAdapter("seasonPoster")
fun bindSeasonPoster(imageView: ImageView, seasonId: UUID) { fun bindSeasonPoster(imageView: ImageView, seasonId: UUID) {
imageView.loadImage("/items/$seasonId/Images/${ImageType.PRIMARY}") imageView.loadImage("/items/$seasonId/Images/${ImageType.PRIMARY}")
} }
@BindingAdapter("userImage")
fun bindUserImage(imageView: ImageView, user: User) { fun bindUserImage(imageView: ImageView, user: User) {
imageView imageView
.loadImage("/users/${user.id}/Images/${ImageType.PRIMARY}", placeholderId = CoreR.drawable.user_placeholder) .loadImage("/users/${user.id}/Images/${ImageType.PRIMARY}", placeholderId = CoreR.drawable.user_placeholder)

View file

@ -5,6 +5,7 @@ import android.view.ViewGroup
import androidx.recyclerview.widget.DiffUtil import androidx.recyclerview.widget.DiffUtil
import androidx.recyclerview.widget.ListAdapter import androidx.recyclerview.widget.ListAdapter
import androidx.recyclerview.widget.RecyclerView import androidx.recyclerview.widget.RecyclerView
import dev.jdtech.jellyfin.bindCardItemImage
import dev.jdtech.jellyfin.databinding.CollectionItemBinding import dev.jdtech.jellyfin.databinding.CollectionItemBinding
import dev.jdtech.jellyfin.models.FindroidCollection import dev.jdtech.jellyfin.models.FindroidCollection
@ -14,8 +15,8 @@ class CollectionListAdapter(
class CollectionViewHolder(private var binding: CollectionItemBinding) : class CollectionViewHolder(private var binding: CollectionItemBinding) :
RecyclerView.ViewHolder(binding.root) { RecyclerView.ViewHolder(binding.root) {
fun bind(collection: FindroidCollection) { fun bind(collection: FindroidCollection) {
binding.collection = collection binding.collectionName.text = collection.name
binding.executePendingBindings() bindCardItemImage(binding.collectionImage, collection)
} }
} }

View file

@ -8,6 +8,9 @@ import androidx.core.view.isVisible
import androidx.recyclerview.widget.DiffUtil import androidx.recyclerview.widget.DiffUtil
import androidx.recyclerview.widget.ListAdapter import androidx.recyclerview.widget.ListAdapter
import androidx.recyclerview.widget.RecyclerView import androidx.recyclerview.widget.RecyclerView
import dev.jdtech.jellyfin.bindCardItemImage
import dev.jdtech.jellyfin.bindItemBackdropById
import dev.jdtech.jellyfin.bindSeasonPoster
import dev.jdtech.jellyfin.databinding.EpisodeItemBinding import dev.jdtech.jellyfin.databinding.EpisodeItemBinding
import dev.jdtech.jellyfin.databinding.SeasonHeaderBinding import dev.jdtech.jellyfin.databinding.SeasonHeaderBinding
import dev.jdtech.jellyfin.models.EpisodeItem import dev.jdtech.jellyfin.models.EpisodeItem
@ -26,25 +29,24 @@ class EpisodeListAdapter(
class HeaderViewHolder(private var binding: SeasonHeaderBinding) : class HeaderViewHolder(private var binding: SeasonHeaderBinding) :
RecyclerView.ViewHolder(binding.root) { RecyclerView.ViewHolder(binding.root) {
fun bind(header: EpisodeItem.Header) { fun bind(header: EpisodeItem.Header) {
binding.seriesId = header.seriesId
binding.seasonId = header.seasonId
binding.seasonName.text = header.seasonName binding.seasonName.text = header.seasonName
binding.seriesName.text = header.seriesName binding.seriesName.text = header.seriesName
binding.executePendingBindings() bindItemBackdropById(binding.itemBanner, header.seriesId)
bindSeasonPoster(binding.seasonPoster, header.seasonId)
} }
} }
class EpisodeViewHolder(private var binding: EpisodeItemBinding) : class EpisodeViewHolder(private var binding: EpisodeItemBinding) :
RecyclerView.ViewHolder(binding.root) { RecyclerView.ViewHolder(binding.root) {
fun bind(episode: FindroidEpisode) { fun bind(episode: FindroidEpisode) {
binding.episode = episode
binding.episodeTitle.text = if (episode.indexNumberEnd == null) { binding.episodeTitle.text = if (episode.indexNumberEnd == null) {
binding.root.context.getString(CoreR.string.episode_name, episode.indexNumber, episode.name) binding.root.context.getString(CoreR.string.episode_name, episode.indexNumber, episode.name)
} else { } else {
binding.root.context.getString(CoreR.string.episode_name_with_end, episode.indexNumber, episode.indexNumberEnd, episode.name) binding.root.context.getString(CoreR.string.episode_name_with_end, episode.indexNumber, episode.indexNumberEnd, episode.name)
} }
binding.episodeOverview.text = episode.overview
if (episode.playbackPositionTicks > 0) { if (episode.playbackPositionTicks > 0) {
binding.progressBar.layoutParams.width = TypedValue.applyDimension( binding.progressBar.layoutParams.width = TypedValue.applyDimension(
TypedValue.COMPLEX_UNIT_DIP, TypedValue.COMPLEX_UNIT_DIP,
@ -56,9 +58,11 @@ class EpisodeListAdapter(
binding.progressBar.visibility = View.GONE binding.progressBar.visibility = View.GONE
} }
binding.playedIcon.isVisible = episode.played
binding.missingIcon.isVisible = episode.missing
binding.downloadedIcon.isVisible = episode.isDownloaded() binding.downloadedIcon.isVisible = episode.isDownloaded()
binding.executePendingBindings() bindCardItemImage(binding.episodeImage, episode)
} }
} }

View file

@ -8,6 +8,7 @@ import androidx.core.view.isVisible
import androidx.recyclerview.widget.DiffUtil import androidx.recyclerview.widget.DiffUtil
import androidx.recyclerview.widget.ListAdapter import androidx.recyclerview.widget.ListAdapter
import androidx.recyclerview.widget.RecyclerView import androidx.recyclerview.widget.RecyclerView
import dev.jdtech.jellyfin.bindCardItemImage
import dev.jdtech.jellyfin.databinding.HomeEpisodeItemBinding import dev.jdtech.jellyfin.databinding.HomeEpisodeItemBinding
import dev.jdtech.jellyfin.models.FindroidEpisode import dev.jdtech.jellyfin.models.FindroidEpisode
import dev.jdtech.jellyfin.models.FindroidItem import dev.jdtech.jellyfin.models.FindroidItem
@ -22,7 +23,6 @@ class HomeEpisodeListAdapter(private val onClickListener: OnClickListener) : Lis
) : ) :
RecyclerView.ViewHolder(binding.root) { RecyclerView.ViewHolder(binding.root) {
fun bind(item: FindroidItem) { fun bind(item: FindroidItem) {
binding.item = item
if (item.playbackPositionTicks > 0) { if (item.playbackPositionTicks > 0) {
binding.progressBar.layoutParams.width = TypedValue.applyDimension( binding.progressBar.layoutParams.width = TypedValue.applyDimension(
TypedValue.COMPLEX_UNIT_DIP, TypedValue.COMPLEX_UNIT_DIP,
@ -49,7 +49,7 @@ class HomeEpisodeListAdapter(private val onClickListener: OnClickListener) : Lis
} }
} }
binding.executePendingBindings() bindCardItemImage(binding.episodeImage, item)
} }
} }

View file

@ -5,6 +5,7 @@ import android.view.ViewGroup
import androidx.recyclerview.widget.DiffUtil import androidx.recyclerview.widget.DiffUtil
import androidx.recyclerview.widget.ListAdapter import androidx.recyclerview.widget.ListAdapter
import androidx.recyclerview.widget.RecyclerView import androidx.recyclerview.widget.RecyclerView
import dev.jdtech.jellyfin.bindPersonImage
import dev.jdtech.jellyfin.databinding.PersonItemBinding import dev.jdtech.jellyfin.databinding.PersonItemBinding
import org.jellyfin.sdk.model.api.BaseItemPerson import org.jellyfin.sdk.model.api.BaseItemPerson
@ -13,8 +14,9 @@ class PersonListAdapter(private val clickListener: (item: BaseItemPerson) -> Uni
class PersonViewHolder(private var binding: PersonItemBinding) : class PersonViewHolder(private var binding: PersonItemBinding) :
RecyclerView.ViewHolder(binding.root) { RecyclerView.ViewHolder(binding.root) {
fun bind(person: BaseItemPerson) { fun bind(person: BaseItemPerson) {
binding.person = person binding.personName.text = person.name
binding.executePendingBindings() binding.personRole.text = person.role
bindPersonImage(binding.personImage, person)
} }
} }

View file

@ -5,6 +5,7 @@ import android.view.ViewGroup
import androidx.recyclerview.widget.DiffUtil import androidx.recyclerview.widget.DiffUtil
import androidx.recyclerview.widget.ListAdapter import androidx.recyclerview.widget.ListAdapter
import androidx.recyclerview.widget.RecyclerView import androidx.recyclerview.widget.RecyclerView
import dev.jdtech.jellyfin.bindUserImage
import dev.jdtech.jellyfin.databinding.UserListItemBinding import dev.jdtech.jellyfin.databinding.UserListItemBinding
import dev.jdtech.jellyfin.models.User import dev.jdtech.jellyfin.models.User
@ -15,8 +16,8 @@ class UserListAdapter(
class UserViewHolder(private var binding: UserListItemBinding) : class UserViewHolder(private var binding: UserListItemBinding) :
RecyclerView.ViewHolder(binding.root) { RecyclerView.ViewHolder(binding.root) {
fun bind(user: User) { fun bind(user: User) {
binding.user = user binding.userName.text = user.name
binding.executePendingBindings() bindUserImage(binding.userImage, user)
} }
} }

View file

@ -5,6 +5,7 @@ import android.view.ViewGroup
import androidx.recyclerview.widget.DiffUtil import androidx.recyclerview.widget.DiffUtil
import androidx.recyclerview.widget.ListAdapter import androidx.recyclerview.widget.ListAdapter
import androidx.recyclerview.widget.RecyclerView import androidx.recyclerview.widget.RecyclerView
import dev.jdtech.jellyfin.bindUserImage
import dev.jdtech.jellyfin.databinding.UserItemBinding import dev.jdtech.jellyfin.databinding.UserItemBinding
import dev.jdtech.jellyfin.models.User import dev.jdtech.jellyfin.models.User
@ -14,8 +15,8 @@ class UserLoginListAdapter(
class UserLoginViewHolder(private var binding: UserItemBinding) : class UserLoginViewHolder(private var binding: UserItemBinding) :
RecyclerView.ViewHolder(binding.root) { RecyclerView.ViewHolder(binding.root) {
fun bind(user: User) { fun bind(user: User) {
binding.user = user binding.userName.text = user.name
binding.executePendingBindings() bindUserImage(binding.userImage, user)
} }
} }

View file

@ -7,6 +7,7 @@ import androidx.core.view.isVisible
import androidx.recyclerview.widget.DiffUtil import androidx.recyclerview.widget.DiffUtil
import androidx.recyclerview.widget.ListAdapter import androidx.recyclerview.widget.ListAdapter
import androidx.recyclerview.widget.RecyclerView import androidx.recyclerview.widget.RecyclerView
import dev.jdtech.jellyfin.bindItemImage
import dev.jdtech.jellyfin.databinding.BaseItemBinding import dev.jdtech.jellyfin.databinding.BaseItemBinding
import dev.jdtech.jellyfin.models.FindroidEpisode import dev.jdtech.jellyfin.models.FindroidEpisode
import dev.jdtech.jellyfin.models.FindroidItem import dev.jdtech.jellyfin.models.FindroidItem
@ -21,7 +22,6 @@ class ViewItemListAdapter(
class ItemViewHolder(private var binding: BaseItemBinding, private val parent: ViewGroup) : class ItemViewHolder(private var binding: BaseItemBinding, private val parent: ViewGroup) :
RecyclerView.ViewHolder(binding.root) { RecyclerView.ViewHolder(binding.root) {
fun bind(item: FindroidItem, fixedWidth: Boolean) { fun bind(item: FindroidItem, fixedWidth: Boolean) {
binding.item = item
binding.itemName.text = if (item is FindroidEpisode) item.seriesName else item.name binding.itemName.text = if (item is FindroidEpisode) item.seriesName else item.name
binding.itemCount.visibility = binding.itemCount.visibility =
if (item.unplayedItemCount != null && item.unplayedItemCount!! > 0) View.VISIBLE else View.GONE if (item.unplayedItemCount != null && item.unplayedItemCount!! > 0) View.VISIBLE else View.GONE
@ -31,9 +31,11 @@ class ViewItemListAdapter(
(binding.itemLayout.layoutParams as ViewGroup.MarginLayoutParams).bottomMargin = 0 (binding.itemLayout.layoutParams as ViewGroup.MarginLayoutParams).bottomMargin = 0
} }
binding.itemCount.text = item.unplayedItemCount.toString()
binding.playedIcon.isVisible = item.played
binding.downloadedIcon.isVisible = item.isDownloaded() binding.downloadedIcon.isVisible = item.isDownloaded()
binding.executePendingBindings() bindItemImage(binding.itemImage, item)
} }
} }

View file

@ -7,6 +7,7 @@ import androidx.core.view.isVisible
import androidx.paging.PagingDataAdapter import androidx.paging.PagingDataAdapter
import androidx.recyclerview.widget.DiffUtil import androidx.recyclerview.widget.DiffUtil
import androidx.recyclerview.widget.RecyclerView import androidx.recyclerview.widget.RecyclerView
import dev.jdtech.jellyfin.bindItemImage
import dev.jdtech.jellyfin.databinding.BaseItemBinding import dev.jdtech.jellyfin.databinding.BaseItemBinding
import dev.jdtech.jellyfin.models.FindroidEpisode import dev.jdtech.jellyfin.models.FindroidEpisode
import dev.jdtech.jellyfin.models.FindroidItem import dev.jdtech.jellyfin.models.FindroidItem
@ -21,7 +22,6 @@ class ViewItemPagingAdapter(
class ItemViewHolder(private var binding: BaseItemBinding, private val parent: ViewGroup) : class ItemViewHolder(private var binding: BaseItemBinding, private val parent: ViewGroup) :
RecyclerView.ViewHolder(binding.root) { RecyclerView.ViewHolder(binding.root) {
fun bind(item: FindroidItem, fixedWidth: Boolean) { fun bind(item: FindroidItem, fixedWidth: Boolean) {
binding.item = item
binding.itemName.text = binding.itemName.text =
if (item is FindroidEpisode) item.seriesName else item.name if (item is FindroidEpisode) item.seriesName else item.name
binding.itemCount.visibility = binding.itemCount.visibility =
@ -32,9 +32,11 @@ class ViewItemPagingAdapter(
(binding.itemLayout.layoutParams as ViewGroup.MarginLayoutParams).bottomMargin = 0 (binding.itemLayout.layoutParams as ViewGroup.MarginLayoutParams).bottomMargin = 0
} }
binding.itemCount.text = item.unplayedItemCount.toString()
binding.playedIcon.isVisible = item.played
binding.downloadedIcon.isVisible = item.isDownloaded() binding.downloadedIcon.isVisible = item.isDownloaded()
binding.executePendingBindings() bindItemImage(binding.itemImage, item)
} }
} }

View file

@ -1,103 +1,88 @@
<?xml version="1.0" encoding="utf-8"?> <?xml version="1.0" encoding="utf-8"?>
<layout xmlns:android="http://schemas.android.com/apk/res/android" <androidx.constraintlayout.widget.ConstraintLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto" xmlns:app="http://schemas.android.com/apk/res-auto"
xmlns:tools="http://schemas.android.com/tools"> xmlns:tools="http://schemas.android.com/tools"
android:id="@+id/item_layout"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_marginHorizontal="12dp"
android:layout_marginBottom="24dp"
android:clickable="true"
android:focusable="true"
android:foreground="@drawable/ripple_background"
android:orientation="vertical">
<data> <com.google.android.material.imageview.ShapeableImageView
android:id="@+id/item_image"
android:layout_width="0dp"
android:layout_height="0dp"
android:scaleType="centerCrop"
app:layout_constraintDimensionRatio="H,2:3"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toTopOf="parent"
app:shapeAppearanceOverlay="@style/ShapeAppearanceOverlay.Findroid.Image" />
<import type="android.view.View" /> <TextView
android:id="@+id/item_name"
<variable android:layout_width="wrap_content"
name="item"
type="dev.jdtech.jellyfin.models.FindroidItem" />
</data>
<androidx.constraintlayout.widget.ConstraintLayout
android:id="@+id/item_layout"
android:layout_width="match_parent"
android:layout_height="wrap_content" android:layout_height="wrap_content"
android:layout_marginHorizontal="12dp" android:layout_marginTop="4dp"
android:layout_marginBottom="24dp" android:ellipsize="end"
android:clickable="true" android:maxLines="2"
android:focusable="true" android:textAppearance="@style/TextAppearance.Material3.BodyMedium"
android:foreground="@drawable/ripple_background" app:layout_constraintStart_toStartOf="parent"
android:orientation="vertical"> app:layout_constraintTop_toBottomOf="@id/item_image"
tools:text="Movie title" />
<com.google.android.material.imageview.ShapeableImageView <LinearLayout
android:id="@+id/item_image" android:layout_width="wrap_content"
android:layout_width="0dp" android:layout_height="wrap_content"
android:layout_height="0dp" android:layout_marginTop="8dp"
android:scaleType="centerCrop" android:layout_marginEnd="8dp"
app:itemImage="@{item}" android:orientation="horizontal"
app:layout_constraintDimensionRatio="H,2:3" app:layout_constraintEnd_toEndOf="@id/item_image"
app:layout_constraintEnd_toEndOf="parent" app:layout_constraintTop_toTopOf="@id/item_image">
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toTopOf="parent" <ImageView
app:shapeAppearanceOverlay="@style/ShapeAppearanceOverlay.Findroid.Image" /> android:id="@+id/downloaded_icon"
android:layout_width="24dp"
android:layout_height="24dp"
android:layout_marginStart="8dp"
android:background="@drawable/circle_background"
android:contentDescription="@string/downloaded_indicator"
android:padding="4dp"
android:src="@drawable/ic_download"
android:visibility="gone"
app:tint="?attr/colorOnPrimary"
tools:visibility="visible" />
<TextView <TextView
android:id="@+id/item_name" android:id="@+id/item_count"
android:layout_width="wrap_content" android:layout_width="24dp"
android:layout_height="wrap_content" android:layout_height="24dp"
android:layout_marginTop="4dp" android:layout_marginStart="8dp"
android:ellipsize="end" android:background="@drawable/circle_background"
android:maxLines="2" android:gravity="center"
android:textAppearance="@style/TextAppearance.Material3.BodyMedium" android:textAppearance="@style/TextAppearance.Material3.BodySmall"
app:layout_constraintStart_toStartOf="parent" android:textColor="?attr/colorOnPrimary"
app:layout_constraintTop_toBottomOf="@id/item_image" app:layout_constraintEnd_toEndOf="parent"
tools:text="Movie title" /> app:layout_constraintTop_toTopOf="parent"
tools:text="9" />
<LinearLayout <ImageView
android:layout_width="wrap_content" android:id="@+id/played_icon"
android:layout_height="wrap_content" android:layout_width="24dp"
android:orientation="horizontal" android:layout_height="24dp"
android:layout_marginTop="8dp" android:layout_marginStart="8dp"
android:layout_marginEnd="8dp" android:background="@drawable/circle_background"
android:contentDescription="@string/episode_watched_indicator"
android:padding="4dp"
android:src="@drawable/ic_check"
app:layout_constraintEnd_toEndOf="@id/item_image" app:layout_constraintEnd_toEndOf="@id/item_image"
app:layout_constraintTop_toTopOf="@id/item_image"> app:layout_constraintTop_toTopOf="@id/item_image"
app:tint="?attr/colorOnPrimary" />
<ImageView </LinearLayout>
android:id="@+id/downloaded_icon"
android:layout_width="24dp"
android:layout_height="24dp"
android:layout_marginStart="8dp"
android:background="@drawable/circle_background"
android:contentDescription="@string/downloaded_indicator"
android:padding="4dp"
android:src="@drawable/ic_download"
android:visibility="gone"
app:tint="?attr/colorOnPrimary"
tools:visibility="visible"/>
<TextView </androidx.constraintlayout.widget.ConstraintLayout>
android:id="@+id/item_count"
android:layout_width="24dp"
android:layout_height="24dp"
android:layout_marginStart="8dp"
android:background="@drawable/circle_background"
android:gravity="center"
android:text="@{item.unplayedItemCount.toString()}"
android:textAppearance="@style/TextAppearance.Material3.BodySmall"
android:textColor="?attr/colorOnPrimary"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintTop_toTopOf="parent"
tools:text="9" />
<ImageView
android:id="@+id/played_icon"
android:layout_width="24dp"
android:layout_height="24dp"
android:layout_marginStart="8dp"
android:background="@drawable/circle_background"
android:contentDescription="@string/episode_watched_indicator"
android:padding="4dp"
android:src="@drawable/ic_check"
android:visibility="@{item.played == true ? View.VISIBLE : View.GONE}"
app:layout_constraintEnd_toEndOf="@id/item_image"
app:layout_constraintTop_toTopOf="@id/item_image"
app:tint="?attr/colorOnPrimary" />
</LinearLayout>
</androidx.constraintlayout.widget.ConstraintLayout>
</layout>

View file

@ -1,47 +1,36 @@
<?xml version="1.0" encoding="utf-8"?> <?xml version="1.0" encoding="utf-8"?>
<layout xmlns:android="http://schemas.android.com/apk/res/android" <androidx.constraintlayout.widget.ConstraintLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto" xmlns:app="http://schemas.android.com/apk/res-auto"
xmlns:tools="http://schemas.android.com/tools"> xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_marginHorizontal="12dp"
android:layout_marginBottom="24dp"
android:clickable="true"
android:focusable="true"
android:foreground="@drawable/ripple_background"
android:orientation="vertical">
<data> <com.google.android.material.imageview.ShapeableImageView
android:id="@+id/collection_image"
android:layout_width="0dp"
android:layout_height="0dp"
android:adjustViewBounds="true"
android:scaleType="centerCrop"
app:layout_constraintDimensionRatio="H,16:9"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toTopOf="parent"
app:shapeAppearanceOverlay="@style/ShapeAppearanceOverlay.Findroid.Image" />
<variable <TextView
name="collection" android:id="@+id/collection_name"
type="dev.jdtech.jellyfin.models.FindroidCollection" /> android:layout_width="0dp"
</data>
<androidx.constraintlayout.widget.ConstraintLayout
android:layout_width="match_parent"
android:layout_height="wrap_content" android:layout_height="wrap_content"
android:layout_marginHorizontal="12dp" android:layout_marginTop="4dp"
android:layout_marginBottom="24dp" android:textAppearance="@style/TextAppearance.Material3.BodyMedium"
android:clickable="true" app:layout_constraintEnd_toEndOf="parent"
android:focusable="true" app:layout_constraintStart_toStartOf="parent"
android:foreground="@drawable/ripple_background" app:layout_constraintTop_toBottomOf="@id/collection_image"
android:orientation="vertical"> tools:text="Movies" />
</androidx.constraintlayout.widget.ConstraintLayout>
<com.google.android.material.imageview.ShapeableImageView
android:id="@+id/collection_image"
android:layout_width="0dp"
android:layout_height="0dp"
android:adjustViewBounds="true"
android:scaleType="centerCrop"
app:cardItemImage="@{collection}"
app:layout_constraintDimensionRatio="H,16:9"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toTopOf="parent"
app:shapeAppearanceOverlay="@style/ShapeAppearanceOverlay.Findroid.Image" />
<TextView
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_marginTop="4dp"
android:text="@{collection.name}"
android:textAppearance="@style/TextAppearance.Material3.BodyMedium"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toBottomOf="@id/collection_image"
tools:text="Movies" />
</androidx.constraintlayout.widget.ConstraintLayout>
</layout>

View file

@ -1,143 +1,127 @@
<?xml version="1.0" encoding="utf-8"?> <?xml version="1.0" encoding="utf-8"?>
<layout xmlns:android="http://schemas.android.com/apk/res/android" <androidx.constraintlayout.widget.ConstraintLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto" xmlns:app="http://schemas.android.com/apk/res-auto"
xmlns:tools="http://schemas.android.com/tools"> xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="100dp"
android:layout_marginHorizontal="24dp"
android:layout_marginBottom="24dp"
android:clickable="true"
android:focusable="true"
android:foreground="@drawable/ripple_background">
<data> <com.google.android.material.imageview.ShapeableImageView
android:id="@+id/episode_image"
<import type="android.view.View" /> android:layout_width="100dp"
<variable
name="episode"
type="dev.jdtech.jellyfin.models.FindroidEpisode" />
</data>
<androidx.constraintlayout.widget.ConstraintLayout
android:layout_width="match_parent"
android:layout_height="100dp" android:layout_height="100dp"
android:layout_marginHorizontal="24dp" android:scaleType="centerCrop"
android:layout_marginBottom="24dp" app:layout_constraintBottom_toBottomOf="parent"
android:clickable="true" app:layout_constraintStart_toStartOf="parent"
android:focusable="true" app:layout_constraintTop_toTopOf="parent"
android:foreground="@drawable/ripple_background"> app:shapeAppearanceOverlay="@style/ShapeAppearanceOverlay.Findroid.Image" />
<com.google.android.material.imageview.ShapeableImageView <LinearLayout
android:id="@+id/episode_image" android:layout_width="wrap_content"
android:layout_width="100dp" android:layout_height="wrap_content"
android:layout_height="100dp" android:layout_marginTop="8dp"
android:scaleType="centerCrop" android:layout_marginEnd="8dp"
app:cardItemImage="@{episode}" android:orientation="horizontal"
app:layout_constraintBottom_toBottomOf="parent" app:layout_constraintEnd_toEndOf="@id/episode_image"
app:layout_constraintStart_toStartOf="parent" app:layout_constraintTop_toTopOf="@id/episode_image">
app:layout_constraintTop_toTopOf="parent"
app:shapeAppearanceOverlay="@style/ShapeAppearanceOverlay.Findroid.Image" />
<LinearLayout <ImageView
android:layout_width="wrap_content" android:id="@+id/downloaded_icon"
android:layout_height="wrap_content" android:layout_width="24dp"
android:layout_marginTop="8dp" android:layout_height="24dp"
android:layout_marginEnd="8dp" android:layout_marginStart="8dp"
android:orientation="horizontal" android:background="@drawable/circle_background"
app:layout_constraintEnd_toEndOf="@id/episode_image" android:contentDescription="@string/downloaded_indicator"
app:layout_constraintTop_toTopOf="@id/episode_image"> android:padding="4dp"
android:src="@drawable/ic_download"
<ImageView
android:id="@+id/downloaded_icon"
android:layout_width="24dp"
android:layout_height="24dp"
android:layout_marginStart="8dp"
android:background="@drawable/circle_background"
android:contentDescription="@string/downloaded_indicator"
android:padding="4dp"
android:src="@drawable/ic_download"
android:visibility="gone"
app:layout_constraintEnd_toEndOf="@id/episode_image"
app:layout_constraintTop_toTopOf="@id/episode_image"
app:tint="?attr/colorOnPrimary"
tools:visibility="visible" />
<FrameLayout
android:id="@+id/missing_icon"
android:layout_width="24dp"
android:layout_height="24dp"
android:layout_marginStart="8dp"
android:background="@drawable/circle_background"
android:backgroundTint="?attr/colorError"
android:visibility="@{episode.missing ? View.VISIBLE : View.GONE}"
app:layout_constraintEnd_toStartOf="@id/played_icon"
app:layout_constraintTop_toTopOf="@id/episode_image"
tools:visibility="visible">
<TextView
android:layout_width="match_parent"
android:layout_height="match_parent"
android:gravity="center"
android:text="M"
android:textColor="@android:color/white"
tools:ignore="HardcodedText" />
</FrameLayout>
<ImageView
android:id="@+id/played_icon"
android:layout_width="24dp"
android:layout_height="24dp"
android:layout_marginStart="8dp"
android:background="@drawable/circle_background"
android:contentDescription="@string/episode_watched_indicator"
android:padding="4dp"
android:src="@drawable/ic_check"
android:visibility="@{episode.played ? View.VISIBLE : View.GONE}"
app:layout_constraintEnd_toEndOf="@id/episode_image"
app:layout_constraintTop_toTopOf="@id/episode_image"
app:tint="?attr/colorOnPrimary" />
</LinearLayout>
<FrameLayout
android:id="@+id/progress_bar"
android:layout_width="wrap_content"
android:layout_height="4dp"
android:layout_marginHorizontal="8dp"
android:layout_marginBottom="8dp"
android:background="@drawable/button_setup_background"
android:visibility="gone" android:visibility="gone"
app:layout_constraintBottom_toBottomOf="@id/episode_image" app:layout_constraintEnd_toEndOf="@id/episode_image"
app:layout_constraintStart_toStartOf="@id/episode_image" app:layout_constraintTop_toTopOf="@id/episode_image"
tools:layout_width="50dp" app:tint="?attr/colorOnPrimary"
tools:visibility="visible" /> tools:visibility="visible" />
<TextView
android:id="@+id/episode_title"
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_marginStart="12dp"
android:textAppearance="@style/TextAppearance.Material3.BodyMedium"
app:layout_constraintBottom_toTopOf="@id/episode_desc"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toEndOf="@id/episode_image"
app:layout_constraintTop_toTopOf="parent"
tools:text="1. To You, in 2000 Years: The Fall of Shiganshina, Part 1" />
<TextView
android:id="@+id/episode_desc"
android:layout_width="0dp"
android:layout_height="0dp"
android:scrollbars="none"
android:text="@{episode.overview}"
android:textAppearance="@style/TextAppearance.Material3.BodySmall"
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toStartOf="@id/episode_title"
app:layout_constraintTop_toBottomOf="@id/episode_title"
tools:text="After one hundred years of peace, humanity is suddenly reminded of the terror of being at the Titans' mercy. After one hundred years of peace, humanity is suddenly reminded of the terror of being at the Titans' mercy." />
<FrameLayout <FrameLayout
android:layout_width="0dp" android:id="@+id/missing_icon"
android:layout_width="24dp"
android:layout_height="24dp" android:layout_height="24dp"
android:background="@drawable/header_gradient" android:layout_marginStart="8dp"
app:layout_constraintBottom_toBottomOf="@id/episode_desc" android:background="@drawable/circle_background"
app:layout_constraintEnd_toEndOf="@id/episode_desc" android:backgroundTint="?attr/colorError"
app:layout_constraintStart_toStartOf="@id/episode_desc" /> app:layout_constraintEnd_toStartOf="@id/played_icon"
</androidx.constraintlayout.widget.ConstraintLayout> app:layout_constraintTop_toTopOf="@id/episode_image"
</layout> tools:visibility="visible">
<TextView
android:layout_width="match_parent"
android:layout_height="match_parent"
android:gravity="center"
android:text="M"
android:textColor="@android:color/white"
tools:ignore="HardcodedText" />
</FrameLayout>
<ImageView
android:id="@+id/played_icon"
android:layout_width="24dp"
android:layout_height="24dp"
android:layout_marginStart="8dp"
android:background="@drawable/circle_background"
android:contentDescription="@string/episode_watched_indicator"
android:padding="4dp"
android:src="@drawable/ic_check"
app:layout_constraintEnd_toEndOf="@id/episode_image"
app:layout_constraintTop_toTopOf="@id/episode_image"
app:tint="?attr/colorOnPrimary" />
</LinearLayout>
<FrameLayout
android:id="@+id/progress_bar"
android:layout_width="wrap_content"
android:layout_height="4dp"
android:layout_marginHorizontal="8dp"
android:layout_marginBottom="8dp"
android:background="@drawable/button_setup_background"
android:visibility="gone"
app:layout_constraintBottom_toBottomOf="@id/episode_image"
app:layout_constraintStart_toStartOf="@id/episode_image"
tools:layout_width="50dp"
tools:visibility="visible" />
<TextView
android:id="@+id/episode_title"
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_marginStart="12dp"
android:textAppearance="@style/TextAppearance.Material3.BodyMedium"
app:layout_constraintBottom_toTopOf="@id/episode_overview"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toEndOf="@id/episode_image"
app:layout_constraintTop_toTopOf="parent"
tools:text="1. To You, in 2000 Years: The Fall of Shiganshina, Part 1" />
<TextView
android:id="@+id/episode_overview"
android:layout_width="0dp"
android:layout_height="0dp"
android:scrollbars="none"
android:textAppearance="@style/TextAppearance.Material3.BodySmall"
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toStartOf="@id/episode_title"
app:layout_constraintTop_toBottomOf="@id/episode_title"
tools:text="After one hundred years of peace, humanity is suddenly reminded of the terror of being at the Titans' mercy. After one hundred years of peace, humanity is suddenly reminded of the terror of being at the Titans' mercy." />
<FrameLayout
android:layout_width="0dp"
android:layout_height="24dp"
android:background="@drawable/header_gradient"
app:layout_constraintBottom_toBottomOf="@id/episode_overview"
app:layout_constraintEnd_toEndOf="@id/episode_overview"
app:layout_constraintStart_toStartOf="@id/episode_overview" />
</androidx.constraintlayout.widget.ConstraintLayout>

View file

@ -1,88 +1,77 @@
<?xml version="1.0" encoding="utf-8"?> <?xml version="1.0" encoding="utf-8"?>
<layout xmlns:android="http://schemas.android.com/apk/res/android" <androidx.constraintlayout.widget.ConstraintLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto" xmlns:app="http://schemas.android.com/apk/res-auto"
xmlns:tools="http://schemas.android.com/tools"> xmlns:tools="http://schemas.android.com/tools"
android:layout_width="240dp"
android:layout_height="wrap_content"
android:layout_marginHorizontal="12dp"
android:clickable="true"
android:focusable="true"
android:foreground="@drawable/ripple_background">
<data> <com.google.android.material.imageview.ShapeableImageView
android:id="@+id/episode_image"
android:layout_width="0dp"
android:layout_height="0dp"
android:scaleType="centerCrop"
app:layout_constraintDimensionRatio="H,16:9"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toTopOf="parent"
app:shapeAppearanceOverlay="@style/ShapeAppearanceOverlay.Findroid.Image" />
<variable <TextView
name="item" android:id="@+id/primary_name"
type="dev.jdtech.jellyfin.models.FindroidItem" /> android:layout_width="0dp"
</data>
<androidx.constraintlayout.widget.ConstraintLayout
android:layout_width="240dp"
android:layout_height="wrap_content" android:layout_height="wrap_content"
android:layout_marginHorizontal="12dp" android:layout_marginTop="4dp"
android:clickable="true" android:ellipsize="end"
android:focusable="true" android:maxLines="1"
android:foreground="@drawable/ripple_background"> android:textAppearance="@style/TextAppearance.Material3.BodyMedium"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toBottomOf="@id/episode_image"
tools:text="Wonder Egg Priority" />
<com.google.android.material.imageview.ShapeableImageView <TextView
android:id="@+id/episode_image" android:id="@+id/secondary_name"
android:layout_width="0dp" android:layout_width="0dp"
android:layout_height="0dp" android:layout_height="wrap_content"
android:scaleType="centerCrop" android:ellipsize="end"
app:cardItemImage="@{item}" android:maxLines="1"
app:layout_constraintDimensionRatio="H,16:9" android:textAppearance="@style/TextAppearance.Material3.BodySmall"
app:layout_constraintEnd_toEndOf="parent" app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toStartOf="parent" app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toTopOf="parent" app:layout_constraintTop_toBottomOf="@id/primary_name"
app:shapeAppearanceOverlay="@style/ShapeAppearanceOverlay.Findroid.Image" /> tools:text="The Girl Flautist" />
<TextView <ImageView
android:id="@+id/primary_name" android:id="@+id/downloaded_icon"
android:layout_width="0dp" android:layout_width="24dp"
android:layout_height="wrap_content" android:layout_height="24dp"
android:layout_marginTop="4dp" android:layout_marginTop="8dp"
android:ellipsize="end" android:layout_marginEnd="8dp"
android:maxLines="1" android:background="@drawable/circle_background"
android:textAppearance="@style/TextAppearance.Material3.BodyMedium" android:contentDescription="@string/downloaded_indicator"
app:layout_constraintEnd_toEndOf="parent" android:padding="4dp"
app:layout_constraintStart_toStartOf="parent" android:src="@drawable/ic_download"
app:layout_constraintTop_toBottomOf="@id/episode_image" android:visibility="gone"
tools:text="Wonder Egg Priority" /> app:layout_constraintEnd_toEndOf="@id/episode_image"
app:layout_constraintTop_toTopOf="@id/episode_image"
app:tint="?attr/colorOnPrimary"
tools:visibility="visible" />
<TextView <FrameLayout
android:id="@+id/secondary_name" android:id="@+id/progress_bar"
android:layout_width="0dp" android:layout_width="wrap_content"
android:layout_height="wrap_content" android:layout_height="4dp"
android:ellipsize="end" android:layout_marginHorizontal="8dp"
android:maxLines="1" android:layout_marginBottom="8dp"
android:textAppearance="@style/TextAppearance.Material3.BodySmall" android:background="@drawable/button_setup_background"
app:layout_constraintEnd_toEndOf="parent" android:visibility="gone"
app:layout_constraintStart_toStartOf="parent" app:layout_constraintBottom_toBottomOf="@id/episode_image"
app:layout_constraintTop_toBottomOf="@id/primary_name" app:layout_constraintStart_toStartOf="parent"
tools:text="The Girl Flautist" /> tools:layout_width="50dp"
tools:visibility="visible" />
<ImageView </androidx.constraintlayout.widget.ConstraintLayout>
android:id="@+id/downloaded_icon"
android:layout_width="24dp"
android:layout_height="24dp"
android:layout_marginTop="8dp"
android:layout_marginEnd="8dp"
android:background="@drawable/circle_background"
android:contentDescription="@string/downloaded_indicator"
android:padding="4dp"
android:src="@drawable/ic_download"
android:visibility="gone"
app:layout_constraintEnd_toEndOf="@id/episode_image"
app:layout_constraintTop_toTopOf="@id/episode_image"
app:tint="?attr/colorOnPrimary"
tools:visibility="visible"/>
<FrameLayout
android:id="@+id/progress_bar"
android:layout_width="wrap_content"
android:layout_height="4dp"
android:layout_marginHorizontal="8dp"
android:layout_marginBottom="8dp"
android:background="@drawable/button_setup_background"
android:visibility="gone"
app:layout_constraintBottom_toBottomOf="@id/episode_image"
app:layout_constraintStart_toStartOf="parent"
tools:layout_width="50dp"
tools:visibility="visible" />
</androidx.constraintlayout.widget.ConstraintLayout>
</layout>

View file

@ -1,52 +1,39 @@
<?xml version="1.0" encoding="utf-8"?> <?xml version="1.0" encoding="utf-8"?>
<layout xmlns:android="http://schemas.android.com/apk/res/android" <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto" xmlns:app="http://schemas.android.com/apk/res-auto"
xmlns:tools="http://schemas.android.com/tools"> xmlns:tools="http://schemas.android.com/tools"
android:id="@+id/item_layout"
android:layout_width="110dp"
android:layout_height="wrap_content"
android:layout_marginHorizontal="8dp"
android:clickable="true"
android:focusable="true"
android:foreground="@drawable/ripple_background"
android:orientation="vertical">
<data> <com.google.android.material.imageview.ShapeableImageView
android:id="@+id/person_image"
android:layout_width="match_parent"
android:layout_height="160dp"
android:layout_marginBottom="4dp"
android:scaleType="centerCrop"
app:shapeAppearanceOverlay="@style/ShapeAppearanceOverlay.Findroid.Image" />
<variable <TextView
name="person" android:id="@+id/person_name"
type="org.jellyfin.sdk.model.api.BaseItemPerson" /> android:layout_width="wrap_content"
</data>
<LinearLayout
android:id="@+id/item_layout"
android:layout_width="110dp"
android:layout_height="wrap_content" android:layout_height="wrap_content"
android:layout_marginHorizontal="8dp" android:ellipsize="end"
android:clickable="true" android:maxLines="1"
android:focusable="true" android:textAppearance="@style/TextAppearance.Material3.BodyMedium"
android:foreground="@drawable/ripple_background" tools:text="Rosa Salazar" />
android:orientation="vertical">
<com.google.android.material.imageview.ShapeableImageView <TextView
android:id="@+id/person_image" android:id="@+id/person_role"
android:layout_width="match_parent" android:layout_width="wrap_content"
android:layout_height="160dp" android:layout_height="wrap_content"
android:layout_marginBottom="4dp" android:ellipsize="end"
android:scaleType="centerCrop" android:maxLines="1"
app:personImage="@{person}" android:textAppearance="@style/TextAppearance.Material3.BodySmall"
app:shapeAppearanceOverlay="@style/ShapeAppearanceOverlay.Findroid.Image" /> tools:text="Alita" />
</LinearLayout>
<TextView
android:id="@+id/person_name"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:ellipsize="end"
android:maxLines="1"
android:text="@{person.name}"
android:textAppearance="@style/TextAppearance.Material3.BodyMedium"
tools:text="Rosa Salazar" />
<TextView
android:id="@+id/person_role"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:ellipsize="end"
android:maxLines="1"
android:text="@{person.role}"
android:textAppearance="@style/TextAppearance.Material3.BodySmall"
tools:text="Alita" />
</LinearLayout>
</layout>

View file

@ -1,86 +1,69 @@
<?xml version="1.0" encoding="utf-8"?> <?xml version="1.0" encoding="utf-8"?>
<androidx.constraintlayout.widget.ConstraintLayout xmlns:android="http://schemas.android.com/apk/res/android"
<layout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto" xmlns:app="http://schemas.android.com/apk/res-auto"
xmlns:tools="http://schemas.android.com/tools"> xmlns:tools="http://schemas.android.com/tools"
android:id="@+id/header"
android:layout_width="match_parent"
android:layout_height="200dp"
android:layout_marginBottom="16dp"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toTopOf="parent">
<data> <ImageView
android:id="@+id/item_banner"
android:layout_width="match_parent"
android:layout_height="200dp"
android:contentDescription="@string/series_poster"
android:scaleType="centerCrop"
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toTopOf="parent" />
<variable <FrameLayout
name="seriesId" android:layout_width="0dp"
type="java.util.UUID" /> android:layout_height="0dp"
android:background="@drawable/header_gradient"
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toTopOf="parent" />
<variable <com.google.android.material.imageview.ShapeableImageView
name="seasonId" android:id="@+id/season_poster"
type="java.util.UUID" /> android:layout_width="0dp"
</data> android:layout_height="0dp"
android:layout_marginStart="24dp"
android:layout_marginTop="24dp"
android:elevation="8dp"
android:scaleType="centerCrop"
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintDimensionRatio="H,3:2"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toTopOf="parent"
app:shapeAppearanceOverlay="@style/ShapeAppearanceOverlay.Findroid.Image" />
<androidx.constraintlayout.widget.ConstraintLayout <TextView
android:id="@+id/header" android:id="@+id/series_name"
android:layout_width="match_parent" android:layout_width="0dp"
android:layout_height="200dp" android:layout_height="wrap_content"
android:layout_marginBottom="16dp" android:layout_marginHorizontal="24dp"
app:layout_constraintEnd_toEndOf="parent" android:textAppearance="@style/TextAppearance.Material3.BodyLarge"
app:layout_constraintStart_toStartOf="parent" app:layout_constraintBottom_toTopOf="@id/season_name"
app:layout_constraintTop_toTopOf="parent"> app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toEndOf="@id/season_poster"
tools:text="Attack on Titan" />
<ImageView <TextView
android:id="@+id/item_banner" android:id="@+id/season_name"
android:layout_width="match_parent" android:layout_width="0dp"
android:layout_height="200dp" android:layout_height="wrap_content"
android:contentDescription="@string/series_poster" android:layout_marginHorizontal="24dp"
android:scaleType="centerCrop" android:textAppearance="@style/TextAppearance.Material3.HeadlineMedium"
app:itemBackdropById="@{seriesId}" app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintBottom_toBottomOf="parent" app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintEnd_toEndOf="parent" app:layout_constraintStart_toEndOf="@id/season_poster"
app:layout_constraintStart_toStartOf="parent" tools:text="Season 1" />
app:layout_constraintTop_toTopOf="parent" />
<FrameLayout </androidx.constraintlayout.widget.ConstraintLayout>
android:layout_width="0dp"
android:layout_height="0dp"
android:background="@drawable/header_gradient"
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toTopOf="parent" />
<com.google.android.material.imageview.ShapeableImageView
android:id="@+id/season_poster"
android:layout_width="0dp"
android:layout_height="0dp"
android:layout_marginStart="24dp"
android:layout_marginTop="24dp"
android:elevation="8dp"
android:scaleType="centerCrop"
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintDimensionRatio="H,3:2"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toTopOf="parent"
app:seasonPoster="@{seasonId}"
app:shapeAppearanceOverlay="@style/ShapeAppearanceOverlay.Findroid.Image" />
<TextView
android:id="@+id/series_name"
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_marginHorizontal="24dp"
android:textAppearance="@style/TextAppearance.Material3.BodyLarge"
app:layout_constraintBottom_toTopOf="@id/season_name"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toEndOf="@id/season_poster"
tools:text="Attack on Titan" />
<TextView
android:id="@+id/season_name"
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_marginHorizontal="24dp"
android:textAppearance="@style/TextAppearance.Material3.HeadlineMedium"
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toEndOf="@id/season_poster"
tools:text="Season 1" />
</androidx.constraintlayout.widget.ConstraintLayout>
</layout>

View file

@ -1,51 +1,38 @@
<?xml version="1.0" encoding="utf-8"?> <?xml version="1.0" encoding="utf-8"?>
<layout xmlns:android="http://schemas.android.com/apk/res/android" <androidx.constraintlayout.widget.ConstraintLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto" xmlns:app="http://schemas.android.com/apk/res-auto"
xmlns:tools="http://schemas.android.com/tools"> xmlns:tools="http://schemas.android.com/tools"
android:layout_width="64dp"
android:layout_height="wrap_content"
android:layout_marginHorizontal="12dp"
android:clickable="true"
android:focusable="true"
android:foreground="@drawable/ripple_background">
<data> <com.google.android.material.imageview.ShapeableImageView
android:id="@+id/user_image"
android:layout_width="0dp"
android:layout_height="0dp"
android:importantForAccessibility="no"
android:scaleType="centerCrop"
app:layout_constraintDimensionRatio="w,1:1"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toTopOf="parent"
app:shapeAppearanceOverlay="@style/ShapeAppearanceOverlay.Findroid.Image" />
<variable <TextView
name="user" android:id="@+id/user_name"
type="dev.jdtech.jellyfin.models.User" /> android:layout_width="match_parent"
</data>
<androidx.constraintlayout.widget.ConstraintLayout
android:layout_width="64dp"
android:layout_height="wrap_content" android:layout_height="wrap_content"
android:layout_marginHorizontal="12dp" android:layout_marginTop="8dp"
android:clickable="true" android:ellipsize="end"
android:focusable="true" android:maxLines="1"
android:foreground="@drawable/ripple_background"> android:textAlignment="center"
android:textAppearance="@style/TextAppearance.Material3.BodyMedium"
<com.google.android.material.imageview.ShapeableImageView app:layout_constraintBottom_toBottomOf="parent"
android:id="@+id/user_image" app:layout_constraintEnd_toEndOf="parent"
android:layout_width="0dp" app:layout_constraintStart_toStartOf="parent"
android:layout_height="0dp" app:layout_constraintTop_toBottomOf="@id/user_image"
android:importantForAccessibility="no" tools:text="username" />
android:scaleType="centerCrop" </androidx.constraintlayout.widget.ConstraintLayout>
app:layout_constraintDimensionRatio="w,1:1"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toTopOf="parent"
app:shapeAppearanceOverlay="@style/ShapeAppearanceOverlay.Findroid.Image"
app:userImage="@{user}" />
<TextView
android:id="@+id/user_name"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_marginTop="8dp"
android:ellipsize="end"
android:maxLines="1"
android:text="@{user.name}"
android:textAlignment="center"
android:textAppearance="@style/TextAppearance.Material3.BodyMedium"
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toBottomOf="@id/user_image"
tools:text="username" />
</androidx.constraintlayout.widget.ConstraintLayout>
</layout>

View file

@ -1,52 +1,39 @@
<?xml version="1.0" encoding="utf-8"?> <?xml version="1.0" encoding="utf-8"?>
<layout xmlns:android="http://schemas.android.com/apk/res/android" <androidx.constraintlayout.widget.ConstraintLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto" xmlns:app="http://schemas.android.com/apk/res-auto"
xmlns:tools="http://schemas.android.com/tools"> xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="50dp"
android:layout_marginHorizontal="24dp"
android:layout_marginTop="12dp"
android:layout_marginBottom="12dp"
android:clickable="true"
android:focusable="true"
android:foreground="@drawable/ripple_background">
<data> <com.google.android.material.imageview.ShapeableImageView
android:id="@+id/user_image"
android:layout_width="0dp"
android:layout_height="0dp"
android:importantForAccessibility="no"
android:scaleType="centerCrop"
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintDimensionRatio="w,1:1"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toTopOf="parent"
app:shapeAppearanceOverlay="@style/ShapeAppearanceOverlay.Findroid.Image" />
<variable <TextView
name="user" android:id="@+id/user_name"
type="dev.jdtech.jellyfin.models.User" /> android:layout_width="0dp"
</data> android:layout_height="wrap_content"
android:layout_marginStart="12dp"
<androidx.constraintlayout.widget.ConstraintLayout android:ellipsize="end"
android:layout_width="match_parent" android:maxLines="1"
android:layout_height="50dp" android:textAppearance="@style/TextAppearance.Material3.BodyLarge"
android:layout_marginHorizontal="24dp" app:layout_constraintBottom_toBottomOf="parent"
android:layout_marginTop="12dp" app:layout_constraintEnd_toEndOf="parent"
android:layout_marginBottom="12dp" app:layout_constraintStart_toEndOf="@id/user_image"
android:clickable="true" app:layout_constraintTop_toTopOf="parent"
android:focusable="true" tools:text="username" />
android:foreground="@drawable/ripple_background"> </androidx.constraintlayout.widget.ConstraintLayout>
<com.google.android.material.imageview.ShapeableImageView
android:id="@+id/user_image"
android:layout_width="0dp"
android:layout_height="0dp"
android:importantForAccessibility="no"
android:scaleType="centerCrop"
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintDimensionRatio="w,1:1"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toTopOf="parent"
app:shapeAppearanceOverlay="@style/ShapeAppearanceOverlay.Findroid.Image"
app:userImage="@{user}" />
<TextView
android:id="@+id/user_name"
android:layout_width="0dp"
android:layout_height="wrap_content"
android:ellipsize="end"
android:maxLines="1"
android:text="@{user.name}"
android:layout_marginStart="12dp"
android:textAppearance="@style/TextAppearance.Material3.BodyLarge"
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toEndOf="@id/user_image"
app:layout_constraintTop_toTopOf="parent"
tools:text="username" />
</androidx.constraintlayout.widget.ConstraintLayout>
</layout>