別のCorodinatorLayout
内のCoordinatorLayout
。子ビューをスクロールすると、親CoordinatorLayout
もスクロールします。
coordinatorLayout
に異なるViewPager
を含むFragment
があり、Scroll
でtabLayout
を非表示にします
coordinatorLayout
を持つ別のviewPager
があります。このfragment
は、親フラグメント(parent Coordinator layout
)のViewPager
で拡張されます。
問題はonScrolling
です。childViewpager
の子フラグメントは、fragment
を非表示にするために必要な親coordinator layout
ではなく、tablayout
のcoordinator layout
にのみ反映されます。
構造は次のとおりです。
CoordinatorLayout(p) ->(tablayout(p) & ViewPager(p) -> CoordinatorLayout(c) ->(tablayout(c) & ViewPAger(c) ->recyclerView(cc)))
p -> parent;
c -> child; cc -> child to child
スクロールリサイクラビューの作成方法は、両方のcoordinator layoutに影響するため、toolbar tablayout(p)は非表示になります。
私はそれが古い質問であることを知っています。しかし、別のCoordinatorLayout
にあるフラグメントにCoordinatorLayout
を含めるために長い間検索しました。
Dev.bmaxの答えを少し変更して、両方のコーディネーターレイアウトを呼び出し、両方のレイアウトの添付の動作を呼び出しました。
だからここに私の解決策があります。
@SuppressWarnings("unused")
public class NestedCoordinatorLayout extends CoordinatorLayout implements NestedScrollingChild {
private NestedScrollingChildHelper mChildHelper;
public NestedCoordinatorLayout(Context context) {
super(context);
mChildHelper = new NestedScrollingChildHelper(this);
setNestedScrollingEnabled(true);
}
public NestedCoordinatorLayout(Context context, AttributeSet attrs) {
super(context, attrs);
mChildHelper = new NestedScrollingChildHelper(this);
setNestedScrollingEnabled(true);
}
public NestedCoordinatorLayout(Context context, AttributeSet attrs, int defStyleAttr) {
super(context, attrs, defStyleAttr);
mChildHelper = new NestedScrollingChildHelper(this);
setNestedScrollingEnabled(true);
}
@Override
public boolean onStartNestedScroll(View child, View target, int nestedScrollAxes) {
/* Enable the scrolling behavior of our own children */
boolean tHandled = super.onStartNestedScroll(child, target, nestedScrollAxes);
/* Enable the scrolling behavior of the parent's other children */
return startNestedScroll(nestedScrollAxes) || tHandled;
}
@Override
public void onStopNestedScroll(View target) {
/* Disable the scrolling behavior of our own children */
super.onStopNestedScroll(target);
/* Disable the scrolling behavior of the parent's other children */
stopNestedScroll();
}
@Override
public void onNestedPreScroll(View target, int dx, int dy, int[] consumed) {
int[][] tConsumed = new int[2][2];
super.onNestedPreScroll(target, dx, dy, tConsumed[0]);
dispatchNestedPreScroll(dx, dy, tConsumed[1], null);
consumed[0] = tConsumed[0][0] + tConsumed[1][0];
consumed[1] = tConsumed[0][1] + tConsumed[1][1];
}
@Override
public void onNestedScroll(View target, int dxConsumed, int dyConsumed,
int dxUnconsumed, int dyUnconsumed) {
super.onNestedScroll(target, dxConsumed, dyConsumed, dxUnconsumed, dyUnconsumed);
dispatchNestedScroll(dxConsumed, dyConsumed, dxUnconsumed, dyUnconsumed, null);
}
@Override
public boolean onNestedPreFling(View target, float velocityX, float velocityY) {
boolean tHandled = super.onNestedPreFling(target, velocityX, velocityY);
return dispatchNestedPreFling(velocityX, velocityY) || tHandled;
}
@Override
public boolean onNestedFling(View target, float velocityX, float velocityY, boolean consumed) {
boolean tHandled = super.onNestedFling(target, velocityX, velocityY, consumed);
return dispatchNestedFling(velocityX, velocityY, consumed) || tHandled;
}
@Override
public void setNestedScrollingEnabled(boolean enabled) {
mChildHelper.setNestedScrollingEnabled(enabled);
}
@Override
public boolean isNestedScrollingEnabled() {
return mChildHelper.isNestedScrollingEnabled();
}
@Override
public boolean startNestedScroll(int axes) {
return mChildHelper.startNestedScroll(axes);
}
@Override
public void stopNestedScroll() {
mChildHelper.stopNestedScroll();
}
@Override
public boolean hasNestedScrollingParent() {
return mChildHelper.hasNestedScrollingParent();
}
@Override
public boolean dispatchNestedScroll(int dxConsumed, int dyConsumed, int dxUnconsumed,
int dyUnconsumed, int[] offsetInWindow) {
return mChildHelper.dispatchNestedScroll(dxConsumed, dyConsumed, dxUnconsumed,
dyUnconsumed, offsetInWindow);
}
@Override
public boolean dispatchNestedPreScroll(int dx, int dy, int[] consumed, int[] offsetInWindow) {
return mChildHelper.dispatchNestedPreScroll(dx, dy, consumed, offsetInWindow);
}
@Override
public boolean dispatchNestedFling(float velocityX, float velocityY, boolean consumed) {
return mChildHelper.dispatchNestedFling(velocityX, velocityY, consumed);
}
@Override
public boolean dispatchNestedPreFling(float velocityX, float velocityY) {
return mChildHelper.dispatchNestedPreFling(velocityX, velocityY);
}
}
ネストされたコーディネーターレイアウトの簡単な実装を次に示します。
/**
* This variation of CoordinatorLayout also serves as a nested scrolling child,
* which supports passing nested scrolling operations to it's parent when it's
* own nested scrolling is locked.
*/
public class NestedCoordinatorLayout extends CoordinatorLayout implements NestedScrollingChild {
private NestedScrollingChildHelper mChildHelper;
private volatile boolean mPassToParent;
public NestedCoordinatorLayout(Context context) {
super(context);
mChildHelper = new NestedScrollingChildHelper(this);
setNestedScrollingEnabled(true);
}
public NestedCoordinatorLayout(Context context, AttributeSet attrs) {
super(context, attrs);
mChildHelper = new NestedScrollingChildHelper(this);
setNestedScrollingEnabled(true);
}
public NestedCoordinatorLayout(Context context, AttributeSet attrs, int defStyleAttr) {
super(context, attrs, defStyleAttr);
mChildHelper = new NestedScrollingChildHelper(this);
setNestedScrollingEnabled(true);
}
/**
* Locks the nested scrolling. Further scroll events will
* be passed to the nested scrolling parent.
*/
public void lockNestedScrolling() {
mPassToParent = true;
}
/**
* Unlocks the nested scrolling. Further scroll events will
* be dispatched to this layout's own scrolling children.
*/
public void unlockNestedScrolling() {
mPassToParent = false;
}
/*
* NestedScrollingParent implementation
*/
@Override
public boolean onStartNestedScroll(View child, View target, int nestedScrollAxes) {
/* Enable the scrolling behavior of our own children */
super.onStartNestedScroll(child, target, nestedScrollAxes);
/* Enable the scrolling behavior of the parent's other children */
startNestedScroll(nestedScrollAxes);
/* Start tracking the current scroll */
return true;
}
@Override
public void onStopNestedScroll(View target) {
/* Disable the scrolling behavior of our own children */
super.onStopNestedScroll(target);
/* Disable the scrolling behavior of the parent's other children */
stopNestedScroll();
}
@Override
public void onNestedPreScroll(View target, int dx, int dy, int[] consumed) {
if (mPassToParent) {
dispatchNestedPreScroll(dx, dy, consumed, null);
} else {
super.onNestedPreScroll(target, dx, dy, consumed);
}
}
@Override
public void onNestedScroll(View target, int dxConsumed, int dyConsumed,
int dxUnconsumed, int dyUnconsumed) {
if (mPassToParent) {
dispatchNestedScroll(dxConsumed, dyConsumed, dxUnconsumed, dyUnconsumed, null);
} else {
super.onNestedScroll(target, dxConsumed, dyConsumed, dxUnconsumed, dyUnconsumed);
}
}
@Override
public boolean onNestedPreFling(View target, float velocityX, float velocityY) {
if (mPassToParent) {
return dispatchNestedPreFling(velocityX, velocityY);
} else {
return super.onNestedPreFling(target, velocityX, velocityY);
}
}
@Override
public boolean onNestedFling(View target, float velocityX, float velocityY, boolean consumed) {
if (mPassToParent) {
return dispatchNestedFling(velocityX, velocityY, consumed);
} else {
return super.onNestedFling(target, velocityX, velocityY, consumed);
}
}
/*
* NestedScrollingChild implementation
*/
@Override
public void setNestedScrollingEnabled(boolean enabled) {
mChildHelper.setNestedScrollingEnabled(enabled);
}
@Override
public boolean isNestedScrollingEnabled() {
return mChildHelper.isNestedScrollingEnabled();
}
@Override
public boolean startNestedScroll(int axes) {
return mChildHelper.startNestedScroll(axes);
}
@Override
public void stopNestedScroll() {
mChildHelper.stopNestedScroll();
}
@Override
public boolean hasNestedScrollingParent() {
return mChildHelper.hasNestedScrollingParent();
}
@Override
public boolean dispatchNestedScroll(int dxConsumed, int dyConsumed, int dxUnconsumed,
int dyUnconsumed, int[] offsetInWindow) {
return mChildHelper.dispatchNestedScroll(dxConsumed, dyConsumed, dxUnconsumed,
dyUnconsumed, offsetInWindow);
}
@Override
public boolean dispatchNestedPreScroll(int dx, int dy, int[] consumed, int[] offsetInWindow) {
return mChildHelper.dispatchNestedPreScroll(dx, dy, consumed, offsetInWindow);
}
@Override
public boolean dispatchNestedFling(float velocityX, float velocityY, boolean consumed) {
return mChildHelper.dispatchNestedFling(velocityX, velocityY, consumed);
}
@Override
public boolean dispatchNestedPreFling(float velocityX, float velocityY) {
return mChildHelper.dispatchNestedPreFling(velocityX, velocityY);
}
}
私はこれをライブラリにしました、それを見てください GitHubで 。
使用するのは<NestedScrollCoordinatorLayout>
レイアウトで。
うまくいけば、これは他の人を助けるでしょう。 preScrollで実装したアイデアは、既に0である場合に親が消費できる量を計算し、super.onNestedPreScroll
を呼び出します。
コードは次のとおりです。
import Android.content.Context;
import Android.support.annotation.Nullable;
import Android.support.design.widget.CoordinatorLayout;
import Android.support.v4.view.NestedScrollingChild2;
import Android.support.v4.view.NestedScrollingChildHelper;
import Android.util.AttributeSet;
import Android.view.View;
public class NestedScrollCoordinatorLayout extends CoordinatorLayout implements NestedScrollingChild2 {
private NestedScrollingChildHelper mChildHelper;
public NestedScrollCoordinatorLayout(Context context) {
super(context);
mChildHelper = new NestedScrollingChildHelper(this);
setNestedScrollingEnabled(true);
}
public NestedScrollCoordinatorLayout(Context context, AttributeSet attrs) {
super(context, attrs);
mChildHelper = new NestedScrollingChildHelper(this);
setNestedScrollingEnabled(true);
}
public NestedScrollCoordinatorLayout(Context context, AttributeSet attrs, int defStyleAttr) {
super(context, attrs, defStyleAttr);
mChildHelper = new NestedScrollingChildHelper(this);
setNestedScrollingEnabled(true);
}
@Override
public boolean isNestedScrollingEnabled() {
return mChildHelper.isNestedScrollingEnabled();
}
@Override
public void setNestedScrollingEnabled(boolean enabled) {
mChildHelper.setNestedScrollingEnabled(enabled);
}
@Override
public boolean hasNestedScrollingParent() {
return mChildHelper.hasNestedScrollingParent();
}
@Override
public boolean hasNestedScrollingParent(int type) {
return mChildHelper.hasNestedScrollingParent(type);
}
@Override
public boolean onStartNestedScroll(View child, View target, int axes, int type) {
boolean superResult = super.onStartNestedScroll(child, target, axes, type);
return startNestedScroll(axes, type) || superResult;
}
@Override
public boolean onStartNestedScroll(View child, View target, int nestedScrollAxes) {
boolean superResult = super.onStartNestedScroll(child, target, nestedScrollAxes);
return startNestedScroll(nestedScrollAxes) || superResult;
}
@Override
public void onNestedPreScroll(View target, int dx, int dy, int[] consumed, int type) {
dispatchNestedPreScroll(dx, dy, consumed, null);
if (consumed[1] == 0) {
super.onNestedPreScroll(target, dx, dy, consumed, type);
}
}
@Override
public void onNestedPreScroll(View target, int dx, int dy, int[] consumed) {
dispatchNestedPreScroll(dx, dy, consumed, null);
if (consumed[1] == 0) {
super.onNestedPreScroll(target, dx, dy, consumed);
}
}
@Override
public void onNestedScroll(View target, int dxConsumed, int dyConsumed, int dxUnconsumed, int dyUnconsumed, int type) {
super.onNestedScroll(target, dxConsumed, dyConsumed, dxUnconsumed, dyUnconsumed, type);
dispatchNestedScroll(dxConsumed, dyConsumed, dxUnconsumed, dyUnconsumed, null, type);
}
@Override
public void onNestedScroll(View target, int dxConsumed, int dyConsumed, int dxUnconsumed, int dyUnconsumed) {
super.onNestedScroll(target, dxConsumed, dyConsumed, dxUnconsumed, dyUnconsumed);
dispatchNestedScroll(dxConsumed, dyConsumed, dxUnconsumed, dyUnconsumed, null);
}
@Override
public void onStopNestedScroll(View target, int type) {
super.onStopNestedScroll(target, type);
stopNestedScroll(type);
}
@Override
public void onStopNestedScroll(View target) {
super.onStopNestedScroll(target);
stopNestedScroll();
}
@Override
public boolean onNestedPreFling(View target, float velocityX, float velocityY) {
boolean superResult = super.onNestedPreFling(target, velocityX, velocityY);
return dispatchNestedPreFling(velocityX, velocityY) || superResult;
}
@Override
public boolean onNestedFling(View target, float velocityX, float velocityY, boolean consumed) {
boolean superResult = super.onNestedFling(target, velocityX, velocityY, consumed);
return dispatchNestedFling(velocityX, velocityY, consumed) || superResult;
}
@Override
public boolean startNestedScroll(int axes, int type) {
return mChildHelper.startNestedScroll(axes, type);
}
@Override
public boolean startNestedScroll(int axes) {
return mChildHelper.startNestedScroll(axes);
}
@Override
public void stopNestedScroll() {
mChildHelper.stopNestedScroll();
}
@Override
public void stopNestedScroll(int type) {
mChildHelper.stopNestedScroll(type);
}
@Override
public boolean dispatchNestedScroll(int dxConsumed, int dyConsumed, int dxUnconsumed, int dyUnconsumed, @Nullable int[] offsetInWindow, int type) {
return mChildHelper.dispatchNestedScroll(dxConsumed, dyConsumed, dxUnconsumed, dyUnconsumed, offsetInWindow, type);
}
@Override
public boolean dispatchNestedScroll(int dxConsumed, int dyConsumed, int dxUnconsumed, int dyUnconsumed, @Nullable int[] offsetInWindow) {
return mChildHelper.dispatchNestedScroll(dxConsumed, dyConsumed, dxUnconsumed, dyUnconsumed, offsetInWindow);
}
@Override
public boolean dispatchNestedPreScroll(int dx, int dy, @Nullable int[] consumed, @Nullable int[] offsetInWindow) {
return mChildHelper.dispatchNestedPreScroll(dx, dy, consumed, offsetInWindow);
}
@Override
public boolean dispatchNestedPreScroll(int dx, int dy, @Nullable int[] consumed, @Nullable int[] offsetInWindow, int type) {
return mChildHelper.dispatchNestedPreScroll(dx, dy, consumed, offsetInWindow, type);
}
@Override
public boolean dispatchNestedPreFling(float velocityX, float velocityY) {
return mChildHelper.dispatchNestedPreFling(velocityX, velocityY);
}
@Override
public boolean dispatchNestedFling(float velocityX, float velocityY, boolean consumed) {
return mChildHelper.dispatchNestedFling(velocityX, velocityY, consumed);
}
}
こちらもご覧ください Gist on GithHub
残念ながら、これはCoordinatorLayout
でサポートされていません。
NestedScrollingChildHelper.startNestedScroll()
およびCoordinatorLayout.onStartNestedScroll()
のコードを確認してください。ネストされたスクロールイベントは、内部Behavior
のCoordinatorLayout
sのいずれかが消費すると「消費」され、それ以上伝播されません。
CHILD CoordinatorLayoutをカスタマイズし、NestedScrollingChildを実装させ(ori coordinatorlayoutは実装しなかった)、いくつかの関数をオーバーライドして、ネストされたスクロールイベントをPARENT CoordinatorLayoutにディスパッチできるようにする必要があります。
リポジトリに ChildCoordinatorLayout を1つ記述しました nestrefresh 。このレポでは、1つのAppBarLayoutをChildCoordinatorLayoutでラップし、プルリフレッシュ動作でChildCoordinatorLayoutのプルリフレッシュも追加します。そして、dyUnConsumedはまず親を、次に子を与えます。これはコードです:
class ChildCoordinatorLayout @JvmOverloads constructor(
context: Context,
attrs: AttributeSet? = null,
defStyleAttr: Int = 0
) : CoordinatorLayout(context, attrs, defStyleAttr), NestedScrollingChild2 {
private lateinit var childHelper: NestedScrollingChildHelper
init {
init()
}
private fun init() {
childHelper = NestedScrollingChildHelper(this)
childHelper.isNestedScrollingEnabled = true
}
override fun setNestedScrollingEnabled(enabled: Boolean) {
childHelper.isNestedScrollingEnabled = enabled
}
override fun isNestedScrollingEnabled(): Boolean {
return childHelper.isNestedScrollingEnabled
}
override fun startNestedScroll(i: Int, i1: Int): Boolean {
return childHelper.startNestedScroll(i, i1)
}
override fun stopNestedScroll(i: Int) {
childHelper.stopNestedScroll(i)
}
override fun hasNestedScrollingParent(i: Int): Boolean {
return childHelper.hasNestedScrollingParent()
}
override fun dispatchNestedScroll(i: Int, i1: Int, i2: Int, i3: Int, ints: IntArray?, i4: Int): Boolean {
return childHelper.dispatchNestedScroll(i, i1, i2, i3, ints, i4)
}
override fun dispatchNestedPreScroll(i: Int, i1: Int, ints: IntArray?, ints1: IntArray?, i2: Int): Boolean {
return childHelper.dispatchNestedPreScroll(i, i1, ints, ints1, i2)
}
override fun dispatchNestedPreFling(velocityX: Float, velocityY: Float): Boolean {
return childHelper.dispatchNestedPreFling(velocityX, velocityY)
}
override fun dispatchNestedFling(velocityX: Float, velocityY: Float, consumed: Boolean): Boolean {
return childHelper.dispatchNestedFling(velocityX, velocityY, consumed)
}
override fun onStartNestedScroll(child: View, target: View, axes: Int, type: Int): Boolean {
if (type == TYPE_TOUCH) {
stopNestedScroll(TYPE_NON_TOUCH)
ViewCompat.stopNestedScroll(child, TYPE_NON_TOUCH)
}
val handle = super.onStartNestedScroll(child, target, axes, type)
return startNestedScroll(axes, type) || handle
}
override fun onStopNestedScroll(target: View, type: Int) {
super.onStopNestedScroll(target, type)
stopNestedScroll(type)
}
override fun onNestedPreScroll(target: View, dx: Int, dy: Int, consumed: IntArray, type: Int) {
val thisConsume = IntArray(2)
dispatchNestedPreScroll(dx, dy, thisConsume, null, type)
consumed[0] += thisConsume[0]
consumed[1] += thisConsume[1]
thisConsume[0] = 0
thisConsume[1] = 0
super.onNestedPreScroll(target, dx - consumed[0], dy - consumed[1], thisConsume, type)
consumed[0] += thisConsume[0]
consumed[1] += thisConsume[1]
}
override fun onNestedScroll(
target: View,
dxConsumed: Int,
dyConsumed: Int,
dxUnconsumed: Int,
dyUnconsumed: Int,
type: Int
) {
val offsetInWindow = IntArray(2)
target.getLocationInWindow(offsetInWindow)
val startX = offsetInWindow[0]
val startY = offsetInWindow[1]
super.onNestedScroll(target, dxConsumed, dyConsumed, dxUnconsumed, dyUnconsumed, type)
target.getLocationInWindow(offsetInWindow)
offsetInWindow[0] -= startX
offsetInWindow[1] -= startY
dispatchNestedScroll(dxConsumed, dyConsumed, dxUnconsumed + offsetInWindow[0]
, dyUnconsumed + offsetInWindow[1], null, type)
}
override fun onNestedPreFling(target: View, velocityX: Float, velocityY: Float): Boolean {
val handled = super.onNestedPreFling(target, velocityX, velocityY)
return dispatchNestedPreFling(velocityX, velocityY) || handled
}
override fun onNestedFling(target: View, velocityX: Float, velocityY: Float, consumed: Boolean): Boolean {
val handled = super.onNestedFling(target, velocityX, velocityY, consumed)
return dispatchNestedFling(velocityX, velocityY, consumed) || handled
}
}