0
0
mirror of https://github.com/mediathekview/zapp.git synced 2024-09-20 04:12:14 +02:00

Switch to new MenuProvider interface for menu generation

This commit is contained in:
Christine Coenen 2022-10-23 18:46:01 +02:00
parent 3b7046fc3a
commit 2b86db259d
8 changed files with 86 additions and 77 deletions

View File

@ -3,9 +3,11 @@ package de.christinecoenen.code.zapp.app.downloads.ui.list
import android.os.Bundle import android.os.Bundle
import android.view.* import android.view.*
import android.widget.PopupMenu import android.widget.PopupMenu
import androidx.core.view.MenuProvider
import androidx.core.view.isVisible import androidx.core.view.isVisible
import androidx.fragment.app.Fragment import androidx.fragment.app.Fragment
import androidx.fragment.app.setFragmentResultListener import androidx.fragment.app.setFragmentResultListener
import androidx.lifecycle.Lifecycle
import androidx.lifecycle.lifecycleScope import androidx.lifecycle.lifecycleScope
import androidx.navigation.fragment.findNavController import androidx.navigation.fragment.findNavController
import androidx.recyclerview.widget.RecyclerView import androidx.recyclerview.widget.RecyclerView
@ -18,7 +20,7 @@ import de.christinecoenen.code.zapp.models.shows.PersistedMediathekShow
import kotlinx.coroutines.launch import kotlinx.coroutines.launch
import org.koin.androidx.viewmodel.ext.android.viewModel import org.koin.androidx.viewmodel.ext.android.viewModel
class DownloadsFragment : Fragment(), DownloadListAdapter.Listener { class DownloadsFragment : Fragment(), DownloadListAdapter.Listener, MenuProvider {
private var _binding: DownloadsFragmentBinding? = null private var _binding: DownloadsFragmentBinding? = null
private val binding: DownloadsFragmentBinding get() = _binding!! private val binding: DownloadsFragmentBinding get() = _binding!!
@ -46,8 +48,6 @@ class DownloadsFragment : Fragment(), DownloadListAdapter.Listener {
super.onCreate(savedInstanceState) super.onCreate(savedInstanceState)
downloadAdapter = DownloadListAdapter(lifecycleScope, this, viewModel) downloadAdapter = DownloadListAdapter(lifecycleScope, this, viewModel)
setHasOptionsMenu(true)
} }
override fun onCreateView( override fun onCreateView(
@ -68,6 +68,8 @@ class DownloadsFragment : Fragment(), DownloadListAdapter.Listener {
} }
updateNoDownloadsVisibility() updateNoDownloadsVisibility()
requireActivity().addMenuProvider(this, viewLifecycleOwner, Lifecycle.State.RESUMED)
return binding.root return binding.root
} }
@ -77,10 +79,12 @@ class DownloadsFragment : Fragment(), DownloadListAdapter.Listener {
_binding = null _binding = null
} }
override fun onCreateOptionsMenu(menu: Menu, inflater: MenuInflater) { override fun onCreateMenu(menu: Menu, menuInflater: MenuInflater) {
inflater.inflate(R.menu.activity_main_toolbar, menu) menuInflater.inflate(R.menu.activity_main_toolbar, menu)
} }
override fun onMenuItemSelected(menuItem: MenuItem): Boolean = false
override fun onShowClicked(show: PersistedMediathekShow) { override fun onShowClicked(show: PersistedMediathekShow) {
val directions = val directions =
MediathekListFragmentDirections.toMediathekDetailFragment(show.mediathekShow) MediathekListFragmentDirections.toMediathekDetailFragment(show.mediathekShow)

View File

@ -4,6 +4,7 @@ import android.content.Context
import android.content.Intent import android.content.Intent
import android.os.Bundle import android.os.Bundle
import android.view.Menu import android.view.Menu
import android.view.MenuInflater
import android.view.MenuItem import android.view.MenuItem
import de.christinecoenen.code.zapp.R import de.christinecoenen.code.zapp.R
import de.christinecoenen.code.zapp.app.livestream.ui.ProgramInfoViewModel import de.christinecoenen.code.zapp.app.livestream.ui.ProgramInfoViewModel
@ -39,16 +40,14 @@ class ChannelPlayerActivity : AbstractPlayerActivity() {
programInfoViewModel.title.observe(this, ::onShowTitleChanged) programInfoViewModel.title.observe(this, ::onShowTitleChanged)
} }
override fun onCreateOptionsMenu(menu: Menu): Boolean { override fun onCreateMenu(menu: Menu, menuInflater: MenuInflater) {
super.onCreateOptionsMenu(menu) super.onCreateMenu(menu, menuInflater)
menuInflater.inflate(R.menu.activity_channel_player, menu) menuInflater.inflate(R.menu.activity_channel_player, menu)
return true
} }
override fun onOptionsItemSelected(item: MenuItem): Boolean { override fun onMenuItemSelected(menuItem: MenuItem): Boolean {
when (item.itemId) { when (menuItem.itemId) {
R.id.menu_program_info -> { R.id.menu_program_info -> {
val modalBottomSheet = ProgramInfoSheetDialogFragment(programInfoViewModel) val modalBottomSheet = ProgramInfoSheetDialogFragment(programInfoViewModel)
modalBottomSheet.show(supportFragmentManager, ProgramInfoSheetDialogFragment.TAG) modalBottomSheet.show(supportFragmentManager, ProgramInfoSheetDialogFragment.TAG)
@ -56,7 +55,7 @@ class ChannelPlayerActivity : AbstractPlayerActivity() {
} }
} }
return super.onOptionsItemSelected(item) return super.onMenuItemSelected(menuItem)
} }
override fun onShareMenuItemClicked() { override fun onShareMenuItemClicked() {

View File

@ -4,8 +4,10 @@ import android.annotation.SuppressLint
import android.os.Bundle import android.os.Bundle
import android.view.* import android.view.*
import android.widget.PopupMenu import android.widget.PopupMenu
import androidx.core.view.MenuProvider
import androidx.core.view.ViewCompat import androidx.core.view.ViewCompat
import androidx.fragment.app.Fragment import androidx.fragment.app.Fragment
import androidx.lifecycle.Lifecycle
import de.christinecoenen.code.zapp.R import de.christinecoenen.code.zapp.R
import de.christinecoenen.code.zapp.app.livestream.ui.detail.ChannelPlayerActivity import de.christinecoenen.code.zapp.app.livestream.ui.detail.ChannelPlayerActivity
import de.christinecoenen.code.zapp.app.livestream.ui.list.adapter.BaseChannelListAdapter import de.christinecoenen.code.zapp.app.livestream.ui.list.adapter.BaseChannelListAdapter
@ -17,7 +19,7 @@ import de.christinecoenen.code.zapp.models.channels.ISortableChannelList
import de.christinecoenen.code.zapp.models.channels.json.SortableVisibleJsonChannelList import de.christinecoenen.code.zapp.models.channels.json.SortableVisibleJsonChannelList
import de.christinecoenen.code.zapp.utils.view.GridAutofitLayoutManager import de.christinecoenen.code.zapp.utils.view.GridAutofitLayoutManager
class ChannelListFragment : Fragment(), ListItemListener { class ChannelListFragment : Fragment(), MenuProvider, ListItemListener {
private lateinit var channelList: ISortableChannelList private lateinit var channelList: ISortableChannelList
private lateinit var gridAdapter: BaseChannelListAdapter private lateinit var gridAdapter: BaseChannelListAdapter
@ -28,8 +30,6 @@ class ChannelListFragment : Fragment(), ListItemListener {
channelList = SortableVisibleJsonChannelList(requireContext()) channelList = SortableVisibleJsonChannelList(requireContext())
gridAdapter = ChannelListAdapter(channelList, this, this) gridAdapter = ChannelListAdapter(channelList, this, this)
setHasOptionsMenu(true)
} }
override fun onCreateView( override fun onCreateView(
@ -44,6 +44,8 @@ class ChannelListFragment : Fragment(), ListItemListener {
channelGridView.layoutManager = GridAutofitLayoutManager(requireContext(), 400) channelGridView.layoutManager = GridAutofitLayoutManager(requireContext(), 400)
channelGridView.adapter = gridAdapter channelGridView.adapter = gridAdapter
requireActivity().addMenuProvider(this, viewLifecycleOwner, Lifecycle.State.RESUMED)
return binding.root return binding.root
} }
@ -58,10 +60,12 @@ class ChannelListFragment : Fragment(), ListItemListener {
gridAdapter.notifyDataSetChanged() gridAdapter.notifyDataSetChanged()
} }
override fun onCreateOptionsMenu(menu: Menu, inflater: MenuInflater) { override fun onCreateMenu(menu: Menu, menuInflater: MenuInflater) {
inflater.inflate(R.menu.activity_main_toolbar, menu) menuInflater.inflate(R.menu.activity_main_toolbar, menu)
} }
override fun onMenuItemSelected(menuItem: MenuItem): Boolean = false
override fun onItemClick(channel: ChannelModel) { override fun onItemClick(channel: ChannelModel) {
val intent = ChannelPlayerActivity.getStartIntent(context, channel.id) val intent = ChannelPlayerActivity.getStartIntent(context, channel.id)
startActivity(intent) startActivity(intent)

View File

@ -1,8 +1,11 @@
package de.christinecoenen.code.zapp.app.main package de.christinecoenen.code.zapp.app.main
import android.os.Bundle import android.os.Bundle
import android.view.Menu
import android.view.MenuInflater
import android.view.MenuItem import android.view.MenuItem
import androidx.appcompat.app.AppCompatActivity import androidx.appcompat.app.AppCompatActivity
import androidx.core.view.MenuProvider
import androidx.core.view.isVisible import androidx.core.view.isVisible
import androidx.navigation.NavController import androidx.navigation.NavController
import androidx.navigation.NavDestination import androidx.navigation.NavDestination
@ -12,7 +15,7 @@ import androidx.preference.PreferenceManager
import de.christinecoenen.code.zapp.R import de.christinecoenen.code.zapp.R
import de.christinecoenen.code.zapp.databinding.ActivityMainBinding import de.christinecoenen.code.zapp.databinding.ActivityMainBinding
class MainActivity : AppCompatActivity() { class MainActivity : AppCompatActivity(), MenuProvider {
private var _binding: ActivityMainBinding? = null private var _binding: ActivityMainBinding? = null
private val binding get() = _binding!! private val binding get() = _binding!!
@ -45,6 +48,8 @@ class MainActivity : AppCompatActivity() {
binding.bottomNavigation.setupWithNavController(navController) binding.bottomNavigation.setupWithNavController(navController)
addMenuProvider(this)
PreferenceManager.setDefaultValues(application, R.xml.preferences, false) PreferenceManager.setDefaultValues(application, R.xml.preferences, false)
} }
@ -73,8 +78,12 @@ class MainActivity : AppCompatActivity() {
_binding = null _binding = null
} }
override fun onOptionsItemSelected(item: MenuItem): Boolean { override fun onCreateMenu(menu: Menu, menuInflater: MenuInflater) {
return item.onNavDestinationSelected(navController) || super.onOptionsItemSelected(item) // done by child fragments
}
override fun onMenuItemSelected(menuItem: MenuItem): Boolean {
return menuItem.onNavDestinationSelected(navController)
} }
override fun onSupportNavigateUp(): Boolean { override fun onSupportNavigateUp(): Boolean {

View File

@ -2,9 +2,11 @@ package de.christinecoenen.code.zapp.app.mediathek.ui.detail
import android.os.Bundle import android.os.Bundle
import android.view.* import android.view.*
import androidx.core.view.MenuProvider
import androidx.core.view.isVisible import androidx.core.view.isVisible
import androidx.fragment.app.Fragment import androidx.fragment.app.Fragment
import androidx.fragment.app.setFragmentResultListener import androidx.fragment.app.setFragmentResultListener
import androidx.lifecycle.Lifecycle
import androidx.lifecycle.lifecycleScope import androidx.lifecycle.lifecycleScope
import androidx.navigation.fragment.findNavController import androidx.navigation.fragment.findNavController
import androidx.navigation.fragment.navArgs import androidx.navigation.fragment.navArgs
@ -27,7 +29,7 @@ import kotlinx.coroutines.flow.*
import org.koin.android.ext.android.inject import org.koin.android.ext.android.inject
import timber.log.Timber import timber.log.Timber
class MediathekDetailFragment : Fragment() { class MediathekDetailFragment : Fragment(), MenuProvider {
private val args: MediathekDetailFragmentArgs by navArgs() private val args: MediathekDetailFragmentArgs by navArgs()
@ -41,11 +43,6 @@ class MediathekDetailFragment : Fragment() {
private var persistedMediathekShow: PersistedMediathekShow? = null private var persistedMediathekShow: PersistedMediathekShow? = null
private var downloadStatus = DownloadStatus.NONE private var downloadStatus = DownloadStatus.NONE
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setHasOptionsMenu(true)
}
override fun onCreateView( override fun onCreateView(
inflater: LayoutInflater, inflater: LayoutInflater,
container: ViewGroup?, container: ViewGroup?,
@ -68,6 +65,8 @@ class MediathekDetailFragment : Fragment() {
.collect(::updatePlaybackPosition) .collect(::updatePlaybackPosition)
} }
requireActivity().addMenuProvider(this, viewLifecycleOwner, Lifecycle.State.RESUMED)
return binding.root return binding.root
} }
@ -86,17 +85,17 @@ class MediathekDetailFragment : Fragment() {
downloadController.deleteDownloadsWithDeletedFiles() downloadController.deleteDownloadsWithDeletedFiles()
} }
override fun onCreateOptionsMenu(menu: Menu, inflater: MenuInflater) { override fun onCreateMenu(menu: Menu, menuInflater: MenuInflater) {
inflater.inflate(R.menu.mediathek_detail_fragment, menu) menuInflater.inflate(R.menu.mediathek_detail_fragment, menu)
} }
override fun onOptionsItemSelected(item: MenuItem): Boolean { override fun onMenuItemSelected(menuItem: MenuItem): Boolean {
return when (item.itemId) { return when (menuItem.itemId) {
R.id.menu_share -> { R.id.menu_share -> {
args.mediathekShow.shareExternally(requireContext()) args.mediathekShow.shareExternally(requireContext())
true true
} }
else -> super.onOptionsItemSelected(item) else -> false
} }
} }

View File

@ -4,10 +4,12 @@ import android.os.Bundle
import android.view.* import android.view.*
import android.widget.PopupMenu import android.widget.PopupMenu
import androidx.activity.OnBackPressedCallback import androidx.activity.OnBackPressedCallback
import androidx.core.view.MenuProvider
import androidx.core.view.isVisible import androidx.core.view.isVisible
import androidx.core.widget.NestedScrollView import androidx.core.widget.NestedScrollView
import androidx.core.widget.addTextChangedListener import androidx.core.widget.addTextChangedListener
import androidx.fragment.app.Fragment import androidx.fragment.app.Fragment
import androidx.lifecycle.Lifecycle
import androidx.lifecycle.lifecycleScope import androidx.lifecycle.lifecycleScope
import androidx.navigation.fragment.findNavController import androidx.navigation.fragment.findNavController
import androidx.paging.LoadState import androidx.paging.LoadState
@ -37,7 +39,7 @@ import java.util.*
import javax.net.ssl.SSLHandshakeException import javax.net.ssl.SSLHandshakeException
class MediathekListFragment : Fragment(), ListItemListener, OnRefreshListener { class MediathekListFragment : Fragment(), MenuProvider, ListItemListener, OnRefreshListener {
private var _binding: MediathekListFragmentBinding? = null private var _binding: MediathekListFragmentBinding? = null
private val binding: MediathekListFragmentBinding private val binding: MediathekListFragmentBinding
@ -65,12 +67,6 @@ class MediathekListFragment : Fragment(), ListItemListener, OnRefreshListener {
} }
} }
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setHasOptionsMenu(true)
}
override fun onCreateView( override fun onCreateView(
inflater: LayoutInflater, inflater: LayoutInflater,
container: ViewGroup?, container: ViewGroup?,
@ -101,6 +97,8 @@ class MediathekListFragment : Fragment(), ListItemListener, OnRefreshListener {
override fun onSlide(bottomSheet: View, slideOffset: Float) {} override fun onSlide(bottomSheet: View, slideOffset: Float) {}
}) })
requireActivity().addMenuProvider(this, viewLifecycleOwner, Lifecycle.State.RESUMED)
return binding.root return binding.root
} }
@ -159,25 +157,13 @@ class MediathekListFragment : Fragment(), ListItemListener, OnRefreshListener {
_bottomSheetBehavior = null _bottomSheetBehavior = null
} }
override fun onCreateOptionsMenu(menu: Menu, inflater: MenuInflater) { override fun onCreateMenu(menu: Menu, menuInflater: MenuInflater) {
inflater.inflate(R.menu.activity_main_toolbar, menu) menuInflater.inflate(R.menu.activity_main_toolbar, menu)
inflater.inflate(R.menu.mediathek_list_fragment, menu) menuInflater.inflate(R.menu.mediathek_list_fragment, menu)
} }
override fun onPrepareOptionsMenu(menu: Menu) { override fun onMenuItemSelected(menuItem: MenuItem): Boolean {
super.onPrepareOptionsMenu(menu) return when (menuItem.itemId) {
val filterIconResId = if (viewmodel.isFilterApplied.value == true) {
R.drawable.ic_sharp_filter_list_off_24
} else {
R.drawable.ic_sharp_filter_list_24
}
val filterItem = menu.findItem(R.id.menu_filter)
filterItem.setIcon(filterIconResId)
}
override fun onOptionsItemSelected(item: MenuItem): Boolean {
return when (item.itemId) {
R.id.menu_filter -> { R.id.menu_filter -> {
onFilterMenuClicked() onFilterMenuClicked()
true true
@ -186,10 +172,20 @@ class MediathekListFragment : Fragment(), ListItemListener, OnRefreshListener {
onRefresh() onRefresh()
true true
} }
else -> super.onOptionsItemSelected(item) else -> false
} }
} }
override fun onPrepareMenu(menu: Menu) {
val filterIconResId = if (viewmodel.isFilterApplied.value == true) {
R.drawable.ic_sharp_filter_list_off_24
} else {
R.drawable.ic_sharp_filter_list_24
}
val filterItem = menu.findItem(R.id.menu_filter)
filterItem.setIcon(filterIconResId)
}
override fun onShowClicked(show: MediathekShow) { override fun onShowClicked(show: MediathekShow) {
val directions = MediathekListFragmentDirections.toMediathekDetailFragment(show) val directions = MediathekListFragmentDirections.toMediathekDetailFragment(show)
findNavController().navigate(directions) findNavController().navigate(directions)

View File

@ -7,11 +7,9 @@ import android.content.ServiceConnection
import android.content.res.Configuration import android.content.res.Configuration
import android.os.Bundle import android.os.Bundle
import android.os.IBinder import android.os.IBinder
import android.view.KeyEvent import android.view.*
import android.view.Menu
import android.view.MenuItem
import android.view.View
import androidx.appcompat.app.AppCompatActivity import androidx.appcompat.app.AppCompatActivity
import androidx.core.view.MenuProvider
import androidx.core.view.WindowInsetsCompat import androidx.core.view.WindowInsetsCompat
import androidx.core.view.WindowInsetsControllerCompat import androidx.core.view.WindowInsetsControllerCompat
import androidx.lifecycle.lifecycleScope import androidx.lifecycle.lifecycleScope
@ -26,7 +24,7 @@ import org.koin.androidx.viewmodel.ext.android.viewModel
import timber.log.Timber import timber.log.Timber
abstract class AbstractPlayerActivity : abstract class AbstractPlayerActivity :
AppCompatActivity(), StyledPlayerView.ControllerVisibilityListener { AppCompatActivity(), MenuProvider, StyledPlayerView.ControllerVisibilityListener {
private val viewModel: AbstractPlayerActivityViewModel by viewModel() private val viewModel: AbstractPlayerActivityViewModel by viewModel()
@ -75,6 +73,8 @@ abstract class AbstractPlayerActivity :
binding.video.setControllerVisibilityListener(this) binding.video.setControllerVisibilityListener(this)
binding.video.requestFocus() binding.video.requestFocus()
binding.error.setOnClickListener { onErrorViewClick() } binding.error.setOnClickListener { onErrorViewClick() }
addMenuProvider(this)
} }
override fun onNewIntent(intent: Intent) { override fun onNewIntent(intent: Intent) {
@ -134,18 +134,16 @@ abstract class AbstractPlayerActivity :
handlePictureInPictureModeChanged(isInPictureInPictureMode) handlePictureInPictureModeChanged(isInPictureInPictureMode)
} }
override fun onCreateOptionsMenu(menu: Menu): Boolean { override fun onCreateMenu(menu: Menu, menuInflater: MenuInflater) {
menuInflater.inflate(R.menu.activity_abstract_player, menu) menuInflater.inflate(R.menu.activity_abstract_player, menu)
if (!supportsPictureInPictureMode(this)) { if (!supportsPictureInPictureMode(this)) {
menu.removeItem(R.id.menu_pip) menu.removeItem(R.id.menu_pip)
} }
return true
} }
override fun onOptionsItemSelected(item: MenuItem): Boolean { override fun onMenuItemSelected(menuItem: MenuItem): Boolean {
return when (item.itemId) { return when (menuItem.itemId) {
R.id.menu_share -> { R.id.menu_share -> {
onShareMenuItemClicked() onShareMenuItemClicked()
true true
@ -163,7 +161,7 @@ abstract class AbstractPlayerActivity :
finish() finish()
true true
} }
else -> super.onOptionsItemSelected(item) else -> false
} }
} }

View File

@ -2,7 +2,9 @@ package de.christinecoenen.code.zapp.app.settings.ui
import android.os.Bundle import android.os.Bundle
import android.view.* import android.view.*
import androidx.core.view.MenuProvider
import androidx.fragment.app.Fragment import androidx.fragment.app.Fragment
import androidx.lifecycle.Lifecycle
import androidx.navigation.fragment.findNavController import androidx.navigation.fragment.findNavController
import de.christinecoenen.code.zapp.R import de.christinecoenen.code.zapp.R
import de.christinecoenen.code.zapp.databinding.ChannelSelectionFragmentBinding import de.christinecoenen.code.zapp.databinding.ChannelSelectionFragmentBinding
@ -11,7 +13,7 @@ import de.christinecoenen.code.zapp.models.channels.json.SortableJsonChannelList
import de.christinecoenen.code.zapp.utils.view.GridAutofitLayoutManager import de.christinecoenen.code.zapp.utils.view.GridAutofitLayoutManager
import de.christinecoenen.code.zapp.utils.view.SimpleDragListListener import de.christinecoenen.code.zapp.utils.view.SimpleDragListListener
class ChannelSelectionFragment : Fragment() { class ChannelSelectionFragment : Fragment(), MenuProvider {
private var _binding: ChannelSelectionFragmentBinding? = null private var _binding: ChannelSelectionFragmentBinding? = null
private val binding: ChannelSelectionFragmentBinding get() = _binding!! private val binding: ChannelSelectionFragmentBinding get() = _binding!!
@ -25,8 +27,6 @@ class ChannelSelectionFragment : Fragment() {
channelList = SortableJsonChannelList(requireContext()) channelList = SortableJsonChannelList(requireContext())
listAdapter = ChannelSelectionAdapter(requireContext()) listAdapter = ChannelSelectionAdapter(requireContext())
setHasOptionsMenu(true)
} }
override fun onCreateView( override fun onCreateView(
@ -57,6 +57,8 @@ class ChannelSelectionFragment : Fragment() {
}) })
} }
requireActivity().addMenuProvider(this, viewLifecycleOwner, Lifecycle.State.RESUMED)
return binding.root return binding.root
} }
@ -66,19 +68,17 @@ class ChannelSelectionFragment : Fragment() {
channelList.persistChannelOrder() channelList.persistChannelOrder()
} }
override fun onCreateOptionsMenu(menu: Menu, inflater: MenuInflater) { override fun onCreateMenu(menu: Menu, menuInflater: MenuInflater) {
inflater.inflate(R.menu.channel_selection_fragment, menu) menuInflater.inflate(R.menu.channel_selection_fragment, menu)
} }
override fun onOptionsItemSelected(item: MenuItem): Boolean { override fun onMenuItemSelected(menuItem: MenuItem): Boolean {
return when (item.itemId) { return when (menuItem.itemId) {
R.id.menu_help -> { R.id.menu_help -> {
openHelpDialog() openHelpDialog()
true true
} }
else -> { else -> false
super.onOptionsItemSelected(item)
}
} }
} }