滚动WebView时如何实现隐藏工具栏?

时间:2019-03-29 10:19:26

标签: java android webview toolbar android-coordinatorlayout

我有一个带有WebView和我自己的AppBarLayout的Activity。 我想在滚动WebView时实现隐藏/显示带有动画的AppBarLayout,就像在Google Chrome应用中一样。

enter image description here

我尝试了不同的方法。

  • ObservableWebView,但是它无法正常运行,它并不总是显示AppBar,尤其是在页面较短的情况下。

  • 带有动画的ConstraintLayout。与此类似,但仍与Google Chrome浏览器不同。

  • 协调器布局。我认为这是最好的变体。但是它有一些错误。

我写了这样的布局代码:

<?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"
    xmlns:tools="http://schemas.android.com/tools"
    android:id="@+id/main_content"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:fitsSystemWindows="true">

    <android.support.design.widget.AppBarLayout
        android:id="@+id/appBar"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:theme="@style/ThemeOverlay.AppCompat.Dark.ActionBar">


        <android.support.constraint.ConstraintLayout
            android:layout_width="match_parent"
            android:layout_height="?attr/actionBarSize"
            android:background="@android:color/white"
            app:layout_scrollFlags="scroll|enterAlways">

            <View
                android:id="@+id/linkFrame"
                android:layout_width="match_parent"
                android:layout_height="match_parent"
                android:background="@color/colorPrimary"
                app:layout_constraintBottom_toBottomOf="parent"
                app:layout_constraintTop_toTopOf="parent"
                tools:visibility="visible" />

            <HorizontalScrollView
                android:layout_width="0dp"
                android:layout_height="wrap_content"
                android:layout_marginStart="8dp"
                android:layout_marginLeft="8dp"
                android:layout_marginEnd="8dp"
                android:layout_marginRight="8dp"
                android:background="@drawable/frame_link_browser"
                android:padding="8dp"
                app:layout_constraintBottom_toBottomOf="@+id/linkFrame"
                app:layout_constraintEnd_toStartOf="@+id/pauseButton"
                app:layout_constraintStart_toEndOf="@+id/linkDivider"
                app:layout_constraintTop_toTopOf="@+id/linkFrame">

                <TextView
                    android:id="@+id/linkTextView"
                    style="@style/BrowserSmallSecondaryText"
                    android:layout_width="wrap_content"
                    android:layout_height="wrap_content"
                    android:maxLines="1"
                    android:textColor="@color/textPrimary"
                    android:textIsSelectable="true"
                    tools:text="https://vk.com/id118573338"
                    tools:visibility="visible" />
            </HorizontalScrollView>


            <View
                android:id="@+id/linkDivider"
                style="@style/VerticalDivider"
                android:layout_height="24dp"
                android:layout_centerVertical="true"
                android:layout_marginStart="8dp"
                android:layout_marginLeft="8dp"
                android:background="#90FFFFFF"
                android:textColor="@color/textPrimary"
                app:layout_constraintBottom_toBottomOf="@+id/timerTextView"
                app:layout_constraintStart_toEndOf="@+id/timerTextView"
                app:layout_constraintTop_toTopOf="@+id/timerTextView"
                tools:visibility="visible" />

            <TextView
                android:id="@+id/timerTextView"
                style="@style/BrowserMiddlePrimaryText"
                android:layout_width="wrap_content"
                android:layout_height="wrap_content"
                android:layout_centerVertical="true"
                android:layout_marginStart="8dp"
                android:layout_marginLeft="8dp"
                android:gravity="center_vertical"
                app:layout_constraintBottom_toBottomOf="@+id/linkFrame"
                app:layout_constraintStart_toStartOf="@+id/linkFrame"
                app:layout_constraintTop_toTopOf="@+id/linkFrame"
                tools:text="30" />

            <TextView
                android:id="@+id/noInternetTextView"
                style="@style/BrowserBigPrimaryText"
                android:layout_width="wrap_content"
                android:layout_height="wrap_content"
                android:layout_marginStart="16dp"
                android:layout_marginLeft="16dp"
                android:text="@string/no_internet_connection"
                android:visibility="gone"
                app:layout_constraintBottom_toBottomOf="parent"
                app:layout_constraintLeft_toLeftOf="parent"
                app:layout_constraintTop_toTopOf="parent" />

            <TextView
                android:id="@+id/noInternetAdditionalTextView"
                style="@style/BrowserSmallSecondaryText"
                android:layout_width="wrap_content"
                android:layout_height="wrap_content"
                android:text="@string/no_internet_connection_additional"
                android:visibility="gone"
                app:layout_constraintLeft_toLeftOf="@+id/noInternetTextView"
                app:layout_constraintTop_toBottomOf="@+id/noInternetTextView" />

            <ImageButton
                android:id="@+id/pauseButton"
                android:layout_width="44dp"
                android:layout_height="44dp"
                android:background="@color/transparent"
                android:text="@string/pause"
                app:layout_constraintBottom_toBottomOf="@+id/linkFrame"
                app:layout_constraintEnd_toStartOf="@+id/settingsButton"
                app:layout_constraintTop_toTopOf="@+id/linkFrame"
                app:srcCompat="@drawable/ic_pause_circle_filled_white_36dp"
                tools:visibility="visible" />

            <ImageButton
                android:id="@+id/settingsButton"
                android:layout_width="44dp"
                android:layout_height="44dp"
                android:background="@color/transparent"
                android:text="@string/settings"
                app:layout_constraintBottom_toBottomOf="@+id/linkFrame"
                app:layout_constraintEnd_toEndOf="@+id/linkFrame"
                app:layout_constraintTop_toTopOf="@+id/linkFrame"
                app:srcCompat="@drawable/ic_settings_white_36dp"
                tools:visibility="visible" />

        </android.support.constraint.ConstraintLayout>

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


    <android.support.v4.widget.SwipeRefreshLayout
        android:id="@+id/swipeRefresh"
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        app:layout_behavior="@string/appbar_scrolling_view_behavior">


        <android.support.v4.widget.NestedScrollView
            android:layout_width="match_parent"
            android:layout_height="match_parent"
            android:fillViewport="true"
            app:layout_behavior="@string/appbar_scrolling_view_behavior">

            <LinearLayout
                android:layout_width="match_parent"
                android:layout_height="match_parent"
                android:background="@color/white"
                android:orientation="vertical">

                <ProgressBar
                    android:id="@+id/progressBar"
                    style="?android:attr/progressBarStyleHorizontal"
                    android:layout_width="match_parent"
                    android:layout_height="4dp"
                    android:indeterminate="false"
                    android:max="100"
                    android:progress="0"
                    app:layout_constraintEnd_toEndOf="parent"
                    app:layout_constraintStart_toEndOf="parent"
                    app:layout_constraintStart_toStartOf="parent" />

                <com.github.ksoichiro.android.observablescrollview.ObservableWebView xmlns:android="http://schemas.android.com/apk/res/android"
                    android:id="@+id/webView"
                    android:layout_width="match_parent"
                    android:layout_height="match_parent" />

            </LinearLayout>

        </android.support.v4.widget.NestedScrollView>
    </android.support.v4.widget.SwipeRefreshLayout>
</android.support.design.widget.CoordinatorLayout>

在这种情况下,页面无法滚动。我尝试了许多变体。如果在行为上我放置了干净的webview(没有swiperefresh,nestedscrolling等),则可以正常工作,但是如果我锁定并解锁了屏幕-WebView膨胀了,并且在页面底部出现了白色的空白处。 我已经尝试解决这一问题已有好几天了,但是没有用。请帮助为该问题提供稳定的解决方案。非常感谢。

我尝试了以下方法:How to Hide ActionBar/Toolbar While Scrolling Down in Webview,但是如果我锁定和解锁屏幕-WebView会膨胀,并且页面底部会出现空白处

1 个答案:

答案 0 :(得分:1)

我使用此功能创建了WebView,它可以完美运行:

import android.content.Context;
import android.support.v4.view.MotionEventCompat;
import android.support.v4.view.NestedScrollingChild;
import android.support.v4.view.NestedScrollingChildHelper;
import android.support.v4.view.ViewCompat;
import android.util.AttributeSet;
import android.view.MotionEvent;
import android.view.ViewGroup;
import android.webkit.WebView;

import com.github.ksoichiro.android.observablescrollview.ObservableScrollViewCallbacks;
import com.github.ksoichiro.android.observablescrollview.Scrollable;

public class NestedWebView extends WebView implements NestedScrollingChild, Scrollable {
    private int mLastY;
    private final int[] mScrollOffset = new int[2];
    private final int[] mScrollConsumed = new int[2];
    private int mNestedOffsetY;
    private NestedScrollingChildHelper mChildHelper;

    private int mScrollY;
    private ScrollViewCallback callback;
    private boolean firstScroll = true;


    public NestedWebView(Context context) {
        this(context, null);
    }

    public NestedWebView(Context context, AttributeSet attrs) {
        this(context, attrs, android.R.attr.webViewStyle);
    }

    public NestedWebView(Context context, AttributeSet attrs, int defStyleAttr) {
        super(context, attrs, defStyleAttr);
        mChildHelper = new NestedScrollingChildHelper(this);
        setNestedScrollingEnabled(true);
    }

    public void setOnScrollListener(ScrollViewCallback callback) {
        this.callback = callback;
    }

    @Override
    public boolean onTouchEvent(MotionEvent ev) {
        boolean returnValue = false;

        MotionEvent event = MotionEvent.obtain(ev);
        final int action = MotionEventCompat.getActionMasked(event);
        if (action == MotionEvent.ACTION_DOWN) {
            mNestedOffsetY = 0;
        }
        int eventY = (int) event.getY();
        event.offsetLocation(0, mNestedOffsetY);
        switch (action) {
            case MotionEvent.ACTION_MOVE:
                int deltaY = mLastY - eventY;
                // NestedPreScroll
                if (dispatchNestedPreScroll(0, deltaY, mScrollConsumed, mScrollOffset)) {
                    deltaY -= mScrollConsumed[1];
                    mLastY = eventY - mScrollOffset[1];
                    event.offsetLocation(0, -mScrollOffset[1]);
                    mNestedOffsetY += mScrollOffset[1];
                }
                returnValue = super.onTouchEvent(event);

                // NestedScroll
                if (dispatchNestedScroll(0, mScrollOffset[1], 0, deltaY, mScrollOffset)) {
                    event.offsetLocation(0, mScrollOffset[1]);
                    mNestedOffsetY += mScrollOffset[1];
                    mLastY -= mScrollOffset[1];
                }
                break;
            case MotionEvent.ACTION_DOWN:
                returnValue = super.onTouchEvent(event);
                if (firstScroll) {
                    // dispatching first down scrolling properly by making sure that first deltaY will be -ve
                    mLastY = eventY - 5;
                    firstScroll = false;
                } else {
                    mLastY = eventY;
                }
                // start NestedScroll
                startNestedScroll(ViewCompat.SCROLL_AXIS_VERTICAL);
                break;
            default:
                returnValue = super.onTouchEvent(event);
                break;
        }
        return returnValue;
    }

    // Nested Scroll implements
    @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);
    }


    @Override
    protected void onScrollChanged(int l, int t, int oldl, int oldt) {
        super.onScrollChanged(l, t, oldl, oldt);
        mScrollY = t;
        dispatchOnScrollChanged(mScrollY);
    }

    private void dispatchOnScrollChanged(int scrollY) {
        if (callback != null) {
            callback.onScrollChanged(scrollY);
        }
    }

    // Scrollable implements
    @Override
    public void setScrollViewCallbacks(ObservableScrollViewCallbacks listener) {

    }

    @Override
    public void scrollVerticallyTo(int y) {

    }

    @Override
    public int getCurrentScrollY() {
        return mScrollY;
    }

    @Override
    public void setTouchInterceptionViewGroup(ViewGroup viewGroup) {

    }

    public interface ScrollViewCallback {
        void onScrollChanged(int scrollY);
    }


}