javaandroidtabsandroid-lifecycleandroid-search

Android: Tabs and searchbars


I have two tabs and each tabs has its own searchbar.

I bind the searchbar in onCreateOptionsMenu. However, the searchbars only work if I leave the screen once and return to the screen (meaning it needs one more lifecycle for the searchbars to react). I confirmed that onCreateOptionsMenu is indeed called two times at the time of the creation of the ViewPagerFragment.

I bind them like this:

MenuItem searchItem = menu.findItem(R.id.search);
searchItem.setVisible(true);

SearchView searchView = (SearchView) searchItem.getActionView();
searchView.setImeOptions(EditorInfo.IME_ACTION_DONE);

searchView.setOnQueryTextListener(new SearchView.OnQueryTextListener() {
   @Override
    public boolean onQueryTextSubmit(String query) {
          ...
          return false;
     }

     @Override
     public boolean onQueryTextChange(String newText) {
           ...
          return false;
     }
});

I am guessing this bug is related to the tabs. How do implement a working searchbar with tabs (i.e. viewpager2)?


I call this on onCreateOptionsMenu:

public void onCreateOptionsMenu(@NonNull Menu menu, @NonNull MenuInflater inflater) {
    super.onCreateOptionsMenu(menu, inflater);
    // Call the above...
}

The ViewPager hosting them looks like this:

private void init(View view) {
    ViewPager2 viewPager2 = view.findViewById(R.id.view_pager_fragment_view_pager);
    TabLayout tabLayout = view.findViewById(R.id.tab_layout_fragment_view_pager);
    viewPager2.setUserInputEnabled(true);

    viewPager2.setAdapter(new ViewPagerFragmentAdapter(ViewPagerFragment.this));
    viewPager2.setOffscreenPageLimit(5);

    new TabLayoutMediator
            (tabLayout, viewPager2,
                    (tab, position) -> tab.setText(titles[position])).attach();
}

Solution

  • OP and I were communicating while we found a solution.

    First each fragment was changed to

    public class MergedItemsFragment extends Fragment implements SearchView.OnQueryTextListener {
    
        /// ------------------------------
        /// SearchView.OnQueryTextListener
    
        @Override
        public boolean onQueryTextSubmit(String query) {
            // ...
            return false;
    
        }
    
        @Override
        public boolean onQueryTextChange(String newText) {
            // ...
            return false;
    
        }
    
        /// --------
        /// Fragment
    
        @Override
        public View onCreateView(@NonNull LayoutInflater inflater, ViewGroup container,
                                 Bundle savedInstanceState) {
    
            return inflater.inflate(R.layout.fragment_merged_items, container, false);
    
        }
    
        @Override
        public void onCreateOptionsMenu(@NonNull Menu menu, @NonNull MenuInflater inflater) {
            super.onCreateOptionsMenu(menu, inflater);
    
            final MenuItem   searchItem = menu.findItem(R.id.search);
            final SearchView searchView = (SearchView) searchItem.getActionView();
    
            searchView.setImeOptions(EditorInfo.IME_ACTION_DONE);
            searchView.setOnQueryTextListener(this);
    
        }
    
    }
    
    

    If any more code is desired, i'd be happy to post what I have, and if I come up with a solution using viewPager2.setOffscreenPageLimit(5); i.e. caching, i'll post that as well