【问题标题】:How to use Navigation Drawer without duplicate code?如何在没有重复代码的情况下使用导航抽屉?
【发布时间】:2016-02-29 19:29:12
【问题描述】:

我按照教程创建了一个导航抽屉,但现在我遇到了问题。如何在不复制代码的情况下在多个活动中使用它? 我尝试扩展主要活动,但我发现工具栏存在一些问题。还有别的办法吗? 谢谢,这是我的代码。

MainActivity.java

import android.content.Context;
import android.content.Intent;
import android.os.Bundle;
import android.support.v4.widget.DrawerLayout;
import android.support.v7.app.ActionBarDrawerToggle;
import android.support.v7.app.AppCompatActivity;
import android.support.v7.widget.Toolbar;
import android.util.Log;
import android.view.LayoutInflater;
import android.view.Menu;
import android.view.MenuItem;
import android.view.View;
import android.view.ViewGroup;
import android.widget.AdapterView;
import android.widget.BaseAdapter;
import android.widget.ImageView;
import android.widget.ListView;
import android.widget.RelativeLayout;
import android.widget.TextView;

public class MainActivity extends AppCompatActivity {
    class NavItem {
        String mTitle;
        int mIcon;

        public NavItem(String title, int icon) {
            mTitle = title;
            mIcon = icon;
        }
    }

    class DrawerListAdapter extends BaseAdapter {

        Context mContext;
        ArrayList<NavItem> mNavItems;

        public DrawerListAdapter(Context context, ArrayList<NavItem> navItems) {
            mContext = context;
            mNavItems = navItems;
        }

        public int getCount() {
            return mNavItems.size();
        }

        public Object getItem(int position) {
            return mNavItems.get(position);
        }

        public long getItemId(int position) {
            return 0;
        }

        public View getView(int position, View convertView, ViewGroup parent) {
            View view;

            if (convertView == null) {
                LayoutInflater inflater = (LayoutInflater) mContext.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
                view = inflater.inflate(R.layout.drawer_item, parent, false);
            }
            else {
                view = convertView;
            }

            TextView titleView = (TextView) view.findViewById(R.id.title);
            ImageView iconView = (ImageView) view.findViewById(R.id.icon);

            titleView.setText( mNavItems.get(position).mTitle );
            iconView.setImageResource(mNavItems.get(position).mIcon);

            return view;
        }
    }

    ListView mDrawerList;
    RelativeLayout mDrawerPane;

    private static String TAG = MainActivity.class.getSimpleName();

    private ActionBarDrawerToggle mDrawerToggle;
    private DrawerLayout mDrawerLayout;

    ArrayList<NavItem> mNavItems = new ArrayList<>();

    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
        Toolbar toolbar = (Toolbar) findViewById(R.id.toolbar);
        setSupportActionBar(toolbar);
        assert getSupportActionBar() != null;
        getSupportActionBar().setDisplayHomeAsUpEnabled(true);

        mNavItems.add(new NavItem(getString(R.string.home), R.drawable.ic_action_home));
        mNavItems.add(new NavItem(getString(R.string.company), R.drawable.ic_action_company));
        mNavItems.add(new NavItem(getString(R.string.services), R.drawable.ic_action_services));
        mNavItems.add(new NavItem(getString(R.string.solutions), R.drawable.ic_action_solutions));
        mNavItems.add(new NavItem(getString(R.string.case_history), R.drawable.ic_action_case_history));
        mNavItems.add(new NavItem(getString(R.string.contacts), R.drawable.ic_action_contacts));

        mDrawerLayout = (DrawerLayout) findViewById(R.id.drawerLayout);
        mDrawerPane = (RelativeLayout) findViewById(R.id.drawerPane);
        mDrawerList = (ListView) findViewById(R.id.navList);
        DrawerListAdapter adapter = new DrawerListAdapter(this, mNavItems);
        mDrawerList.setAdapter(adapter);

        mDrawerList.setOnItemClickListener(new AdapterView.OnItemClickListener() {
            public void onItemClick(AdapterView<?> parent, View view, int position, long id) {
                mDrawerLayout.closeDrawer(mDrawerPane);

                if (position == 0) {
                    Intent intent = new Intent(getApplicationContext(), MainActivity.class);
                    startActivity(intent);
                } else if (position == 1) {
                    Intent intent = new Intent(getApplicationContext(), CompanyActivity.class);
                    startActivity(intent);
                }
            }
        });

        mDrawerToggle = new ActionBarDrawerToggle(this, mDrawerLayout, R.string.drawer_open, R.string.drawer_close) {
            public void onDrawerOpened(View drawerView) {
                super.onDrawerOpened(drawerView);

                invalidateOptionsMenu();
            }

            public void onDrawerClosed(View drawerView) {
                super.onDrawerClosed(drawerView);
                Log.d(TAG, "onDrawerClosed: " + getTitle());

                invalidateOptionsMenu();
            }
        };

        mDrawerLayout.setDrawerListener(mDrawerToggle);
    }

    public boolean onCreateOptionsMenu(Menu menu) {
        getMenuInflater().inflate(R.menu.menu_main, menu);
        return true;
    }

    public boolean onOptionsItemSelected(MenuItem item) {
        return mDrawerToggle.onOptionsItemSelected(item);
    }

    protected void onPostCreate(Bundle savedInstanceState) {
        super.onPostCreate(savedInstanceState);
        mDrawerToggle.syncState();
    }
}

activity_main.xml:

<?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:fitsSystemWindows="true" >

    <RelativeLayout
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        android:paddingBottom="@dimen/activity_vertical_margin"
        android:paddingLeft="@dimen/activity_horizontal_margin"
        android:paddingRight="@dimen/activity_horizontal_margin"
        android:paddingTop="@dimen/activity_vertical_margin"
        app:layout_behavior="@string/appbar_scrolling_view_behavior" >

        <ImageView
            android:contentDescription="@string/app_name"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:src="@drawable/logo" />
    </RelativeLayout>

    <include layout="@layout/side_menu" />
    <include layout="@layout/toolbar" />
</android.support.design.widget.CoordinatorLayout>

side_menu.xml:

<?xml version="1.0" encoding="utf-8"?>
<android.support.v4.widget.DrawerLayout
    xmlns:android="http://schemas.android.com/apk/res/android"
    android:id="@+id/drawerLayout"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:layout_marginTop="?attr/actionBarSize" >

    <RelativeLayout
        android:id="@+id/mainContent"
        android:layout_width="match_parent"
        android:layout_height="match_parent" />

    <RelativeLayout
    android:layout_width="280dp"
    android:layout_height="match_parent"
    android:id="@+id/drawerPane"
    android:layout_gravity="start">

        <ListView
            android:id="@+id/navList"
            android:layout_width="280dp"
            android:layout_height="match_parent"
            android:choiceMode="singleChoice"
            android:background="#FFF" />
    </RelativeLayout>
</android.support.v4.widget.DrawerLayout>

工具栏.xml:

<android.support.design.widget.AppBarLayout 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="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:minHeight="?attr/actionBarSize"
        android:background="?attr/colorPrimary"
        app:popupTheme="@style/AppTheme.PopupOverlay" />
</android.support.design.widget.AppBarLayout>

【问题讨论】:

  • 继承是您的解决方案。您应该为您的抽屉布局和工具栏提供相同的 id。覆盖 setContentView 并初始化您的工具栏和抽屉布局。可能,您想让它们受到保护,以便从子类访问。有关更多信息,您可能需要查看此链接:github.com/google/iosched
  • 当我看到:MainActivity.js

标签: java android android-layout android-studio navigation-drawer


【解决方案1】:

在您的抽屉内创建​​一个基本活动,然后将基本活动扩展到您想要抽屉的所有活动。 而不是在 oncreate 继承活动中调用 setcontentview() 使用布局充气器

查看这篇文章

How to Display Navigation Drawer in all activities?

【讨论】:

    【解决方案2】:

    这是我项目中真实代码的一部分。 @Bind 来自很棒的 Butterknife 库。 AbstractToolbarActivityAppCompatActivity 的子类,遵循相同的逻辑(避免重复初始化工具栏的代码)

    public abstract class AbstractDrawerActivity extends AbstractToolbarActivity {
    
      @Bind(R.id.drawer_layout) DrawerLayout mDrawerLayout;
    
      ActionBarDrawerToggle mDrawerToggle;
    
      protected void initDrawer() {
    
        mDrawerToggle = new ActionBarDrawerToggle(this, mDrawerLayout, mToolbar, R.string.drawer_open,
            R.string.drawer_close);
        mDrawerToggle.setDrawerIndicatorEnabled(true);
        mDrawerLayout.setDrawerListener(mDrawerToggle);
    
        if (getSupportActionBar() != null) {
          getSupportActionBar().setDisplayHomeAsUpEnabled(true);
          getSupportActionBar().setHomeButtonEnabled(true);
        }
      }
    
      @Override protected void onPostCreate(Bundle savedInstanceState) {
        super.onPostCreate(savedInstanceState);
        initDrawer();
        mDrawerToggle.syncState();
      }
    
      @OnClick(R.id.drawer_user_name) protected void openProfile() {
        final Intent profile = new Intent(this, ProfileActivity.class);
        startActivity(profile);
      }
    
      // here some onclicks etc, other methods
    
      @Override protected void onNewIntent(Intent intent) {
        super.onNewIntent(intent);
    
        if (mDrawerLayout.isDrawerOpen(GravityCompat.START)) {
          mDrawerLayout.closeDrawers();
        }
      }
    
      @Override public void onBackPressed() {
        if (mDrawerLayout.isDrawerOpen(GravityCompat.START)) {
          mDrawerLayout.closeDrawers();
        } else {
          super.onBackPressed();
        }
      }
    
      @Override protected void onPause() {
        super.onPause();
    
        if (mDrawerLayout.isDrawerOpen(GravityCompat.START)) {
          mDrawerLayout.closeDrawers();
        }
      }
    }
    

    还有AbstractToolbarActivity.java:

    public abstract class AbstractToolbarActivity extends AppCompatActivity {
    
      @Bind(R.id.action_bar) Toolbar mToolbar;
    
      @Override protected void onPostCreate(Bundle savedInstanceState) {
        super.onPostCreate(savedInstanceState);
        initToolbar();
      }
    
      protected void initToolbar() {
        setSupportActionBar(mToolbar);
      }
    }
    

    【讨论】:

    • 什么是AbstractToolbarActivity
    • 它是 AppCompatActivity 的子类,包含一个工具栏。相同的逻辑,避免重复初始化工具栏的代码
    猜你喜欢
    • 2013-05-18
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2018-10-12
    • 1970-01-01
    • 2018-07-09
    • 2014-03-29
    相关资源
    最近更新 更多