仿QQ侧滑菜单(二)

        


        在(一)https://blog.csdn.net/qq_36551426/article/details/80427352中讲了一下DrawerLayout的简单概念,但是这并不足以让我们去做一个完整的QQ侧滑菜单。首先如果只是简单的在侧面菜单里出现一些list还好,可以通过listview配合adapter的方式对菜单初始化。但是如果要完成再乱七八糟点的呢?可能我们需要一些新的View了。

        下面我们来看一下NavigationView导航菜单,NavigationView继承自FrameLayout。一般用于应用的导航菜单,菜单的内容来自于menu文件。NavigationView通常放置在DrawerLayout内部。

        可能在这里我们还不是特别清楚这个View的作用是什么,大家新建工程的时候注意没有,其实空工程下面是有很多其他类型的模板工程的,其中一个就有DrawerLayout的模板。我们打开看看里面结构是什么样的。

            

           

        可以看到大体的文件结构。

           

        具体的效果,左边这个就是NavigationView了。这里分了两个结构,一个是上面的head,下面是一个menu。我们看一下具体的activity_main.XML:

<?xml version="1.0" encoding="utf-8"?>
<android.support.v4.widget.DrawerLayout 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/drawer_layout"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:fitsSystemWindows="true"
    tools:openDrawer="start">

    <include
        layout="@layout/app_bar_main"
        android:layout_width="match_parent"
        android:layout_height="match_parent" />

    <android.support.design.widget.NavigationView
        android:id="@+id/nav_view"
        android:layout_width="wrap_content"
        android:layout_height="match_parent"
        android:layout_gravity="start"
        android:fitsSystemWindows="true"
        app:headerLayout="@layout/nav_header_main"
        app:menu="@menu/activity_main_drawer" />

</android.support.v4.widget.DrawerLayout>

        这里很简单,只有一个app_bar_main和一个NavigationView。外面是一个DrawerLayout。

        再看一下app_bar_main:

<?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:layout_width="match_parent"
    android:layout_height="match_parent"
    tools:context=".MainActivity">

    <android.support.design.widget.AppBarLayout
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:theme="@style/AppTheme.AppBarOverlay">

        <android.support.v7.widget.Toolbar
            android:id="@+id/toolbar"
            android:layout_width="match_parent"
            android:layout_height="?attr/actionBarSize"
            android:background="?attr/colorPrimary"
            app:popupTheme="@style/AppTheme.PopupOverlay" />

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

    <include layout="@layout/content_main" />

    <android.support.design.widget.FloatingActionButton
        android:id="@+id/fab"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_gravity="bottom|end"
        android:layout_margin="@dimen/fab_margin"
        app:srcCompat="@android:drawable/ic_dialog_email" />

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

        一个toolbar,一个content_main,一个FloatingActionButton(悬浮按钮,在这里可以忽略)。

        content_main里面:

<?xml version="1.0" encoding="utf-8"?>
<android.support.constraint.ConstraintLayout 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:layout_width="match_parent"
    android:layout_height="match_parent"
    app:layout_behavior="@string/appbar_scrolling_view_behavior"
    tools:context=".MainActivity"
    tools:showIn="@layout/app_bar_main">

    <TextView
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:text="Hello World!"
        app:layout_constraintBottom_toBottomOf="parent"
        app:layout_constraintLeft_toLeftOf="parent"
        app:layout_constraintRight_toRightOf="parent"
        app:layout_constraintTop_toTopOf="parent" />

</android.support.constraint.ConstraintLayout>

        只有一个TextView。到这里,就可以看清楚整个布局结构了。主界面一个titlebar的xml,下面一个navigationview。然后titlebar里负责主界面的title之类的东西。而navigationview里的上下结构怎么放呢?再来看下面的headerlayout和menu:

            

        headerlayout的效果,这里不贴代码了,看一看结构,一个ImageView,两个TextView,垂直结构:

            

            下面是menu的代码,menu在之前的文章已经讲过了https://blog.csdn.net/qq_36551426/article/details/80398403不了解的同学可以再看一下:

<?xml version="1.0" encoding="utf-8"?>
<menu xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:tools="http://schemas.android.com/tools"
    tools:showIn="navigation_view">

    <group android:checkableBehavior="single">
        <item
            android:id="@+id/nav_camera"
            android:icon="@drawable/ic_menu_camera"
            android:title="Import" />
        <item
            android:id="@+id/nav_gallery"
            android:icon="@drawable/ic_menu_gallery"
            android:title="Gallery" />
        <item
            android:id="@+id/nav_slideshow"
            android:icon="@drawable/ic_menu_slideshow"
            android:title="Slideshow" />
        <item
            android:id="@+id/nav_manage"
            android:icon="@drawable/ic_menu_manage"
            android:title="Tools" />
    </group>

    <item android:title="Communicate">
        <menu>
            <item
                android:id="@+id/nav_share"
                android:icon="@drawable/ic_menu_share"
                android:title="Share" />
            <item
                android:id="@+id/nav_send"
                android:icon="@drawable/ic_menu_send"
                android:title="Send" />
        </menu>
    </item>

</menu>

        说白了就是一堆menu,内嵌一堆item。item设置了属性,id、icon、title。


        OK,总结一下,要做这个效果就是在DrawerLayout里面加NavigationView,然后NavigationView里放两个布局,一个head,一个menu。这样侧滑菜单栏就出现了,而主菜单又是另外一个部分,我们目前大可以不管。


//---------------------------------------下面我们创建空工程来做自己的侧滑效果-----------------------------------------

        首先分析一下,一个侧滑菜单,用到DrawerLayout,然后上面有我们自己DIY的title,下面先放空白,侧滑菜单放在NavigationView里。NavigationView很自然的帮我们分为了上下(head,menu)两个部分,上面用来放我们QQ头像,签名等信息。下面是QQ的一些菜单选项如QQ会员,相册。

        OK,在activity_main.xml里放好NavigationView:

<?xml version="1.0" encoding="utf-8"?>
<android.support.v4.widget.DrawerLayout 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:layout_width="match_parent"
    android:layout_height="match_parent"
    android:id="@+id/my_drawer_layout"
    tools:context=".MainActivity">

    <android.support.design.widget.NavigationView
        android:id="@+id/Nav_view"
        app:menu="@menu/nav_menu"
        android:layout_gravity="left"
        android:fitsSystemWindows="true"
        app:headerLayout="@layout/nav_head"
        android:layout_width="340dp"
        android:layout_height="match_parent"/>

</android.support.v4.widget.DrawerLayout>

        接下来,我们在res文件夹内建一个menu文件夹,再建一个nav_menu.xml在里面,装上item:

        

<?xml version="1.0" encoding="utf-8"?>
<menu xmlns:android="http://schemas.android.com/apk/res/android">

    <item
        android:id="@+id/nav_menu_vip"
        android:icon="@drawable/ic_menu_camera"
        android:title="我的QQ会员"
        />
    <item
        android:id="@+id/nav_menu_wallet"
        android:icon="@drawable/ic_menu_camera"
        android:title="QQ钱包"
        />
    <item
        android:id="@+id/nav_menu_zhuangban"
        android:icon="@drawable/ic_menu_camera"
        android:title="个性装扮"
        />
    <item
        android:id="@+id/nav_menu_shouchang"
        android:icon="@drawable/ic_menu_camera"
        android:title="我的收藏"
        />
    <item
        android:id="@+id/nav_menu_album"
        android:icon="@drawable/ic_menu_camera"
        android:title="我的相册"
        />
    <item
        android:id="@+id/nav_menu_file"
        android:icon="@drawable/ic_menu_camera"
        android:title="我的文件"
        />
    <item
        android:id="@+id/nav_menu_liuliang"
        android:icon="@drawable/ic_menu_camera"
        android:title="免流量特权"
        />
</menu>

        看到这个图,别慌!

            

        然后是headlayout,在layout里建一个nav_head.xml:

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout
    xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:id="@+id/nav_head_view"
    android:background="@drawable/side_nav_bar"
    android:orientation="vertical"
    android:layout_height="180dp">

    <ImageView
        android:id="@+id/head_im"
        android:layout_width="90dp"
        android:layout_height="90dp"
        android:layout_marginLeft="12dp"
        android:layout_marginTop="36dp"
        android:src="@drawable/head" />

    <TextView
        android:text="刘敏敏我爱你刘敏敏我爱你刘敏敏我爱你"
        android:textSize="18sp"
        android:layout_marginLeft="12dp"
        android:layout_marginTop="5dp"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content" />

</LinearLayout>

        ImageView跟TextView随便放,按自己的效果来。别忘了LinearLayout放背景图。

            

        在这里已经可以有一个侧滑菜单栏的效果了,不过我们还可以再进一步,自定义一个Title,里面放一个Button跟一个TextView。Button响应侧滑菜单。这算是模拟QQ主界面点击头像打开侧滑菜单的效果。

        title的代码跟模板的一模一样:

<?xml version="1.0" encoding="utf-8"?>
<android.support.constraint.ConstraintLayout
    xmlns:android="http://schemas.android.com/apk/res/android" android:layout_width="match_parent"
    android:layout_height="match_parent">

    <android.support.design.widget.AppBarLayout
        android:theme="@style/AppTheme"
        android:layout_width="match_parent"
        android:layout_height="wrap_content">

        <android.support.v7.widget.Toolbar
            android:id="@+id/toolbar"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content">

            <Button
                android:id="@+id/toolbar_btn"
                android:background="@drawable/ic_menu_manage"
                android:layout_width="50dp"
                android:layout_height="50dp" />

            <TextView
                android:textSize="24sp"
                android:layout_marginLeft="60dp"
                android:text="@string/app_name"
                android:layout_width="wrap_content"
                android:layout_height="wrap_content" />

        </android.support.v7.widget.Toolbar>

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

        然后把title放进main.xml里就可以了。

            

        OK,在这里也差不多了,接下来是通过代码响应一下事件。1、点击button打开关闭侧滑菜单栏。2、点击menu内的item响应事件,并关闭菜单。

        我们继承Navigation.OnNavigationItemSelectedListener,和View.OnClickListener。顾名思义,就是响应item点击事件和button点击事件。

package comr.example.administrator.mydrawertest3;

import android.app.Activity;
import android.support.annotation.NonNull;
import android.support.design.widget.NavigationView;
import android.support.v4.widget.DrawerLayout;
import android.support.v7.app.AppCompatActivity;
import android.os.Bundle;
import android.view.Gravity;
import android.view.MenuItem;
import android.view.View;
import android.view.Window;
import android.widget.Button;
import android.widget.Toast;

public class MainActivity extends Activity implements NavigationView.OnNavigationItemSelectedListener, View.OnClickListener {

    private Button button;
    private NavigationView navigationView;
    private DrawerLayout drawerLayout;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);

        drawerLayout = (DrawerLayout)findViewById(R.id.my_drawer_layout);

        button = (Button)findViewById(R.id.toolbar_btn);
        button.setOnClickListener(this);

        navigationView = (NavigationView) findViewById(R.id.Nav_view);
        navigationView.setNavigationItemSelectedListener(this);
    }

    /**
     * navigationview里的item监听
     * @param item
     * @return
     */
    @Override
    public boolean onNavigationItemSelected(@NonNull MenuItem item) {
        DrawerLayout drawer = (DrawerLayout) findViewById(R.id.my_drawer_layout);//新变量

        //对于这类点击响应事件,都是对参数getId,因为在底层这些Id都是一串数值,通过数值比较来确定目标
        switch (item.getItemId()){
            //每点击一次菜单中的itemshowtoast一次然后将drawerlayout关闭
            case R.id.nav_menu_album:
                showToast("相册");
                drawer.closeDrawer(Gravity.LEFT);
                break;
            case R.id.nav_menu_file:
                showToast("文件");
                drawer.closeDrawer(Gravity.LEFT);
                break;
            case R.id.nav_menu_liuliang:
                showToast("流量");
                drawer.closeDrawer(Gravity.LEFT);
                break;
            case R.id.nav_menu_shouchang:
                showToast("收藏");
                drawer.closeDrawer(Gravity.LEFT);
                break;
            case R.id.nav_menu_vip:
                showToast("VIP");
                drawer.closeDrawer(Gravity.LEFT);
                break;
            case R.id.nav_menu_wallet:
                showToast("钱包");
                drawer.closeDrawer(Gravity.LEFT);
                break;
            case R.id.nav_menu_zhuangban:
                showToast("装扮");
                drawer.closeDrawer(Gravity.LEFT);
                break;
                default:
                    break;
        }

        return true;
    }

    private void showToast(String s) {
        Toast.makeText(this,s,Toast.LENGTH_SHORT).show();
    }

    /**
     * implement clickListener接口,对事件做点击监听,其实也可以对navigationview里的item做监听
     * 但是可以通过implement NavigationViewOnNavigationItemSelectedListeneritem做监听,所以可以分离开
     * @param v
     */
    @Override
    public void onClick(View v) {
        switch (v.getId()){
            case R.id.toolbar_btn:
                if(drawerLayout.isDrawerOpen(Gravity.LEFT)){ //判断一下是否已经开启了,开了关,关了开
                    drawerLayout.closeDrawer(Gravity.LEFT);
                }else drawerLayout.openDrawer(Gravity.LEFT);
                break;
                default:
                    break;
        }
    }
}

        不需要多解释,代码里有一些注解,就算不看注解也是很好理解的。

        OK,最后给大家上一张效果图:


贴一下其他博客的链接,大家可以参考一下:

https://blog.csdn.net/u012702547/article/details/51253222   Android5.0之NavigationView的使用

http://www.jcodecraeer.com/a/anzhuokaifa/androidkaifa/2015/0608/3011.html

Design Support Library (I): Navigation View的使用

https://lvwenhan.com/ios/445.html 再造 “手机QQ” 侧滑菜单(一)——实现侧滑效果(这个是IOS,不过有更好看的效果,想研究的同学可以稍微看看)

https://blog.csdn.net/lmj623565791/article/details/39257409 Android 高仿 QQ5.0 侧滑菜单效果 自定义控件来袭(android版)



Android5.0之NavigationView的使用
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值