How can I implement a chrome like “auto-hide navigation” for my Android app?

后端 未结 4 1668
误落风尘
误落风尘 2021-02-04 20:12

In Chrome, the address bar will be hidden/shown when user swipes up/down the content.

Can I implement the similar logic to my app?



        
相关标签:
4条回答
  • 2021-02-04 20:22

    There is now a really clean way to accomplish this without writing any Java code using the Design Support Library. See Dhir Pratap's answer below:

    (I would have placed this as a comment but I don't have enough rep.)

    How to Hide ActionBar/Toolbar While Scrolling Down in Webview

    <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/appbar"
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            android:theme="@style/ThemeOverlay.AppCompat.Dark.ActionBar">
    
            <android.support.v7.widget.Toolbar
                android:id="@+id/toolbar"
                android:layout_width="match_parent"
                android:layout_height="?attr/actionBarSize"
                android:background="?attr/colorPrimary"
                app:layout_scrollFlags="scroll|enterAlways"
                app:popupTheme="@style/ThemeOverlay.AppCompat.Light" />
        </android.support.design.widget.AppBarLayout>
    
        <android.support.v4.widget.NestedScrollView 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:layout_gravity="fill_vertical"
            app:layout_behavior="@string/appbar_scrolling_view_behavior">
    
            <WebView
                android:id="@+id/webview"
                android:layout_width="match_parent"
                android:layout_height="match_parent"/>
        </android.support.v4.widget.NestedScrollView>
    </android.support.design.widget.CoordinatorLayout>
    
    0 讨论(0)
  • 2021-02-04 20:25

    First you need layout with alignParentBottom and match_parent WebView and some bar at top:

    <?xml version="1.0" encoding="utf-8"?>
    <RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:background="#ffff" >
    
    <WebView
        android:id="@+id/webView"
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        android:layout_alignParentBottom="true" />
    
    <RelativeLayout
        android:id="@+id/actionBar"
        android:layout_width="match_parent"
        android:layout_height="50dp" >
    
        <TextView
            android:id="@+id/tvTitle"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:layout_centerInParent="true"
            android:text="TextView" />
    
    </RelativeLayout>
    
    </RelativeLayout>
    

    Then you need code:

    1) Declare and set some internal values and resize WebView to make it below our bar:

    private int baseHeight;
    private int webViewOnTouchHeight;
    private int barHeight;
    private float heightChange;
    private float startEventY;
    
    barHeight = actionBar.getMeasuredHeight();
    baseHeight = getView().getMeasuredHeight();
    webView.getLayoutParams().height = webView.getMeasuredHeight() - barHeight;
    webView.requestLayout();
    webView.setOnTouchListener(listener);
    

    2) Create resize method. Here we check new height with limits of screen top and bar height

    private boolean resizeView(float delta) {
        heightChange = delta;
        int newHeight = (int)(webViewOnTouchHeight - delta);
        if (newHeight > baseHeight){ // scroll over top
            if (webView.getLayoutParams().height < baseHeight){
                webView.getLayoutParams().height = baseHeight;
                webView.requestLayout();
                return true;
            }       
        }else if (newHeight < baseHeight - barHeight){ // scroll below bar
            if (webView.getLayoutParams().height > baseHeight - barHeight){
                webView.getLayoutParams().height = baseHeight - barHeight;
                webView.requestLayout();
                return true;
            }
        } else { // scroll between top and bar
            webView.getLayoutParams().height = (int)(webViewOnTouchHeight - delta);
            webView.requestLayout();
            return true;
        }
        return false;
    }
    

    3) Create custom onTouch listener where we will resize WebView and change Y-value of our bar

    private OnTouchListener listener = new OnTouchListener() {
        @Override
        public boolean onTouch(View v, MotionEvent event) {
            switch (event.getAction() & MotionEvent.ACTION_MASK) {
            case MotionEvent.ACTION_DOWN:
                startEventY = event.getY();
                heightChange = 0;
                webViewOnTouchHeight = webView.getLayoutParams().height;
                break;
            case MotionEvent.ACTION_MOVE:
                float delta = (event.getY()+heightChange)-startEventY;
                boolean heigthChanged = resizeView(delta);
                if (heigthChanged){
                    actionBar.setTranslationY(baseHeight - webView.getLayoutParams().height - barHeight);
                }
            }
            return false;
        }
    };
    
    0 讨论(0)
  • 2021-02-04 20:34

    This pattern is called Quick Return. Start with this blog post.

    However, it is worthwhile reading this when considering its use.

    0 讨论(0)
  • 2021-02-04 20:42

    try the following code, hope it works for you:

        private void init(){
        WebView web = new WebView(this);
        final Context context = this;
        web.setOnTouchListener(new OnTouchListener() {
    
            public boolean onTouch(View arg0, MotionEvent event) {
                // TODO Auto-generated method stub
                switch (event.getAction()) {
                case MotionEvent.ACTION_DOWN:
                    // show action bar
                    ((Activity) context).getActionBar().show();
                    break;
    
                case MotionEvent.ACTION_UP:
                    // hide action bar
                    ((Activity) context).getActionBar().hide();
                    break;
    
                default:
                    break;
                }
                return false;
            }
        });
    }
    
    0 讨论(0)
提交回复
热议问题