use view binding wherever possible
This commit is contained in:
parent
8d1c3d9a3f
commit
7df99ea0cc
|
@ -18,6 +18,10 @@ android {
|
||||||
setProperty("archivesBaseName", "teapod-$versionName")
|
setProperty("archivesBaseName", "teapod-$versionName")
|
||||||
}
|
}
|
||||||
|
|
||||||
|
buildFeatures {
|
||||||
|
viewBinding true
|
||||||
|
}
|
||||||
|
|
||||||
buildTypes {
|
buildTypes {
|
||||||
release {
|
release {
|
||||||
minifyEnabled true
|
minifyEnabled true
|
||||||
|
|
|
@ -22,7 +22,7 @@
|
||||||
</intent-filter>
|
</intent-filter>
|
||||||
</activity>
|
</activity>
|
||||||
<activity
|
<activity
|
||||||
android:name=".PlayerActivity"
|
android:name=".player.PlayerActivity"
|
||||||
android:label="@string/app_name"
|
android:label="@string/app_name"
|
||||||
android:theme="@style/PlayerTheme"
|
android:theme="@style/PlayerTheme"
|
||||||
android:configChanges="orientation|screenSize|layoutDirection" />
|
android:configChanges="orientation|screenSize|layoutDirection" />
|
||||||
|
|
|
@ -30,10 +30,11 @@ import androidx.appcompat.app.AppCompatActivity
|
||||||
import androidx.fragment.app.Fragment
|
import androidx.fragment.app.Fragment
|
||||||
import androidx.fragment.app.commit
|
import androidx.fragment.app.commit
|
||||||
import com.google.android.material.bottomnavigation.BottomNavigationView
|
import com.google.android.material.bottomnavigation.BottomNavigationView
|
||||||
import kotlinx.android.synthetic.main.activity_main.*
|
|
||||||
import kotlinx.coroutines.GlobalScope
|
import kotlinx.coroutines.GlobalScope
|
||||||
import kotlinx.coroutines.launch
|
import kotlinx.coroutines.launch
|
||||||
|
import org.mosad.teapod.databinding.ActivityMainBinding
|
||||||
import org.mosad.teapod.parser.AoDParser
|
import org.mosad.teapod.parser.AoDParser
|
||||||
|
import org.mosad.teapod.player.PlayerActivity
|
||||||
import org.mosad.teapod.preferences.EncryptedPreferences
|
import org.mosad.teapod.preferences.EncryptedPreferences
|
||||||
import org.mosad.teapod.preferences.Preferences
|
import org.mosad.teapod.preferences.Preferences
|
||||||
import org.mosad.teapod.ui.components.LoginDialog
|
import org.mosad.teapod.ui.components.LoginDialog
|
||||||
|
@ -45,6 +46,7 @@ import kotlin.system.measureTimeMillis
|
||||||
|
|
||||||
class MainActivity : AppCompatActivity(), BottomNavigationView.OnNavigationItemSelectedListener {
|
class MainActivity : AppCompatActivity(), BottomNavigationView.OnNavigationItemSelectedListener {
|
||||||
|
|
||||||
|
private lateinit var binding: ActivityMainBinding
|
||||||
private var activeBaseFragment: Fragment = HomeFragment() // the currently active fragment, home at the start
|
private var activeBaseFragment: Fragment = HomeFragment() // the currently active fragment, home at the start
|
||||||
|
|
||||||
companion object {
|
companion object {
|
||||||
|
@ -53,6 +55,7 @@ class MainActivity : AppCompatActivity(), BottomNavigationView.OnNavigationItemS
|
||||||
|
|
||||||
override fun onCreate(savedInstanceState: Bundle?) {
|
override fun onCreate(savedInstanceState: Bundle?) {
|
||||||
super.onCreate(savedInstanceState)
|
super.onCreate(savedInstanceState)
|
||||||
|
binding = ActivityMainBinding.inflate(layoutInflater)
|
||||||
|
|
||||||
if (!wasInitialized) {
|
if (!wasInitialized) {
|
||||||
load()
|
load()
|
||||||
|
@ -60,8 +63,8 @@ class MainActivity : AppCompatActivity(), BottomNavigationView.OnNavigationItemS
|
||||||
|
|
||||||
theme.applyStyle(getThemeResource(), true)
|
theme.applyStyle(getThemeResource(), true)
|
||||||
|
|
||||||
setContentView(R.layout.activity_main)
|
setContentView(binding.root)
|
||||||
nav_view.setOnNavigationItemSelectedListener(this)
|
binding.navView.setOnNavigationItemSelectedListener(this)
|
||||||
|
|
||||||
supportFragmentManager.commit {
|
supportFragmentManager.commit {
|
||||||
replace(R.id.nav_host_fragment, activeBaseFragment, activeBaseFragment.javaClass.simpleName)
|
replace(R.id.nav_host_fragment, activeBaseFragment, activeBaseFragment.javaClass.simpleName)
|
||||||
|
@ -73,7 +76,7 @@ class MainActivity : AppCompatActivity(), BottomNavigationView.OnNavigationItemS
|
||||||
supportFragmentManager.popBackStack()
|
supportFragmentManager.popBackStack()
|
||||||
} else {
|
} else {
|
||||||
if (activeBaseFragment !is HomeFragment) {
|
if (activeBaseFragment !is HomeFragment) {
|
||||||
nav_view.selectedItemId = R.id.navigation_home
|
binding.navView.selectedItemId = R.id.navigation_home
|
||||||
} else {
|
} else {
|
||||||
super.onBackPressed()
|
super.onBackPressed()
|
||||||
}
|
}
|
||||||
|
|
|
@ -1,4 +1,4 @@
|
||||||
package org.mosad.teapod
|
package org.mosad.teapod.player
|
||||||
|
|
||||||
import android.animation.Animator
|
import android.animation.Animator
|
||||||
import android.animation.AnimatorListenerAdapter
|
import android.animation.AnimatorListenerAdapter
|
||||||
|
@ -27,7 +27,7 @@ import kotlinx.coroutines.Dispatchers
|
||||||
import kotlinx.coroutines.GlobalScope
|
import kotlinx.coroutines.GlobalScope
|
||||||
import kotlinx.coroutines.launch
|
import kotlinx.coroutines.launch
|
||||||
import kotlinx.coroutines.withContext
|
import kotlinx.coroutines.withContext
|
||||||
import org.mosad.teapod.player.PlayerViewModel
|
import org.mosad.teapod.R
|
||||||
import org.mosad.teapod.preferences.Preferences
|
import org.mosad.teapod.preferences.Preferences
|
||||||
import org.mosad.teapod.util.Episode
|
import org.mosad.teapod.util.Episode
|
||||||
import java.util.*
|
import java.util.*
|
||||||
|
@ -36,14 +36,14 @@ import kotlin.concurrent.scheduleAtFixedRate
|
||||||
|
|
||||||
class PlayerActivity : AppCompatActivity() {
|
class PlayerActivity : AppCompatActivity() {
|
||||||
|
|
||||||
|
private val model: PlayerViewModel by viewModels()
|
||||||
|
|
||||||
private lateinit var player: SimpleExoPlayer
|
private lateinit var player: SimpleExoPlayer
|
||||||
private lateinit var dataSourceFactory: DataSource.Factory
|
private lateinit var dataSourceFactory: DataSource.Factory
|
||||||
private lateinit var controller: StyledPlayerControlView
|
private lateinit var controller: StyledPlayerControlView
|
||||||
private lateinit var gestureDetector: GestureDetectorCompat
|
private lateinit var gestureDetector: GestureDetectorCompat
|
||||||
private lateinit var timerUpdates: TimerTask
|
private lateinit var timerUpdates: TimerTask
|
||||||
|
|
||||||
private val model: PlayerViewModel by viewModels()
|
|
||||||
|
|
||||||
private var playWhenReady = true
|
private var playWhenReady = true
|
||||||
private var currentWindow = 0
|
private var currentWindow = 0
|
||||||
private var playbackPosition: Long = 0
|
private var playbackPosition: Long = 0
|
||||||
|
@ -78,7 +78,7 @@ class PlayerActivity : AppCompatActivity() {
|
||||||
super.onStart()
|
super.onStart()
|
||||||
if (Util.SDK_INT > 23) {
|
if (Util.SDK_INT > 23) {
|
||||||
initPlayer()
|
initPlayer()
|
||||||
if (video_view != null) video_view.onResume()
|
video_view?.onResume()
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -86,14 +86,14 @@ class PlayerActivity : AppCompatActivity() {
|
||||||
super.onResume()
|
super.onResume()
|
||||||
if (Util.SDK_INT <= 23) {
|
if (Util.SDK_INT <= 23) {
|
||||||
initPlayer()
|
initPlayer()
|
||||||
if (video_view != null) video_view.onResume()
|
video_view?.onResume()
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
override fun onPause() {
|
override fun onPause() {
|
||||||
super.onPause()
|
super.onPause()
|
||||||
if (Util.SDK_INT <= 23) {
|
if (Util.SDK_INT <= 23) {
|
||||||
if (video_view != null) video_view.onPause()
|
video_view?.onPause()
|
||||||
releasePlayer()
|
releasePlayer()
|
||||||
}
|
}
|
||||||
}
|
}
|
|
@ -9,10 +9,10 @@ import androidx.fragment.app.Fragment
|
||||||
import com.afollestad.materialdialogs.MaterialDialog
|
import com.afollestad.materialdialogs.MaterialDialog
|
||||||
import com.afollestad.materialdialogs.list.listItemsSingleChoice
|
import com.afollestad.materialdialogs.list.listItemsSingleChoice
|
||||||
import de.psdev.licensesdialog.LicensesDialog
|
import de.psdev.licensesdialog.LicensesDialog
|
||||||
import kotlinx.android.synthetic.main.fragment_account.*
|
|
||||||
import org.mosad.teapod.BuildConfig
|
import org.mosad.teapod.BuildConfig
|
||||||
import org.mosad.teapod.MainActivity
|
import org.mosad.teapod.MainActivity
|
||||||
import org.mosad.teapod.R
|
import org.mosad.teapod.R
|
||||||
|
import org.mosad.teapod.databinding.FragmentAccountBinding
|
||||||
import org.mosad.teapod.parser.AoDParser
|
import org.mosad.teapod.parser.AoDParser
|
||||||
import org.mosad.teapod.preferences.EncryptedPreferences
|
import org.mosad.teapod.preferences.EncryptedPreferences
|
||||||
import org.mosad.teapod.preferences.Preferences
|
import org.mosad.teapod.preferences.Preferences
|
||||||
|
@ -21,44 +21,46 @@ import org.mosad.teapod.util.DataTypes.Theme
|
||||||
|
|
||||||
class AccountFragment : Fragment() {
|
class AccountFragment : Fragment() {
|
||||||
|
|
||||||
|
private lateinit var binding: FragmentAccountBinding
|
||||||
|
|
||||||
override fun onCreateView(inflater: LayoutInflater, container: ViewGroup?, savedInstanceState: Bundle?): View? {
|
override fun onCreateView(inflater: LayoutInflater, container: ViewGroup?, savedInstanceState: Bundle?): View {
|
||||||
return inflater.inflate(R.layout.fragment_account, container, false)
|
binding = FragmentAccountBinding.inflate(inflater, container, false)
|
||||||
|
return binding.root
|
||||||
}
|
}
|
||||||
|
|
||||||
override fun onViewCreated(view: View, savedInstanceState: Bundle?) {
|
override fun onViewCreated(view: View, savedInstanceState: Bundle?) {
|
||||||
super.onViewCreated(view, savedInstanceState)
|
super.onViewCreated(view, savedInstanceState)
|
||||||
|
|
||||||
text_account_login.text = EncryptedPreferences.login
|
binding.textAccountLogin.text = EncryptedPreferences.login
|
||||||
text_info_about_desc.text = getString(R.string.info_about_desc, BuildConfig.VERSION_NAME, getString(R.string.build_time))
|
binding.textInfoAboutDesc.text = getString(R.string.info_about_desc, BuildConfig.VERSION_NAME, getString(R.string.build_time))
|
||||||
text_theme_selected.text = when (Preferences.theme) {
|
binding.textThemeSelected.text = when (Preferences.theme) {
|
||||||
Theme.DARK -> getString(R.string.theme_dark)
|
Theme.DARK -> getString(R.string.theme_dark)
|
||||||
else -> getString(R.string.theme_light)
|
else -> getString(R.string.theme_light)
|
||||||
}
|
}
|
||||||
|
|
||||||
switch_secondary.isChecked = Preferences.preferSecondary
|
binding.switchSecondary.isChecked = Preferences.preferSecondary
|
||||||
switch_autoplay.isChecked = Preferences.autoplay
|
binding.switchAutoplay.isChecked = Preferences.autoplay
|
||||||
|
|
||||||
initActions()
|
initActions()
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun initActions() {
|
private fun initActions() {
|
||||||
linear_account_login.setOnClickListener {
|
binding.linearAccountLogin.setOnClickListener {
|
||||||
showLoginDialog(true)
|
showLoginDialog(true)
|
||||||
}
|
}
|
||||||
|
|
||||||
linear_theme.setOnClickListener {
|
binding.linearTheme.setOnClickListener {
|
||||||
showThemeDialog()
|
showThemeDialog()
|
||||||
}
|
}
|
||||||
|
|
||||||
linear_about.setOnClickListener {
|
binding.linearInfo.setOnClickListener {
|
||||||
MaterialDialog(requireContext())
|
MaterialDialog(requireContext())
|
||||||
.title(R.string.info_about)
|
.title(R.string.info_about)
|
||||||
.message(R.string.info_about_dialog)
|
.message(R.string.info_about_dialog)
|
||||||
.show()
|
.show()
|
||||||
}
|
}
|
||||||
|
|
||||||
text_licenses.setOnClickListener {
|
binding.textLicenses.setOnClickListener {
|
||||||
|
|
||||||
val dialogCss = when (Preferences.theme) {
|
val dialogCss = when (Preferences.theme) {
|
||||||
Theme.DARK -> R.string.license_dialog_style_dark
|
Theme.DARK -> R.string.license_dialog_style_dark
|
||||||
|
@ -80,12 +82,12 @@ class AccountFragment : Fragment() {
|
||||||
.show()
|
.show()
|
||||||
}
|
}
|
||||||
|
|
||||||
switch_secondary.setOnClickListener {
|
binding.switchSecondary.setOnClickListener {
|
||||||
Preferences.savePreferSecondary(requireContext(), switch_secondary.isChecked)
|
Preferences.savePreferSecondary(requireContext(), binding.switchSecondary.isChecked)
|
||||||
}
|
}
|
||||||
|
|
||||||
switch_autoplay.setOnClickListener {
|
binding.switchAutoplay.setOnClickListener {
|
||||||
Preferences.saveAutoplay(requireContext(), switch_autoplay.isChecked)
|
Preferences.saveAutoplay(requireContext(), binding.switchAutoplay.isChecked)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -5,13 +5,12 @@ import android.view.LayoutInflater
|
||||||
import android.view.View
|
import android.view.View
|
||||||
import android.view.ViewGroup
|
import android.view.ViewGroup
|
||||||
import androidx.fragment.app.Fragment
|
import androidx.fragment.app.Fragment
|
||||||
import kotlinx.android.synthetic.main.fragment_home.*
|
|
||||||
import kotlinx.coroutines.Dispatchers
|
import kotlinx.coroutines.Dispatchers
|
||||||
import kotlinx.coroutines.GlobalScope
|
import kotlinx.coroutines.GlobalScope
|
||||||
import kotlinx.coroutines.launch
|
import kotlinx.coroutines.launch
|
||||||
import kotlinx.coroutines.withContext
|
import kotlinx.coroutines.withContext
|
||||||
import org.mosad.teapod.MainActivity
|
import org.mosad.teapod.MainActivity
|
||||||
import org.mosad.teapod.R
|
import org.mosad.teapod.databinding.FragmentHomeBinding
|
||||||
import org.mosad.teapod.parser.AoDParser
|
import org.mosad.teapod.parser.AoDParser
|
||||||
import org.mosad.teapod.util.StorageController
|
import org.mosad.teapod.util.StorageController
|
||||||
import org.mosad.teapod.util.adapter.MediaItemAdapter
|
import org.mosad.teapod.util.adapter.MediaItemAdapter
|
||||||
|
@ -19,15 +18,13 @@ import org.mosad.teapod.util.decoration.MediaItemDecoration
|
||||||
|
|
||||||
class HomeFragment : Fragment() {
|
class HomeFragment : Fragment() {
|
||||||
|
|
||||||
|
private lateinit var binding: FragmentHomeBinding
|
||||||
private lateinit var adapterMyList: MediaItemAdapter
|
private lateinit var adapterMyList: MediaItemAdapter
|
||||||
private lateinit var adapterNewEpisodes: MediaItemAdapter
|
private lateinit var adapterNewEpisodes: MediaItemAdapter
|
||||||
|
|
||||||
override fun onCreateView(
|
override fun onCreateView(inflater: LayoutInflater, container: ViewGroup?, savedInstanceState: Bundle?): View {
|
||||||
inflater: LayoutInflater,
|
binding = FragmentHomeBinding.inflate(inflater, container, false)
|
||||||
container: ViewGroup?,
|
return binding.root
|
||||||
savedInstanceState: Bundle?
|
|
||||||
): View? {
|
|
||||||
return inflater.inflate(R.layout.fragment_home, container, false)
|
|
||||||
}
|
}
|
||||||
|
|
||||||
override fun onViewCreated(view: View, savedInstanceState: Bundle?) {
|
override fun onViewCreated(view: View, savedInstanceState: Bundle?) {
|
||||||
|
@ -36,13 +33,13 @@ class HomeFragment : Fragment() {
|
||||||
GlobalScope.launch {
|
GlobalScope.launch {
|
||||||
withContext(Dispatchers.Main) {
|
withContext(Dispatchers.Main) {
|
||||||
context?.let {
|
context?.let {
|
||||||
recycler_my_list.addItemDecoration(MediaItemDecoration(9))
|
binding.recyclerMyList.addItemDecoration(MediaItemDecoration(9))
|
||||||
|
|
||||||
updateMyListMedia()
|
updateMyListMedia()
|
||||||
|
|
||||||
adapterNewEpisodes = MediaItemAdapter(AoDParser.newEpisodesList)
|
adapterNewEpisodes = MediaItemAdapter(AoDParser.newEpisodesList)
|
||||||
recycler_new_episodes.adapter = adapterNewEpisodes
|
binding.recyclerNewEpisodes.adapter = adapterNewEpisodes
|
||||||
recycler_new_episodes.addItemDecoration(MediaItemDecoration(9))
|
binding.recyclerNewEpisodes.addItemDecoration(MediaItemDecoration(9))
|
||||||
|
|
||||||
initActions()
|
initActions()
|
||||||
}
|
}
|
||||||
|
@ -63,7 +60,7 @@ class HomeFragment : Fragment() {
|
||||||
(activity as MainActivity).showMediaFragment(mediaId)
|
(activity as MainActivity).showMediaFragment(mediaId)
|
||||||
}
|
}
|
||||||
|
|
||||||
recycler_my_list.adapter = adapterMyList
|
binding.recyclerMyList.adapter = adapterMyList
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun initActions() {
|
private fun initActions() {
|
||||||
|
|
|
@ -5,23 +5,24 @@ import android.view.LayoutInflater
|
||||||
import android.view.View
|
import android.view.View
|
||||||
import android.view.ViewGroup
|
import android.view.ViewGroup
|
||||||
import androidx.fragment.app.Fragment
|
import androidx.fragment.app.Fragment
|
||||||
import kotlinx.android.synthetic.main.fragment_library.*
|
|
||||||
import kotlinx.coroutines.Dispatchers
|
import kotlinx.coroutines.Dispatchers
|
||||||
import kotlinx.coroutines.GlobalScope
|
import kotlinx.coroutines.GlobalScope
|
||||||
import kotlinx.coroutines.launch
|
import kotlinx.coroutines.launch
|
||||||
import kotlinx.coroutines.withContext
|
import kotlinx.coroutines.withContext
|
||||||
import org.mosad.teapod.MainActivity
|
import org.mosad.teapod.MainActivity
|
||||||
import org.mosad.teapod.R
|
import org.mosad.teapod.databinding.FragmentLibraryBinding
|
||||||
import org.mosad.teapod.parser.AoDParser
|
import org.mosad.teapod.parser.AoDParser
|
||||||
import org.mosad.teapod.util.adapter.MediaItemAdapter
|
import org.mosad.teapod.util.adapter.MediaItemAdapter
|
||||||
import org.mosad.teapod.util.decoration.MediaItemDecoration
|
import org.mosad.teapod.util.decoration.MediaItemDecoration
|
||||||
|
|
||||||
class LibraryFragment : Fragment() {
|
class LibraryFragment : Fragment() {
|
||||||
|
|
||||||
|
private lateinit var binding: FragmentLibraryBinding
|
||||||
private lateinit var adapter: MediaItemAdapter
|
private lateinit var adapter: MediaItemAdapter
|
||||||
|
|
||||||
override fun onCreateView(inflater: LayoutInflater, container: ViewGroup?, savedInstanceState: Bundle?): View? {
|
override fun onCreateView(inflater: LayoutInflater, container: ViewGroup?, savedInstanceState: Bundle?): View {
|
||||||
return inflater.inflate(R.layout.fragment_library, container, false)
|
binding = FragmentLibraryBinding.inflate(inflater, container, false)
|
||||||
|
return binding.root
|
||||||
}
|
}
|
||||||
|
|
||||||
override fun onViewCreated(view: View, savedInstanceState: Bundle?) {
|
override fun onViewCreated(view: View, savedInstanceState: Bundle?) {
|
||||||
|
@ -37,8 +38,8 @@ class LibraryFragment : Fragment() {
|
||||||
(activity as MainActivity).showMediaFragment(mediaId)
|
(activity as MainActivity).showMediaFragment(mediaId)
|
||||||
}
|
}
|
||||||
|
|
||||||
recycler_media_library.adapter = adapter
|
binding.recyclerMediaLibrary.adapter = adapter
|
||||||
recycler_media_library.addItemDecoration(MediaItemDecoration(9))
|
binding.recyclerMediaLibrary.addItemDecoration(MediaItemDecoration(9))
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -13,9 +13,9 @@ import androidx.recyclerview.widget.RecyclerView
|
||||||
import com.bumptech.glide.Glide
|
import com.bumptech.glide.Glide
|
||||||
import com.bumptech.glide.request.RequestOptions
|
import com.bumptech.glide.request.RequestOptions
|
||||||
import jp.wasabeef.glide.transformations.BlurTransformation
|
import jp.wasabeef.glide.transformations.BlurTransformation
|
||||||
import kotlinx.android.synthetic.main.fragment_media.*
|
|
||||||
import org.mosad.teapod.MainActivity
|
import org.mosad.teapod.MainActivity
|
||||||
import org.mosad.teapod.R
|
import org.mosad.teapod.R
|
||||||
|
import org.mosad.teapod.databinding.FragmentMediaBinding
|
||||||
import org.mosad.teapod.parser.AoDParser
|
import org.mosad.teapod.parser.AoDParser
|
||||||
import org.mosad.teapod.util.DataTypes.MediaType
|
import org.mosad.teapod.util.DataTypes.MediaType
|
||||||
import org.mosad.teapod.util.Episode
|
import org.mosad.teapod.util.Episode
|
||||||
|
@ -26,6 +26,7 @@ import org.mosad.teapod.util.adapter.EpisodeItemAdapter
|
||||||
|
|
||||||
class MediaFragment(private val media: Media, private val tmdb: TMDBResponse) : Fragment() {
|
class MediaFragment(private val media: Media, private val tmdb: TMDBResponse) : Fragment() {
|
||||||
|
|
||||||
|
private lateinit var binding: FragmentMediaBinding
|
||||||
private lateinit var adapterRecEpisodes: EpisodeItemAdapter
|
private lateinit var adapterRecEpisodes: EpisodeItemAdapter
|
||||||
private lateinit var viewManager: RecyclerView.LayoutManager
|
private lateinit var viewManager: RecyclerView.LayoutManager
|
||||||
private lateinit var nextEpisode: Episode
|
private lateinit var nextEpisode: Episode
|
||||||
|
@ -38,8 +39,9 @@ class MediaFragment(private val media: Media, private val tmdb: TMDBResponse) :
|
||||||
instance = this
|
instance = this
|
||||||
}
|
}
|
||||||
|
|
||||||
override fun onCreateView(inflater: LayoutInflater, container: ViewGroup?, savedInstanceState: Bundle?): View? {
|
override fun onCreateView(inflater: LayoutInflater, container: ViewGroup?, savedInstanceState: Bundle?): View {
|
||||||
return inflater.inflate(R.layout.fragment_media, container, false)
|
binding = FragmentMediaBinding.inflate(inflater, container, false)
|
||||||
|
return binding.root
|
||||||
}
|
}
|
||||||
|
|
||||||
override fun onViewCreated(view: View, savedInstanceState: Bundle?) {
|
override fun onViewCreated(view: View, savedInstanceState: Bundle?) {
|
||||||
|
@ -60,29 +62,29 @@ class MediaFragment(private val media: Media, private val tmdb: TMDBResponse) :
|
||||||
Glide.with(requireContext()).load(backdropUrl)
|
Glide.with(requireContext()).load(backdropUrl)
|
||||||
.apply(RequestOptions.placeholderOf(ColorDrawable(Color.DKGRAY)))
|
.apply(RequestOptions.placeholderOf(ColorDrawable(Color.DKGRAY)))
|
||||||
.apply(RequestOptions.bitmapTransform(BlurTransformation(20, 3)))
|
.apply(RequestOptions.bitmapTransform(BlurTransformation(20, 3)))
|
||||||
.into(image_backdrop)
|
.into(binding.imageBackdrop)
|
||||||
|
|
||||||
Glide.with(requireContext()).load(posterUrl)
|
Glide.with(requireContext()).load(posterUrl)
|
||||||
.into(image_poster)
|
.into(binding.imagePoster)
|
||||||
|
|
||||||
text_title.text = media.info.title
|
binding.textTitle.text = media.info.title
|
||||||
text_year.text = media.info.year.toString()
|
binding.textYear.text = media.info.year.toString()
|
||||||
text_age.text = media.info.age.toString()
|
binding.textAge.text = media.info.age.toString()
|
||||||
text_overview.text = media.info.shortDesc
|
binding.textOverview.text = media.info.shortDesc
|
||||||
if (StorageController.myList.contains(media.id)) {
|
if (StorageController.myList.contains(media.id)) {
|
||||||
Glide.with(requireContext()).load(R.drawable.ic_baseline_check_24).into(image_my_list_action)
|
Glide.with(requireContext()).load(R.drawable.ic_baseline_check_24).into(binding.imageMyListAction)
|
||||||
} else {
|
} else {
|
||||||
Glide.with(requireContext()).load(R.drawable.ic_baseline_add_24).into(image_my_list_action)
|
Glide.with(requireContext()).load(R.drawable.ic_baseline_add_24).into(binding.imageMyListAction)
|
||||||
}
|
}
|
||||||
|
|
||||||
// specific gui
|
// specific gui
|
||||||
if (media.type == MediaType.TVSHOW) {
|
if (media.type == MediaType.TVSHOW) {
|
||||||
adapterRecEpisodes = EpisodeItemAdapter(media.episodes)
|
adapterRecEpisodes = EpisodeItemAdapter(media.episodes)
|
||||||
viewManager = LinearLayoutManager(context)
|
viewManager = LinearLayoutManager(context)
|
||||||
recycler_episodes.layoutManager = viewManager
|
binding.recyclerEpisodes.layoutManager = viewManager
|
||||||
recycler_episodes.adapter = adapterRecEpisodes
|
binding.recyclerEpisodes.adapter = adapterRecEpisodes
|
||||||
|
|
||||||
text_episodes_or_runtime.text = getString(R.string.text_episodes_count, media.info.episodesCount)
|
binding.textEpisodesOrRuntime.text = getString(R.string.text_episodes_count, media.info.episodesCount)
|
||||||
|
|
||||||
// get next episode
|
// get next episode
|
||||||
nextEpisode = if (media.episodes.firstOrNull{ !it.watched } != null) {
|
nextEpisode = if (media.episodes.firstOrNull{ !it.watched } != null) {
|
||||||
|
@ -92,20 +94,20 @@ class MediaFragment(private val media: Media, private val tmdb: TMDBResponse) :
|
||||||
}
|
}
|
||||||
|
|
||||||
// title is the next episodes title
|
// title is the next episodes title
|
||||||
text_title.text = nextEpisode.title
|
binding.textTitle.text = nextEpisode.title
|
||||||
} else if (media.type == MediaType.MOVIE) {
|
} else if (media.type == MediaType.MOVIE) {
|
||||||
recycler_episodes.visibility = View.GONE
|
binding.recyclerEpisodes.visibility = View.GONE
|
||||||
|
|
||||||
if (tmdb.runtime > 0) {
|
if (tmdb.runtime > 0) {
|
||||||
text_episodes_or_runtime.text = getString(R.string.text_runtime, tmdb.runtime)
|
binding.textEpisodesOrRuntime.text = getString(R.string.text_runtime, tmdb.runtime)
|
||||||
} else {
|
} else {
|
||||||
text_episodes_or_runtime.visibility = View.GONE
|
binding.textEpisodesOrRuntime.visibility = View.GONE
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun initActions() {
|
private fun initActions() {
|
||||||
button_play.setOnClickListener {
|
binding.buttonPlay.setOnClickListener {
|
||||||
when (media.type) {
|
when (media.type) {
|
||||||
MediaType.MOVIE -> playStream(media.episodes.first())
|
MediaType.MOVIE -> playStream(media.episodes.first())
|
||||||
MediaType.TVSHOW -> playEpisode(nextEpisode)
|
MediaType.TVSHOW -> playEpisode(nextEpisode)
|
||||||
|
@ -114,13 +116,13 @@ class MediaFragment(private val media: Media, private val tmdb: TMDBResponse) :
|
||||||
}
|
}
|
||||||
|
|
||||||
// add or remove media from myList
|
// add or remove media from myList
|
||||||
linear_my_list_action.setOnClickListener {
|
binding.linearMyListAction.setOnClickListener {
|
||||||
if (StorageController.myList.contains(media.id)) {
|
if (StorageController.myList.contains(media.id)) {
|
||||||
StorageController.myList.remove(media.id)
|
StorageController.myList.remove(media.id)
|
||||||
Glide.with(requireContext()).load(R.drawable.ic_baseline_add_24).into(image_my_list_action)
|
Glide.with(requireContext()).load(R.drawable.ic_baseline_add_24).into(binding.imageMyListAction)
|
||||||
} else {
|
} else {
|
||||||
StorageController.myList.add(media.id)
|
StorageController.myList.add(media.id)
|
||||||
Glide.with(requireContext()).load(R.drawable.ic_baseline_check_24).into(image_my_list_action)
|
Glide.with(requireContext()).load(R.drawable.ic_baseline_check_24).into(binding.imageMyListAction)
|
||||||
}
|
}
|
||||||
StorageController.saveMyList(requireContext())
|
StorageController.saveMyList(requireContext())
|
||||||
|
|
||||||
|
@ -153,7 +155,7 @@ class MediaFragment(private val media: Media, private val tmdb: TMDBResponse) :
|
||||||
} else {
|
} else {
|
||||||
media.episodes.first()
|
media.episodes.first()
|
||||||
}
|
}
|
||||||
text_title.text = nextEpisode.title
|
binding.textTitle.text = nextEpisode.title
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun playStream(ep: Episode) {
|
private fun playStream(ep: Episode) {
|
||||||
|
|
|
@ -6,20 +6,21 @@ import android.view.View
|
||||||
import android.view.ViewGroup
|
import android.view.ViewGroup
|
||||||
import android.widget.SearchView
|
import android.widget.SearchView
|
||||||
import androidx.fragment.app.Fragment
|
import androidx.fragment.app.Fragment
|
||||||
import kotlinx.android.synthetic.main.fragment_search.*
|
|
||||||
import kotlinx.coroutines.*
|
import kotlinx.coroutines.*
|
||||||
import org.mosad.teapod.MainActivity
|
import org.mosad.teapod.MainActivity
|
||||||
import org.mosad.teapod.R
|
import org.mosad.teapod.databinding.FragmentSearchBinding
|
||||||
import org.mosad.teapod.parser.AoDParser
|
import org.mosad.teapod.parser.AoDParser
|
||||||
import org.mosad.teapod.util.decoration.MediaItemDecoration
|
import org.mosad.teapod.util.decoration.MediaItemDecoration
|
||||||
import org.mosad.teapod.util.adapter.MediaItemAdapter
|
import org.mosad.teapod.util.adapter.MediaItemAdapter
|
||||||
|
|
||||||
class SearchFragment : Fragment() {
|
class SearchFragment : Fragment() {
|
||||||
|
|
||||||
|
private lateinit var binding: FragmentSearchBinding
|
||||||
private var adapter : MediaItemAdapter? = null
|
private var adapter : MediaItemAdapter? = null
|
||||||
|
|
||||||
override fun onCreateView(inflater: LayoutInflater, container: ViewGroup?, savedInstanceState: Bundle?): View? {
|
override fun onCreateView(inflater: LayoutInflater, container: ViewGroup?, savedInstanceState: Bundle?): View {
|
||||||
return inflater.inflate(R.layout.fragment_search, container, false)
|
binding = FragmentSearchBinding.inflate(inflater, container, false)
|
||||||
|
return binding.root
|
||||||
}
|
}
|
||||||
|
|
||||||
override fun onViewCreated(view: View, savedInstanceState: Bundle?) {
|
override fun onViewCreated(view: View, savedInstanceState: Bundle?) {
|
||||||
|
@ -31,12 +32,12 @@ class SearchFragment : Fragment() {
|
||||||
context?.let {
|
context?.let {
|
||||||
adapter = MediaItemAdapter(AoDParser.itemMediaList)
|
adapter = MediaItemAdapter(AoDParser.itemMediaList)
|
||||||
adapter!!.onItemClick = { mediaId, _ ->
|
adapter!!.onItemClick = { mediaId, _ ->
|
||||||
search_text.clearFocus()
|
binding.searchText.clearFocus()
|
||||||
(activity as MainActivity).showMediaFragment(mediaId)
|
(activity as MainActivity).showMediaFragment(mediaId)
|
||||||
}
|
}
|
||||||
|
|
||||||
recycler_media_search.adapter = adapter
|
binding.recyclerMediaSearch.adapter = adapter
|
||||||
recycler_media_search.addItemDecoration(MediaItemDecoration(9))
|
binding.recyclerMediaSearch.addItemDecoration(MediaItemDecoration(9))
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -45,7 +46,7 @@ class SearchFragment : Fragment() {
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun initActions() {
|
private fun initActions() {
|
||||||
search_text.setOnQueryTextListener(object : SearchView.OnQueryTextListener {
|
binding.searchText.setOnQueryTextListener(object : SearchView.OnQueryTextListener {
|
||||||
override fun onQueryTextSubmit(query: String?): Boolean {
|
override fun onQueryTextSubmit(query: String?): Boolean {
|
||||||
adapter?.filter?.filter(query)
|
adapter?.filter?.filter(query)
|
||||||
adapter?.notifyDataSetChanged()
|
adapter?.notifyDataSetChanged()
|
||||||
|
|
|
@ -1,30 +1,26 @@
|
||||||
package org.mosad.teapod.util.adapter
|
package org.mosad.teapod.util.adapter
|
||||||
|
|
||||||
import android.view.LayoutInflater
|
import android.view.LayoutInflater
|
||||||
import android.view.View
|
|
||||||
import android.view.ViewGroup
|
import android.view.ViewGroup
|
||||||
import androidx.core.content.ContextCompat
|
import androidx.core.content.ContextCompat
|
||||||
import androidx.recyclerview.widget.RecyclerView
|
import androidx.recyclerview.widget.RecyclerView
|
||||||
import com.bumptech.glide.Glide
|
import com.bumptech.glide.Glide
|
||||||
import com.bumptech.glide.request.RequestOptions
|
import com.bumptech.glide.request.RequestOptions
|
||||||
import jp.wasabeef.glide.transformations.RoundedCornersTransformation
|
import jp.wasabeef.glide.transformations.RoundedCornersTransformation
|
||||||
import kotlinx.android.synthetic.main.item_episode.view.*
|
|
||||||
import org.mosad.teapod.R
|
import org.mosad.teapod.R
|
||||||
|
import org.mosad.teapod.databinding.ItemEpisodeBinding
|
||||||
import org.mosad.teapod.util.Episode
|
import org.mosad.teapod.util.Episode
|
||||||
|
|
||||||
class EpisodeItemAdapter(private val episodes: List<Episode>) : RecyclerView.Adapter<EpisodeItemAdapter.EpisodeViewHolder>() {
|
class EpisodeItemAdapter(private val episodes: List<Episode>) : RecyclerView.Adapter<EpisodeItemAdapter.EpisodeViewHolder>() {
|
||||||
|
|
||||||
var onItemClick: ((String, Int) -> Unit)? = null
|
|
||||||
var onImageClick: ((String, Int) -> Unit)? = null
|
var onImageClick: ((String, Int) -> Unit)? = null
|
||||||
|
|
||||||
override fun onCreateViewHolder(parent: ViewGroup, viewType: Int): EpisodeViewHolder {
|
override fun onCreateViewHolder(parent: ViewGroup, viewType: Int): EpisodeViewHolder {
|
||||||
val view = LayoutInflater.from(parent.context).inflate(R.layout.item_episode, parent, false)
|
return EpisodeViewHolder(ItemEpisodeBinding.inflate(LayoutInflater.from(parent.context), parent, false))
|
||||||
|
|
||||||
return EpisodeViewHolder(view)
|
|
||||||
}
|
}
|
||||||
|
|
||||||
override fun onBindViewHolder(holder: EpisodeViewHolder, position: Int) {
|
override fun onBindViewHolder(holder: EpisodeViewHolder, position: Int) {
|
||||||
val context = holder.view.context
|
val context = holder.binding.root.context
|
||||||
val ep = episodes[position]
|
val ep = episodes[position]
|
||||||
|
|
||||||
val titleText = if (ep.priStreamUrl.isEmpty() && ep.secStreamOmU) {
|
val titleText = if (ep.priStreamUrl.isEmpty() && ep.secStreamOmU) {
|
||||||
|
@ -33,21 +29,21 @@ class EpisodeItemAdapter(private val episodes: List<Episode>) : RecyclerView.Ada
|
||||||
context.getString(R.string.component_episode_title, ep.number, ep.description)
|
context.getString(R.string.component_episode_title, ep.number, ep.description)
|
||||||
}
|
}
|
||||||
|
|
||||||
holder.view.text_episode_title.text = titleText
|
holder.binding.textEpisodeTitle.text = titleText
|
||||||
holder.view.text_episode_desc.text = ep.shortDesc
|
holder.binding.textEpisodeDesc.text = ep.shortDesc
|
||||||
|
|
||||||
if (episodes[position].posterUrl.isNotEmpty()) {
|
if (episodes[position].posterUrl.isNotEmpty()) {
|
||||||
Glide.with(context).load(ep.posterUrl)
|
Glide.with(context).load(ep.posterUrl)
|
||||||
.apply(RequestOptions.bitmapTransform(RoundedCornersTransformation(10, 0)))
|
.apply(RequestOptions.bitmapTransform(RoundedCornersTransformation(10, 0)))
|
||||||
.into(holder.view.image_episode)
|
.into(holder.binding.imageEpisode)
|
||||||
}
|
}
|
||||||
|
|
||||||
if (ep.watched) {
|
if (ep.watched) {
|
||||||
holder.view.image_watched.setImageDrawable(
|
holder.binding.imageWatched.setImageDrawable(
|
||||||
ContextCompat.getDrawable(context, R.drawable.ic_baseline_check_circle_24)
|
ContextCompat.getDrawable(context, R.drawable.ic_baseline_check_circle_24)
|
||||||
)
|
)
|
||||||
} else {
|
} else {
|
||||||
holder.view.image_watched.setImageDrawable(null)
|
holder.binding.imageWatched.setImageDrawable(null)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -59,13 +55,9 @@ class EpisodeItemAdapter(private val episodes: List<Episode>) : RecyclerView.Ada
|
||||||
episodes[position].watched = watched
|
episodes[position].watched = watched
|
||||||
}
|
}
|
||||||
|
|
||||||
inner class EpisodeViewHolder(val view: View) : RecyclerView.ViewHolder(view) {
|
inner class EpisodeViewHolder(val binding: ItemEpisodeBinding) : RecyclerView.ViewHolder(binding.root) {
|
||||||
init {
|
init {
|
||||||
view.setOnClickListener {
|
binding.imageEpisode.setOnClickListener {
|
||||||
onItemClick?.invoke(episodes[adapterPosition].title, adapterPosition)
|
|
||||||
}
|
|
||||||
|
|
||||||
view.image_episode.setOnClickListener {
|
|
||||||
onImageClick?.invoke(episodes[adapterPosition].title, adapterPosition)
|
onImageClick?.invoke(episodes[adapterPosition].title, adapterPosition)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -1,33 +1,29 @@
|
||||||
package org.mosad.teapod.util.adapter
|
package org.mosad.teapod.util.adapter
|
||||||
|
|
||||||
import android.view.LayoutInflater
|
import android.view.LayoutInflater
|
||||||
import android.view.View
|
|
||||||
import android.view.ViewGroup
|
import android.view.ViewGroup
|
||||||
import android.widget.Filter
|
import android.widget.Filter
|
||||||
import android.widget.Filterable
|
import android.widget.Filterable
|
||||||
import androidx.recyclerview.widget.RecyclerView
|
import androidx.recyclerview.widget.RecyclerView
|
||||||
import com.bumptech.glide.Glide
|
import com.bumptech.glide.Glide
|
||||||
import kotlinx.android.synthetic.main.item_media.view.*
|
import org.mosad.teapod.databinding.ItemMediaBinding
|
||||||
import org.mosad.teapod.R
|
|
||||||
import org.mosad.teapod.util.ItemMedia
|
import org.mosad.teapod.util.ItemMedia
|
||||||
import java.util.*
|
import java.util.*
|
||||||
|
|
||||||
class MediaItemAdapter(private val media: List<ItemMedia>) : RecyclerView.Adapter<MediaItemAdapter.ViewHolder>(), Filterable {
|
class MediaItemAdapter(private val media: List<ItemMedia>) : RecyclerView.Adapter<MediaItemAdapter.MediaViewHolder>(), Filterable {
|
||||||
|
|
||||||
var onItemClick: ((Int, Int) -> Unit)? = null
|
var onItemClick: ((Int, Int) -> Unit)? = null
|
||||||
private val filter = MediaFilter()
|
private val filter = MediaFilter()
|
||||||
private var filteredMedia = media.map { it.copy() }
|
private var filteredMedia = media.map { it.copy() }
|
||||||
|
|
||||||
override fun onCreateViewHolder(parent: ViewGroup, viewType: Int): MediaItemAdapter.ViewHolder {
|
override fun onCreateViewHolder(parent: ViewGroup, viewType: Int): MediaItemAdapter.MediaViewHolder {
|
||||||
val view = LayoutInflater.from(parent.context).inflate(R.layout.item_media, parent, false)
|
return MediaViewHolder(ItemMediaBinding.inflate(LayoutInflater.from(parent.context), parent, false))
|
||||||
|
|
||||||
return ViewHolder(view)
|
|
||||||
}
|
}
|
||||||
|
|
||||||
override fun onBindViewHolder(holder: MediaItemAdapter.ViewHolder, position: Int) {
|
override fun onBindViewHolder(holder: MediaItemAdapter.MediaViewHolder, position: Int) {
|
||||||
holder.view.apply {
|
holder.binding.root.apply {
|
||||||
text_title.text = filteredMedia[position].title
|
holder.binding.textTitle.text = filteredMedia[position].title
|
||||||
Glide.with(context).load(filteredMedia[position].posterUrl).into(image_poster)
|
Glide.with(context).load(filteredMedia[position].posterUrl).into(holder.binding.imagePoster)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -39,9 +35,9 @@ class MediaItemAdapter(private val media: List<ItemMedia>) : RecyclerView.Adapte
|
||||||
return filter
|
return filter
|
||||||
}
|
}
|
||||||
|
|
||||||
inner class ViewHolder(val view: View) : RecyclerView.ViewHolder(view) {
|
inner class MediaViewHolder(val binding: ItemMediaBinding) : RecyclerView.ViewHolder(binding.root) {
|
||||||
init {
|
init {
|
||||||
view.setOnClickListener {
|
binding.root.setOnClickListener {
|
||||||
onItemClick?.invoke(filteredMedia[adapterPosition].id, adapterPosition)
|
onItemClick?.invoke(filteredMedia[adapterPosition].id, adapterPosition)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -7,7 +7,7 @@
|
||||||
android:layout_height="match_parent"
|
android:layout_height="match_parent"
|
||||||
android:background="#000000"
|
android:background="#000000"
|
||||||
android:keepScreenOn="true"
|
android:keepScreenOn="true"
|
||||||
tools:context=".PlayerActivity">
|
tools:context=".player.PlayerActivity">
|
||||||
|
|
||||||
<com.google.android.exoplayer2.ui.StyledPlayerView
|
<com.google.android.exoplayer2.ui.StyledPlayerView
|
||||||
android:id="@+id/video_view"
|
android:id="@+id/video_view"
|
||||||
|
|
Loading…
Reference in New Issue