如何在 Android 中旋转屏幕时禁用重新创建片段
How to disable recreate fragment when rotate screen in Android
在我的应用程序中,我使用 NavigationComponent
显示 Fragments
并且我使用 ViewModel
!
但是旋转屏幕重新创建片段并删除所有位置,再次调用 api 等等...
我的片段代码:
@AndroidEntryPoint
class HomeFragment : Fragment() {
//Binding
private lateinit var binding: FragmentHomeBinding
@Inject
lateinit var genreAdapter: GenreAdapter
@Inject
lateinit var topMoviesAdapter: TopMoviesAdapter
private val viewModel: HomeViewModel by viewModels()
override fun onCreateView(inflater: LayoutInflater, container: ViewGroup?, savedInstanceState: Bundle?): View {
binding = FragmentHomeBinding.inflate(inflater, container, false)
return binding.root
}
override fun onViewCreated(view: View, savedInstanceState: Bundle?) {
super.onViewCreated(view, savedInstanceState)
//InitViews
binding.apply {
//Genres
viewModel.genresList.observe(viewLifecycleOwner) {
genreAdapter.differ.submitList(it)
genresRecycler.initRecycler(
LinearLayoutManager(requireContext(), LinearLayoutManager.HORIZONTAL, false),
genreAdapter
)
}
viewModel.loadGenresList()
//Top movies
viewModel.topMoviesList.observe(viewLifecycleOwner) {
topMoviesAdapter.differ.submitList(it.data)
topMoviesRecycler.initRecycler(
LinearLayoutManager(requireContext(), LinearLayoutManager.HORIZONTAL, false),
topMoviesAdapter
)
topMoviesRecycler.smoothScrollToPosition(4)
}
viewModel.loadTopMoviesList(1)
//Loading
viewModel.loading.observe(viewLifecycleOwner) {
if (it) {
homeLoading.showInvisible(true)
} else {
homeLoading.showInvisible(false)
}
}
}
}
}
ViewModel 代码:
@HiltViewModel
class HomeViewModel @Inject constructor(private val repository: HomeRepository) : ViewModel() {
val genresList = MutableLiveData<List<ResponseGenres.ResponseGenresItem>>()
val topMoviesList = MutableLiveData<ResponseMovies>()
val loading = MutableLiveData<Boolean>()
fun loadGenresList() = viewModelScope.launch {
val response = repository.genresList()
if (response.isSuccessful) {
genresList.postValue(response.body())
}
}
fun loadTopMoviesList(id: Int) = viewModelScope.launch {
loading.postValue(true)
val response = repository.topMoviesList(id)
if (response.isSuccessful) {
topMoviesList.postValue(response.body())
}
loading.postValue(false)
}
}
如何修复它并禁用重新创建片段?
我建议避免使用 API 的 re-call,但从未想过禁用在片段中重新创建片段,因为这是一个 Android 架构。
简单的,重写Fragment中的onCreate()
方法,将调用API的逻辑移到里面。
viewModel.loadGenresList()
这将调用一次,因为 onCreate()
即使在屏幕旋转后也只创建一次
在我的应用程序中,我使用 NavigationComponent
显示 Fragments
并且我使用 ViewModel
!
但是旋转屏幕重新创建片段并删除所有位置,再次调用 api 等等...
我的片段代码:
@AndroidEntryPoint
class HomeFragment : Fragment() {
//Binding
private lateinit var binding: FragmentHomeBinding
@Inject
lateinit var genreAdapter: GenreAdapter
@Inject
lateinit var topMoviesAdapter: TopMoviesAdapter
private val viewModel: HomeViewModel by viewModels()
override fun onCreateView(inflater: LayoutInflater, container: ViewGroup?, savedInstanceState: Bundle?): View {
binding = FragmentHomeBinding.inflate(inflater, container, false)
return binding.root
}
override fun onViewCreated(view: View, savedInstanceState: Bundle?) {
super.onViewCreated(view, savedInstanceState)
//InitViews
binding.apply {
//Genres
viewModel.genresList.observe(viewLifecycleOwner) {
genreAdapter.differ.submitList(it)
genresRecycler.initRecycler(
LinearLayoutManager(requireContext(), LinearLayoutManager.HORIZONTAL, false),
genreAdapter
)
}
viewModel.loadGenresList()
//Top movies
viewModel.topMoviesList.observe(viewLifecycleOwner) {
topMoviesAdapter.differ.submitList(it.data)
topMoviesRecycler.initRecycler(
LinearLayoutManager(requireContext(), LinearLayoutManager.HORIZONTAL, false),
topMoviesAdapter
)
topMoviesRecycler.smoothScrollToPosition(4)
}
viewModel.loadTopMoviesList(1)
//Loading
viewModel.loading.observe(viewLifecycleOwner) {
if (it) {
homeLoading.showInvisible(true)
} else {
homeLoading.showInvisible(false)
}
}
}
}
}
ViewModel 代码:
@HiltViewModel
class HomeViewModel @Inject constructor(private val repository: HomeRepository) : ViewModel() {
val genresList = MutableLiveData<List<ResponseGenres.ResponseGenresItem>>()
val topMoviesList = MutableLiveData<ResponseMovies>()
val loading = MutableLiveData<Boolean>()
fun loadGenresList() = viewModelScope.launch {
val response = repository.genresList()
if (response.isSuccessful) {
genresList.postValue(response.body())
}
}
fun loadTopMoviesList(id: Int) = viewModelScope.launch {
loading.postValue(true)
val response = repository.topMoviesList(id)
if (response.isSuccessful) {
topMoviesList.postValue(response.body())
}
loading.postValue(false)
}
}
如何修复它并禁用重新创建片段?
我建议避免使用 API 的 re-call,但从未想过禁用在片段中重新创建片段,因为这是一个 Android 架构。
简单的,重写Fragment中的onCreate()
方法,将调用API的逻辑移到里面。
viewModel.loadGenresList()
这将调用一次,因为 onCreate()
即使在屏幕旋转后也只创建一次