5

I am using Activity class with (usually) one fragment as a content. In the Activity I use CollapsingToolbarLayout as some kind of header for some information and everything works fine. But in some cases (when some fragments are attached) I don't want to show that info, I don't want CollapsingToolbarLayout to open on scroll.

What I want to achieve is to lock CollapsingToolbarLayout, prevent it from opening from the fragment. I am collapsing it programmatically with appBarLayout.setExpanded(false, true);

Visual Vincent
  • 17,424
  • 5
  • 24
  • 66
urgas9
  • 796
  • 7
  • 20

2 Answers2

5

I came up with a different method as setting the nested scrolling flag only works when dragging the NestedScrollView. The appbar can still be expanded by swiping on the bar itself.

I set this up as a static function in "Utils" class. Obviously the flags you set upon unlocking will depend on which ones are relevant for your use case.

This function assumes you are are starting with an expanded toolbar

public static void LockToolbar(boolean locked, final AppBarLayout appbar, final CollapsingToolbarLayout toolbar) {

    if (locked) {
        // We want to lock so add the listener and collapse the toolbar
        appbar.addOnOffsetChangedListener(new AppBarLayout.OnOffsetChangedListener() {

            @Override
            public void onOffsetChanged(AppBarLayout appBarLayout, int verticalOffset) {
                if (toolbar.getHeight() + verticalOffset < 2 * ViewCompat.getMinimumHeight(toolbar)) {
                    // Now fully expanded again so remove the listener
                    appbar.removeOnOffsetChangedListener(this);
                } else {
                    // Fully collapsed so set the flags to lock the toolbar
                    AppBarLayout.LayoutParams lp = (AppBarLayout.LayoutParams) toolbar.getLayoutParams();
                    lp.setScrollFlags(AppBarLayout.LayoutParams.SCROLL_FLAG_ENTER_ALWAYS_COLLAPSED);
                }
            }
        });
        appbar.setExpanded(false, true);
    } else {
        // Unlock by restoring the flags and then expand 
        AppBarLayout.LayoutParams lp = (AppBarLayout.LayoutParams) toolbar.getLayoutParams();
        lp.setScrollFlags(AppBarLayout.LayoutParams.SCROLL_FLAG_SCROLL | AppBarLayout.LayoutParams.SCROLL_FLAG_EXIT_UNTIL_COLLAPSED);
        appbar.setExpanded(true, true);
    }

}
Kuffs
  • 34,562
  • 10
  • 74
  • 91
  • Why are you posting random code in response to my answer? As my answer does not use any arrays and your code is an exception generated by an array, they have no relevance to each other. – Kuffs Dec 01 '16 at 06:04
  • 2
    Attention! Don't forget call this line: toolbar.setLayoutParams(lp); Otherwise workaround doesn't work. – maXp Jun 19 '17 at 00:33
  • I had to add SCROLL_FLAG_SCROLL on top of SCROLL_FLAG_ENTER_ALWAYS_COLLAPSED. According to the doc, "this flag needs to be set for any of the other flags to take effect". – geecko Jul 15 '18 at 19:07
  • Why does enterAlwaysCollapsed lock the toolbar when it's collapsed? – Peter G. Williams May 08 '20 at 15:00
4

Well, I managed to solve it myself. The trick is to disable nested scrolling behaviour with ViewCompat.setNestedScrollingEnabled(recyclerView, expanded);

As I am using one fragment in the activity as a content view and putting it on the backstack I simply check when backstack has changed and which fragment is visibile. Note that I NestedScrollView in every fragment to trigger collapsible toolbar. This is my code:

getSupportFragmentManager().addOnBackStackChangedListener(new FragmentManager.OnBackStackChangedListener() {
        @Override
        public void onBackStackChanged() {
            NestedScrollView nestedScrollView = (NestedScrollView)findViewById(R.id.nested_scroll_view);
            int size = getSupportFragmentManager().getBackStackEntryCount();
            if (size >= 1 && nestedScrollView != null) {
                if (getSupportFragmentManager().getBackStackEntryAt(size - 1).getName().equals("SpotDetailsFragment")) {
                    Log.d(LOG_TAG, "Enabling collapsible toolbar.");
                    ViewCompat.setNestedScrollingEnabled(nestedScrollView, true);
                } else {
                    Log.d(LOG_TAG, "Disabling collapsible toolbar.");
                    ViewCompat.setNestedScrollingEnabled(nestedScrollView, false);
                }
            }
        }
    });

This thread helped me a lot, where another possible solution is presented: Need to disable expand on CollapsingToolbarLayout for certain fragments

Community
  • 1
  • 1
urgas9
  • 796
  • 7
  • 20