I'm stuck on viewpager2 problem on Android. I have a viewpager2 creating some fragments depending on the position. Each fragment has a next button to navigate horizontally in the view pager.
But when I asked for the next page from the button, I had the action of sliding twice. It like the method createFragment from the adapter was called twice, due to the preload of the fragment borders...
Activity who manage the view pager:
class ConfigurationActivity : AppCompatActivity() {
private var viewPager : ViewPager2? = null
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContentView(R.layout.activity_configuration)
viewPager = viewPager2
val instance = this
viewPager!!.apply {
isUserInputEnabled = true
orientation = ViewPager2.ORIENTATION_HORIZONTAL
if(viewPager!!.adapter == null)
viewPager!!.adapter = ConfigAdapter(supportFragmentManager, lifecycle, instance, 2)
}
viewPager!!.registerOnPageChangeCallback(object : ViewPager2.OnPageChangeCallback() {
override fun onPageSelected(position: Int) {
super.onPageSelected(position)
currentItem = position
}
})
}
companion object{
private var currentItem : Int = 0
fun nextPage(instance : ConfigurationActivity, currentPosition : Int?){
instance.viewPager!!.currentItem = currentItem + 1
}
}
}
The FragmentStateAdapter
class ConfigAdapter(fm: FragmentManager, lc : Lifecycle, private val instance : ConfigurationActivity, configSnapshot : ArrayList<Configuration>) : FragmentStateAdapter(fm, lc) {
private val configSize = configSnapshot.size
override fun getItemCount(): Int {
val length = configSize + 3
instance.pageIndicatorView.count = length
return length
}
override fun createFragment(position: Int): Fragment {
Timber.d("creating fragment at position $position")
return when(position){
0 -> WelcomeFragment(instance)
in 1..configSize /* position between 1 and configSize (included) */ -> ConfigureFragment(instance, position-1)
1 + configSize -> IdentifyFragment(instance)
2 + configSize -> EndFragment()
else -> Fragment()
}
}
}
A fragment example:
class ConfigureFragment(private val instance : ConfigurationActivity, private val configPosition: Int) : Fragment() {
...
view.button_continue.setOnClickListener {
nextPage(instance, configPosition+1)
}
...
}
Try like this way:-
First of all change viewPager
variable private
to public
in Activity like removing private
keyword.
var viewPager : ViewPager2? = null
In fragment change setOnClickListener
method like below:
view.button_continue.setOnClickListener {
instance!!.viewPager!!.arrowScroll(View.FOCUS_RIGHT)
}
*Suggestion:
In fragment, we can get parent activity instance and use this way instead of passing activity instance to each fragment.
val instance = ((activity as AppCompatActivity) as ConfigurationActivity)