web-dev-qa-db-ja.com

Android CollapsingToolbarLayoutの子の場合、レイアウト動作は呼び出されません

CollapsingToolbarLayoutの子である要素にlayout_behaviorを設定しようとしていますが、iv_headerビューで動作が呼び出されることはありません。 tv_followビューなど、外部に固定すると完全に機能します。

ドキュメントには、layout_behaviorAppBarLayoutまたはCollapsingToolbarLayout内に適用できないと具体的に記載されていないため、機能しない理由がわかりません。

<?xml version="1.0" encoding="utf-8"?>
<Android.support.design.widget.CoordinatorLayout
    xmlns:Android="http://schemas.Android.com/apk/res/Android"
    xmlns:app="http://schemas.Android.com/apk/res-auto"
    Android:layout_width="match_parent"
    Android:layout_height="match_parent">

    <Android.support.design.widget.AppBarLayout
        Android:id="@+id/header"
        Android:layout_width="match_parent"
        Android:layout_height="@dimen/full_header_height"
        Android:focusable="true"
        Android:focusableInTouchMode="true">

        <Android.support.design.widget.CollapsingToolbarLayout
            Android:id="@+id/collapsing_toolbar"
            Android:layout_width="match_parent"
            Android:layout_height="match_parent"
            app:layout_scrollFlags="scroll|exitUntilCollapsed">

            <ImageView
                Android:id="@+id/iv_header"
                Android:layout_width="match_parent"
                Android:layout_height="match_parent"
                Android:scaleType="centerCrop"
                Android:contentDescription="@null"
                app:layout_behavior="com.package.view.HidingBehavior"
                app:layout_collapseMode="parallax"
                Android:src="@drawable/profile_background"/>

            <Android.support.v7.widget.Toolbar
                Android:id="@+id/header_toolbar"
                Android:layout_height="@dimen/action_bar_height"
                Android:layout_width="match_parent"
                Android:background="@drawable/toolbar_dark_gradient_half"
                Android:gravity="top"
                app:layout_collapseMode="pin"/>

        </Android.support.design.widget.CollapsingToolbarLayout>

    </Android.support.design.widget.AppBarLayout>

    <Android.support.v4.view.ViewPager
        Android:id="@+id/pager"
        Android:layout_width="match_parent"
        Android:layout_height="match_parent"
        app:layout_behavior="@string/appbar_scrolling_view_behavior"/>

    <TextView
        Android:id="@+id/tv_follow"
        Android:textSize="20sp"
        Android:textColor="@Android:color/white"
        Android:text="@string/follow"
        Android:drawableLeft="@drawable/comm_follow"
        Android:layout_width="wrap_content"
        Android:layout_height="wrap_content"
        app:layout_anchor="@id/header"
        app:layout_anchorGravity="center"
        app:layout_behavior="com.package.view.HidingBehavior"
        Android:drawablePadding="8dp"
        Android:gravity="center"
        Android:visibility="gone"
        Android:fitsSystemWindows="true"/>

</Android.support.design.widget.CoordinatorLayout>

動作は、デザインサポートライブラリのFloatingActionButtonコードから取得されました。

public class HidingBehavior extends CoordinatorLayout.Behavior<View>{
    private Rect tmpRect;
    private boolean isAnimatingOut;
    private FastOutSlowInInterpolator fastOutSlowInInterpolator = new FastOutSlowInInterpolator();

    public HidingBehavior() {
    }

    public HidingBehavior(Context context, AttributeSet attrs) {
        super();
    }

    @Override
    public boolean layoutDependsOn(CoordinatorLayout parent, View child, View dependency) {
        return dependency instanceof AppBarLayout;
    }

    @Override
    public boolean onDependentViewChanged(CoordinatorLayout parent, View child, View dependency) {
        if (dependency instanceof AppBarLayout) {
            AppBarLayout appBarLayout = (AppBarLayout) dependency;
            if (this.tmpRect == null) {
                this.tmpRect = new Rect();
            }

            Rect rect = this.tmpRect;
            ViewGroupUtils.getDescendantRect(parent, dependency, rect);
            if (rect.bottom <= getMinimumHeightForContext(appBarLayout)) {
                if(!this.isAnimatingOut && child.getVisibility() == View.VISIBLE) {
                    this.animateOut(child);
                }
            } else if(child.getVisibility() != View.VISIBLE) {
                this.animateIn(child);
            }
        }

        return false;
    }

    private int getMinimumHeightForContext(AppBarLayout appBarLayout) {
        int minHeight = ViewCompat.getMinimumHeight(appBarLayout);
        if(minHeight != 0) {
            return minHeight*2;
        } else {
            int childCount = appBarLayout.getChildCount();
            return childCount >= 1?ViewCompat.getMinimumHeight(appBarLayout.getChildAt(childCount - 1))*2:0;
        }
    }

    private void animateIn(View view) {
        view.setVisibility(View.VISIBLE);
        ViewCompat.animate(view)
                .scaleX(1.0F)
                .scaleY(1.0F)
                .alpha(1.0F)
                .setInterpolator(fastOutSlowInInterpolator)
                .withLayer()
                .setListener((ViewPropertyAnimatorListener)null).start();
    }

    private void animateOut(final View view) {
        ViewCompat.animate(view)
                .scaleX(0.0F)
                .scaleY(0.0F)
                .alpha(0.0F)
                .setInterpolator(fastOutSlowInInterpolator)
                .withLayer()
                .setListener(new ViewPropertyAnimatorListener() {
            public void onAnimationStart(View view) {
                HidingBehavior.this.isAnimatingOut = true;
            }

            public void onAnimationCancel(View view) {
                HidingBehavior.this.isAnimatingOut = false;
            }

            public void onAnimationEnd(View view) {
                HidingBehavior.this.isAnimatingOut = false;
                view.setVisibility(View.GONE);
            }
        }).start();
    }
}
9
bolder5

私が間違っていなければ、この行はあなたが現在持っている場所では不要です...

app:layout_behavior="com.package.view.HidingBehavior"

layout_behaviorは、(ネストされた)子ではなく、AppBarLayoutの兄弟に適用する必要があります。これは、CoordinatorLayout内の兄弟に、彼らがしていることに応じて彼らの行動を調整する必要がある方法を伝えるためです。

言い換えれば、あなたがそれを持っているところでは、それは調整他のビューとの動作ではありません。

11
rf43