I want to hide and unhide a MenuItem ((R.id.bored)) using Firebase remote config. But it is showing NullPointerException. Please help! and is there any alternative way I could remote hide and unhide that menu item (R.id.bored)?
Here is HomeActivity.java
public class HomeActivity
extends Activity
implements NavigationView.OnNavigationItemSelectedListener, PowerfulActionModeSupport {
public static final int REQUEST_PERMISSION_ALL = 1;
private NavigationView mNavigationView;
private DrawerLayout mDrawerLayout;
private PowerfulActionMode mActionMode;
private HomeFragment mHomeFragment;
private MenuItem mTrustZoneToggle;
private IntentFilter mFilter = new IntentFilter();
private BroadcastReceiver mReceiver = null;
private long mExitPressTime;
private int mChosenMenuItemId;
private RewardedVideoAd mRewardedVideoAd;
private InterstitialAd mInterstitialAd;
private FirebaseRemoteConfig mFirebaseRemoteConfig;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
mFirebaseRemoteConfig = FirebaseRemoteConfig.getInstance();
FirebaseRemoteConfigSettings configSettings = new FirebaseRemoteConfigSettings.Builder()
.setMinimumFetchIntervalInSeconds(3600)
.build();
mFirebaseRemoteConfig.setConfigSettingsAsync(configSettings);
mFirebaseRemoteConfig.setDefaultsAsync(R.xml.remote);
final Toolbar toolbar = findViewById(R.id.toolbar);
setSupportActionBar(toolbar);
mHomeFragment = (HomeFragment) getSupportFragmentManager().findFragmentById(R.id.activitiy_home_fragment);
mActionMode = findViewById(R.id.content_powerful_action_mode);
mNavigationView = findViewById(R.id.nav_view);
mDrawerLayout = findViewById(R.id.drawer_layout);
mTrustZoneToggle = mNavigationView.getMenu().findItem(R.id.menu_activity_trustzone);
ActionBarDrawerToggle toggle = new ActionBarDrawerToggle(this, mDrawerLayout, toolbar, R.string.text_navigationDrawerOpen, R.string.text_navigationDrawerClose);
mDrawerLayout.addDrawerListener(toggle);
toggle.syncState();
mFilter.addAction(CommunicationService.ACTION_TRUSTZONE_STATUS);
mDrawerLayout.addDrawerListener(new DrawerLayout.SimpleDrawerListener() {
#Override
public void onDrawerClosed(View drawerView) {
applyAwaitingDrawerAction();
}
});
mNavigationView.setNavigationItemSelectedListener(this);
mActionMode.setOnSelectionTaskListener(new PowerfulActionMode.OnSelectionTaskListener() {
#Override
public void onSelectionTask(boolean started, PowerfulActionMode actionMode) {
toolbar.setVisibility(!started ? View.VISIBLE : View.GONE);
}
});
mFirebaseRemoteConfig.fetchAndActivate()
.addOnCompleteListener(this, new OnCompleteListener<Boolean>() {
#Override
public void onComplete(#NonNull Task<Boolean> task) {
if (task.isSuccessful()) {
mFirebaseRemoteConfig.activate();
boolean updated = task.getResult();
View headerView = mNavigationView.getHeaderView(0);
MenuItem boredItem = mNavigationView.getMenu().findItem(R.id.bored);
Configuration configuration = getApplication().getResources().getConfiguration();
boredItem.setVisible(mFirebaseRemoteConfig.getBoolean("remote_bored"));
Toast.makeText(HomeActivity.this, "Fetch and activate succeeded",
Toast.LENGTH_SHORT).show();
} else {
Toast.makeText(HomeActivity.this, "Fetch failed",
Toast.LENGTH_SHORT).show();
}
}
});
}
Here is remote.xml
<?xml version="1.0" encoding="utf-8"?>
<!-- START xml_defaults -->
<defaultsMap>
<entry>
<key>remote_bored</key>
<value>false</value>
</entry>
</defaultsMap>
<!-- END xml_defaults -->
Here is drawer_main.xml
<menu 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">
<item
android:id="#+id/bored_button"
android:orderInCategory="19"
android:title="#string/bored"
android:icon="#drawable/ic_bored"
android:actionLayout="#layout/layout_main_navigationview_footer"/>
</group>
activity_main.xml
<?xml version="1.0" encoding="utf-8"?>
<androidx.drawerlayout.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/toolbar_main"
android:layout_width="match_parent"
android:layout_height="match_parent" />
<com.google.android.material.navigation.NavigationView
android:id="#+id/nav_view"
style="?navigationViewStyle"
android:layout_width="wrap_content"
android:layout_height="match_parent"
android:layout_gravity="start"
app:headerLayout="#layout/header_default_device"
app:menu="#menu/drawer_main" />
</androidx.drawerlayout.widget.DrawerLayout>
Logcat:
2020-07-25 21:47:07.228 20224-20224/go.dodo.GETit E/AndroidRuntime: FATAL EXCEPTION: main
Process: go.dodo.GETit, PID: 20224
java.lang.NullPointerException: Attempt to invoke interface method 'android.view.MenuItem android.view.MenuItem.setVisible(boolean)' on a null object reference
at go.dodo.GETit.activity.HomeActivity$3.onComplete(HomeActivity.java:203)
at com.google.android.gms.tasks.zzi.run(com.google.android.gms:play-services-tasks##17.0.2:4)
at android.os.Handler.handleCallback(Handler.java:883)
at android.os.Handler.dispatchMessage(Handler.java:100)
at com.google.android.gms.internal.tasks.zzb.dispatchMessage(com.google.android.gms:play-services-tasks##17.0.2:6)
at android.os.Looper.loop(Looper.java:214)
at android.app.ActivityThread.main(ActivityThread.java:7356)
at java.lang.reflect.Method.invoke(Native Method)
at com.android.internal.os.RuntimeInit$MethodAndArgsCaller.run(RuntimeInit.java:492)
at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:930)
This code is returning null:
MenuItem boredItem = mNavigationView.getMenu().findItem(R.id.bored);
This means that your inflated menu XML doesn't have an item called "bored". Perhaps you meant bored_button?
Related
This question already has answers here:
What is a NullPointerException, and how do I fix it?
(12 answers)
Closed 3 years ago.
I am developing new android app using navigation drawer and extending
baseactivity and following this link
Same Navigation Drawer in different Activities
but I am getting following exception
Process: edgar.yodgorbek.sportnews, PID: 7608
java.lang.RuntimeException: Unable to start activity ComponentInfo{edgar.yodgorbek.sportnews/edgar.yodgorbek.sportnews.MainActivity}: java.lang.NullPointerException: Attempt to invoke virtual method 'void android.support.v4.widget.DrawerLayout.setDrawerListener(android.support.v4.widget.DrawerLayout$DrawerListener)' on a null object reference
at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:3102)
at android.app.ActivityThread.handleLaunchActivity(ActivityThread.java:3237)
at android.app.servertransaction.LaunchActivityItem.execute(LaunchActivityItem.java:81)
at android.app.servertransaction.TransactionExecutor.executeCallbacks(TransactionExecutor.java:135)
at android.app.servertransaction.TransactionExecutor.execute(TransactionExecutor.java:95)
at android.app.ActivityThread$H.handleMessage(ActivityThread.java:1929)
at android.os.Handler.dispatchMessage(Handler.java:106)
at android.os.Looper.loop(Looper.java:209)
at android.app.ActivityThread.main(ActivityThread.java:7021)
at java.lang.reflect.Method.invoke(Native Method)
at com.android.internal.os.RuntimeInit$MethodAndArgsCaller.run(RuntimeInit.java:486)
at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:872)
Caused by: java.lang.NullPointerException: Attempt to invoke virtual method 'void android.support.v4.widget.DrawerLayout.setDrawerListener(android.support.v4.widget.DrawerLayout$DrawerListener)' on a null object reference
at edgar.yodgorbek.sportnews.BaseActivity.onCreate(BaseActivity.java:44)
at edgar.yodgorbek.sportnews.MainActivity.onCreate(MainActivity.java:36)
at android.app.Activity.performCreate(Activity.java:7650)
at android.app.Activity.performCreate(Activity.java:7639)
at android.app.Instrumentation.callActivityOnCreate(Instrumentation.java:1295)
at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:3077)
at android.app.ActivityThread.handleLaunchActivity(ActivityThread.java:3237)
at android.app.servertransaction.LaunchActivityItem.execute(LaunchActivityItem.java:81)
at android.app.servertransaction.TransactionExecutor.executeCallbacks(TransactionExecutor.java:135)
at android.app.servertransaction.TransactionExecutor.execute(TransactionExecutor.java:95)
at android.app.ActivityThread$H.handleMessage(ActivityThread.java:1929)
at android.os.Handler.dispatchMessage(Handler.java:106)
at android.os.Looper.loop(Looper.java:209)
at android.app.ActivityThread.main(ActivityThread.java:7021)
at java.lang.reflect.Method.invoke(Native Method)
at com.android.internal.os.RuntimeInit$MethodAndArgsCaller.run(RuntimeInit.java:486)
at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:872)
below my BaseActivity class
public class BaseActivity extends Activity {
public DrawerLayout drawerLayout;
public ListView drawerList;
public String[] layers;
Toolbar toolbar;
private ActionBarDrawerToggle drawerToggle;
private Map map;
protected void onCreate(Bundle savedInstanceState) {
// R.id.drawer_layout should be in every activity with exactly the same id.
super.onCreate(savedInstanceState);
drawerLayout = (DrawerLayout) findViewById(R.id.drawer_layout);
drawerToggle = new ActionBarDrawerToggle( this, drawerLayout,toolbar,0, 0) {
public void onDrawerClosed(View view) {
getActionBar().setTitle(R.string.app_name);
}
public void onDrawerOpened(View drawerView) {
getActionBar().setTitle(R.string.app_name);
}
};
drawerLayout.setDrawerListener(drawerToggle);
getActionBar().setDisplayHomeAsUpEnabled(true);
getActionBar().setHomeButtonEnabled(true);
// layers = getResources().getStringArray(R.array.layers_array);
drawerList = (ListView) findViewById(R.id.left_drawer);
View header = getLayoutInflater().inflate(R.layout.base_activity, null);
drawerList.addHeaderView(header, null, false);
drawerList.setAdapter(new ArrayAdapter<String>(this, R.layout.base_activity, android.R.id.text1,
layers));
View footerView = ((LayoutInflater) this.getSystemService(Context.LAYOUT_INFLATER_SERVICE)).inflate(
R.layout.base_activity, null, false);
drawerList.addFooterView(footerView);
drawerList.setOnItemClickListener(new AdapterView.OnItemClickListener() {
#Override
public void onItemClick(AdapterView<?> arg0, View arg1, int pos, long arg3) {
// map.drawerClickEvent(pos);
}
});
}
#Override
public boolean onOptionsItemSelected(MenuItem item) {
if (drawerToggle.onOptionsItemSelected(item)) {
return true;
}
return super.onOptionsItemSelected(item);
}
#Override
protected void onPostCreate(Bundle savedInstanceState) {
super.onPostCreate(savedInstanceState);
drawerToggle.syncState();
}
#Override
public void onConfigurationChanged(Configuration newConfig) {
super.onConfigurationChanged(newConfig);
drawerToggle.onConfigurationChanged(newConfig);
}
}
below base_activity.xml
android.support.v4.widget.DrawerLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:id="#+id/drawer_layout"
android:layout_width="match_parent"
android:layout_height="match_parent">
<!-- The main content view -->
<FrameLayout
android:id="#+id/content_frame"
android:layout_width="match_parent"
android:layout_height="match_parent">
<!-- Put what you want as your normal screen in here, you can also choose for a linear layout or any other layout, whatever you prefer -->
</FrameLayout>
<!-- The navigation drawer -->
<ListView
android:id="#+id/left_drawer"
android:layout_width="240dp"
android:layout_height="match_parent"
android:layout_gravity="start"
android:background="#111"
android:choiceMode="singleChoice"
android:divider="#android:color/transparent"
android:dividerHeight="0dp" />
</android.support.v4.widget.DrawerLayout>
below my MainActivity
public class MainActivity extends BaseActivity {
public List<Article> articleList = new ArrayList<Article>();
#BindView(R.id.recyclerView)
RecyclerView recyclerView;
private SportNews sportNews;
private ArticleAdapter articleAdapter;
private DrawerLayout drawerLayout;
private ListView drawerList;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
ButterKnife.bind(this);
drawerLayout = (DrawerLayout) findViewById(R.id.drawer_layout);
drawerList = (ListView) findViewById(R.id.left_drawer);
SportInterface sportInterface = SportClient.getApiService();
Call<SportNews> call = sportInterface.getArticles();
call.enqueue(new Callback<SportNews>() {
#Override
public void onResponse(Call<SportNews> call, Response<SportNews> response) {
sportNews = response.body();
if (sportNews != null && sportNews.getArticles() != null) {
articleList.addAll(sportNews.getArticles());
}
articleAdapter = new ArticleAdapter(articleList, sportNews);
RecyclerView.LayoutManager layoutManager = new LinearLayoutManager(getApplicationContext());
recyclerView.setLayoutManager(layoutManager);
recyclerView.setAdapter(articleAdapter);
}
#Override
public void onFailure(Call<SportNews> call, Throwable t) {
}
});
}
}
below activity_main.xml
<android.support.v4.widget.DrawerLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:id="#+id/drawer_layout"
android:layout_width="match_parent"
android:layout_height="match_parent">
<!-- The main content view -->
<android.support.v7.widget.RecyclerView
android:id="#+id/recyclerView"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:scrollbars="vertical" />
<!-- The navigation drawer -->
<ListView
android:id="#+id/left_drawer"
android:layout_width="240dp"
android:layout_height="match_parent"
android:layout_gravity="start"
android:background="#111"
android:choiceMode="singleChoice"
android:divider="#android:color/transparent"
android:dividerHeight="0dp" />
</android.support.v4.widget.DrawerLayout>
Actually, your BaseActivity has not Layout Set(setContentView) so indeed the DrawerLayout will be null, you should Not declare View/findViewById in your BaseActivity, also, the super.onCreate() in your MainActivity trigger before everything the onCreate() in the BaseActivity and thus causing the crash
Write the below line After super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
Menu Item click not working I tried various things but it won't work.
Here are my code:
Home Activity:
public class HomeActivity extends AppCompatActivity implements NavigationView.OnNavigationItemSelectedListener{
private Button mBtRequest;
private Button mBtContinue;
private ProfileFragment mProfileFragment;
private SetPreferences Setpref;
private SlideUp slideUp;
private View dim;
private View sliderView;
Toast toast;
private TextView mTvDrawerName;
private TextView mTvDrawerMobile;
private TextView mtoolbarTitle;
private String mfullName;
private String mMobile;
private SharedPreferences mSharedPreferences;
private CompositeSubscription mSubscriptions;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
// Checking for first time launch - before calling setContentView()
Setpref = new SetPreferences(this);
if (!Setpref.IsLoggined()) {
gotoMain();
finish();
}
setContentView(R.layout.activity_home);
ButterKnife.bind(this);
mSubscriptions = new CompositeSubscription();
initSharedPreferences();
Toolbar toolbar = (Toolbar) findViewById(R.id.toolbar);
setSupportActionBar(toolbar);
getSupportActionBar().setDisplayShowTitleEnabled(false);
toolbar.findViewById(R.id.toolbar_title).setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
Snackbar.make(v, "Replace with your own action", Snackbar.LENGTH_LONG)
.setAction("Action", null).show();
}
});
DrawerLayout drawer = (DrawerLayout) findViewById(R.id.drawer_layout);
mBtRequest = (Button) findViewById(R.id.btn_request);
mBtContinue = (Button) findViewById(R.id.btn_continue);
mBtRequest.setOnClickListener(view -> slideUp());
mBtContinue.setOnClickListener(view -> checkout());
ActionBarDrawerToggle toggle = new ActionBarDrawerToggle(
this, drawer, toolbar, R.string.navigation_drawer_open, R.string.navigation_drawer_close);
drawer.setDrawerListener(toggle);
toggle.syncState();
NavigationView navigationView = (NavigationView) findViewById(R.id.nav_view);
navigationView.setNavigationItemSelectedListener(this);
sliderView = findViewById(R.id.slideView);
sliderView.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
if (toast != null){
toast.cancel();
}
toast = Toast.makeText(HomeActivity.this, "click", Toast.LENGTH_SHORT);
toast.show();
}
});
dim = findViewById(R.id.dim);
slideUp = new SlideUpBuilder(sliderView)
.withListeners(new SlideUp.Listener.Events() {
#Override
public void onSlide(float percent) {
dim.setAlpha(1 - (percent / 100));
}
#Override
public void onVisibilityChanged(int visibility) {
if (visibility == View.GONE){
// fab.show();
}
}
})
.withStartGravity(Gravity.BOTTOM)
.withLoggingEnabled(true)
.withGesturesEnabled(true)
.withStartState(SlideUp.State.HIDDEN)
.build();
Typeface myraid_bold = Typeface.createFromAsset(getAssets(),"fonts/MyriadPro-Bold_0.otf");
Typeface myraid_semibold = Typeface.createFromAsset(getAssets(),"fonts/MyriadPro-Semibold_0.otf");
View header = navigationView.getHeaderView(0);
mTvDrawerName = (TextView) header.findViewById(R.id.nav_user_name);
mTvDrawerMobile = (TextView) header.findViewById(R.id.nav_mobile_number);
mtoolbarTitle = (TextView) findViewById(R.id.toolbar_title);
mTvDrawerName.setText(mfullName);
mTvDrawerMobile.setText(mMobile);
mTvDrawerName.setTypeface(myraid_bold);
mTvDrawerMobile.setTypeface(myraid_bold);
mtoolbarTitle.setTypeface(myraid_semibold);
mBtRequest.setTypeface(myraid_bold);
mBtContinue.setTypeface(myraid_bold);
}
private void initSharedPreferences() {
mSharedPreferences = PreferenceManager.getDefaultSharedPreferences(this);
mfullName = mSharedPreferences.getString(Constants.FULLNAME,"");
mMobile = mSharedPreferences.getString(Constants.MOBILE,"");
}
private void gotoProfile(){
if (mProfileFragment == null) {
mProfileFragment = new ProfileFragment();
}
getFragmentManager().beginTransaction().replace(R.id.fragmentFrame,mProfileFragment,ProfileFragment.TAG).commit();
}
private void gotoMain(){
Setpref.setIsLoggined(false);
Intent intent = new Intent(getApplicationContext(), MainActivity.class);
startActivity(intent);
}
private void slideUp(){
slideUp.show();
}
private void checkout(){
}
#Override
public void onBackPressed() {
DrawerLayout drawer = (DrawerLayout) findViewById(R.id.drawer_layout);
if (drawer.isDrawerOpen(GravityCompat.START)) {
drawer.closeDrawer(GravityCompat.START);
} else {
super.onBackPressed();
}
}
#Override
public boolean onCreateOptionsMenu(Menu menu) {
// Inflate the menu; this adds items to the action bar if it is present.
getMenuInflater().inflate(R.menu.main, menu);
return true;
}
#Override
public boolean onOptionsItemSelected(MenuItem item) {
// Handle action bar item clicks here. The action bar will
// automatically handle clicks on the Home/Up button, so long
// as you specify a parent activity in AndroidManifest.xml.
int id = item.getItemId();
//noinspection SimplifiableIfStatement
if (id == R.id.action_settings) {
return true;
}
return super.onOptionsItemSelected(item);
}
private void logout() {
SharedPreferences.Editor editor = mSharedPreferences.edit();
editor.putString(Constants.MOBILE,"");
editor.putString(Constants.TOKEN,"");
editor.putString(Constants.FULLNAME,"");
editor.apply();
gotoMain();
}
private void showSnackBarMessage(String message) {
Snackbar.make(findViewById(R.id.drawer_layout),message,Snackbar.LENGTH_SHORT).show();
}
#SuppressWarnings("StatementWithEmptyBody")
#Override
public boolean onNavigationItemSelected(MenuItem item) {
// Handle navigation view item clicks here.
int id = item.getItemId();
if (id == R.id.nav_my_addresses) {
// Handle the camera action
} else if (id == R.id.nav_my_orders) {
} else if (id == R.id.nav_refer) {
} else if (id == R.id.nav_logout) {
logout();
}
DrawerLayout drawer = (DrawerLayout) findViewById(R.id.drawer_layout);
drawer.closeDrawer(GravityCompat.START);
return true;
}
activity_home_drawer.xml
<?xml version="1.0" encoding="utf-8"?>
<menu xmlns:android="http://schemas.android.com/apk/res/android">
<group android:checkableBehavior="single">
<item
android:id="#+id/nav_my_addresses"
android:icon="#drawable/ic_location_on_white_24px"
android:title="My Addresses" />
<item
android:id="#+id/nav_my_orders"
android:icon="#drawable/ic_history_white_24px"
android:title="My Orders" />
<item
android:id="#+id/nav_refer"
android:icon="#drawable/ic_record_voice_over_white_24px"
android:title="Refer & Earn" />
</group>
<group
android:id="#+id/menu_bottom"
android:checkableBehavior="none">
<item
android:id="#+id/nav_logout"
android:icon="#drawable/ic_exit_to_app_white_24px"
android:title="Logout" />
</group>
</menu>
nav_header_main.xml
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout 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="#dimen/nav_header_height"
android:background="#drawable/side_nav_bar"
android:gravity="bottom"
android:orientation="vertical"
android:paddingTop="#dimen/activity_vertical_margin"
android:paddingBottom="#dimen/activity_vertical_margin"
android:paddingLeft="#dimen/activity_horizontal_margin"
android:paddingRight="#dimen/activity_horizontal_margin"
android:theme="#style/ThemeOverlay.AppCompat.Dark">
<TextView
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:paddingTop="#dimen/nav_header_vertical_spacing"
android:text="Aashish Kaushik"
android:id="#+id/nav_user_name"
android:textColor="#android:color/white"/>
<TextView
android:id="#+id/nav_mobile_number"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="9910454530"
android:textColor="#android:color/white"/>
</LinearLayout>
activity_home.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">
<FrameLayout
android:alpha="0"
android:id="#+id/dim"
android:fitsSystemWindows="true"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:background="#color/dimBg" />
<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_home_drawer" />
<!-- The Fragment -->
<FrameLayout
android:id="#+id/fragmentFrame"
android:layout_width="match_parent"
android:layout_height="match_parent"/>
</android.support.v4.widget.DrawerLayout>
When I try to view activity_home.xml as a design it will not showing left drawer but when I install the app on device it will show the left drawer on click but when I click on any time it will not showing check able box and not working.
Update These lines of code works for me.. after update clean and rebuild Project.
NavigationView navigationView = (NavigationView) findViewById(R.id.nav_view);
navigationView.setNavigationItemSelectedListener(this);
navigationView.bringToFront();
Here is a simple solution to address this issue. You can just link your HomeActivity methods to the menu items (whichever you want to). Now just create your methods and go to the menu layout. In the menu layout just add the android:onClick inside the item tag and put the particular method name inside it. And you are done. Let me know if this was useful.
I would like to extend AppCompatActivity to centralize codes in order to share codes, e.g. DrawerLayout, etc.
However, I encounter NullPointerException. Here is my code:
MasterActivity
public class MasterActivity extends AppCompatActivity {
public static final String TAG = "MasterActivity";
private DrawerLayout mDrawerLayout;
private ActionBarDrawerToggle mDrawerToggle;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
}
protected void setupDrawer() {
// Drawer
mDrawerLayout = (DrawerLayout)findViewById(R.id.drawer_layout);
mDrawerLayout.setDrawerShadow(R.drawable.drawer_shadow, GravityCompat.START);
mDrawerToggle = new ActionBarDrawerToggle(this, mDrawerLayout, R.string.open_drawer, R.string.close_drawer) {
#Override
public void onDrawerOpened(View drawerView) {
}
#Override
public void onDrawerClosed(View drawerView) {
}
};
mDrawerLayout.addDrawerListener(mDrawerToggle);
}
}
ChildActivity
public class ChildActivity extends MasterActivity {
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_child);
setupDrawer();
}
}
activity_child.xml
<?xml version="1.0" encoding="utf-8"?>
<android.support.v4.widget.DrawerLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:orientation="vertical"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:id="#+id/drawer_layout"
xmlns:tools="http://schemas.android.com/tools"
tools:context=".ChildActivity">
<LinearLayout
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:orientation="vertical" >
<!-- Main Content -->
</LinearLayout>
<LinearLayout android:id="#+id/llv_left_drawer"
android:layout_width="240dp"
android:layout_height="match_parent"
android:layout_gravity="start"
android:orientation="vertical"
android:background="#888" >
<!-- Drawer Content -->
</LinearLayout>
</android.support.v4.widget.DrawerLayout>
The NPE appears at:
mDrawerLayout.setDrawerShadow(R.drawable.drawer_shadow, GravityCompat.START);
the error message is:
Attempt to invoke virtual method 'void android.support.v4.widget.DrawerLayout.setDrawerShadow(int, int)' on a null object reference
Obviously the variable mDrawerLayout is null, as findViewById() cannot locate it from layout XML. The R.id.drawer_layout is located at R.layout.activity_child. If the ChildActivity extends AppCompatActivity, the NPE does not appear.
How can I resolve it?
How about
protected void setupDrawer(View v) {
mDrawerLayout = (DrawerLayout)v.findViewById(R.id.drawer_layout);
...
and then in ChildActivity
setContentView(R.layout.activity_child);
setupDrawer(findViewById(android.R.id.content));//use root view
My BaseDrawerActivity extends BaseActivity and I have a Toolbar in BaseActivity.
The toolbar shows with no issues in classes that extend BaseActivity, but ALL classes that extend BaseDrawerActivity just show a blank toolbar. The nav drawer works fine.
When I had one main activity class (BaseActivity + BaseDrawerActivity) the toolbar showed no problem and the nav drawer worked.
Why is my implementation here not showing the Toolbar? I debugged and getToolbar() is returning the toolbar for sure.
activity_base_drawer.xml
<LinearLayout
xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical">
<include layout="#layout/toolbar"/>
<android.support.v4.widget.DrawerLayout
android:id="#+id/drawer_layout"
android:layout_width="match_parent"
android:layout_height="match_parent">
<FrameLayout
android:layout_width="match_parent"
android:layout_height="match_parent"
android:foreground="?android:windowContentOverlay">
<FrameLayout
android:id="#+id/container"
android:layout_width="match_parent"
android:layout_height="match_parent"/>
<include layout="#layout/call_to_action_banner"/>
</FrameLayout>
<ListView
android:id="#+id/navigation_drawer"
android:layout_width="#dimen/navigation_drawer_width"
android:layout_height="match_parent"
android:layout_gravity="start"
style="#style/NavDrawerListView" />
</android.support.v4.widget.DrawerLayout>
</LinearLayout>
toolbar.xml
<?xml version="1.0" encoding="utf-8"?>
<android.support.v7.widget.Toolbar
xmlns:android="http://schemas.android.com/apk/res/android"
android:theme="#style/ToolbarOverlay"
android:popupTheme="#style/ToolbarOverlay"
android:id="#+id/toolbar"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:background="#android:color/white"
android:minHeight="?attr/actionBarSize"
android:elevation="10dp"/>
BaseDrawerActivity
public abstract class BaseDrawerActivity extends BaseActivity {
private static final int LAYOUT_ID = R.layout.activity_base_drawer;
private DrawerLayout mDrawerLayout;
private ActionBarDrawerToggle mDrawerToggle;
private NavDrawerAdapter mNavDrawerAdapter;
#Override
public void onConfigurationChanged(Configuration newConfig) {
super.onConfigurationChanged(newConfig);
mDrawerToggle.onConfigurationChanged(newConfig);
}
#Override
public void onBackPressed() {
if (mDrawerLayout.isDrawerOpen(GravityCompat.START)){
mDrawerLayout.closeDrawers();
} else {
super.onBackPressed();
}
}
#Override
public boolean onOptionsItemSelected(MenuItem item) {
if (mDrawerToggle.onOptionsItemSelected(item)) {
return true;
} else {
return super.onOptionsItemSelected(item);
}
}
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(LAYOUT_ID);
setupNavDrawer();
}
#Override
protected void onPostCreate(Bundle savedInstanceState) {
super.onPostCreate(savedInstanceState);
// Sync the toggle state after onRestoreInstanceState has occurred.
mDrawerToggle.syncState();
}
private void setupNavDrawer() {
final ListView navDrawerListView = (ListView) findViewById(R.id.navigation_drawer);
View header = getLayoutInflater().inflate(R.layout.nav_drawer_header, null, false);
mNavDrawerAvatarImageView = (ImageView) header.findViewById(R.id.avatar);
mNavDrawerUsernameTextView = (CustomTextView) header.findViewById(R.id.username);
navDrawerListView.addHeaderView(header);
mDrawerLayout = (DrawerLayout) findViewById(R.id.drawer_layout);
mDrawerToggle = new ActionBarDrawerToggle(
this,
mDrawerLayout,
getToolbar(),
R.string.navigation_drawer_open,
R.string.navigation_drawer_close) {
/** Called when a drawer has settled in a completely closed state. */
public void onDrawerClosed(View view) {
super.onDrawerClosed(view);
invalidateOptionsMenu(); // creates call to onPrepareOptionsMenu()
}
/** Called when a drawer has settled in a completely open state. */
public void onDrawerOpened(View drawerView) {
super.onDrawerOpened(drawerView);
updateNavDrawerUserInfo();
invalidateOptionsMenu(); // creates call to onPrepareOptionsMenu()
}
};
mDrawerLayout.setDrawerListener(mDrawerToggle);
mDrawerLayout.setDrawerShadow(R.drawable.drawer_shadow, GravityCompat.START);
mNavDrawerAdapter = new NavDrawerAdapter(this);
navDrawerListView.setAdapter(mNavDrawerAdapter);
navDrawerListView.setOnItemClickListener(new AdapterView.OnItemClickListener() {
#Override
public void onItemClick(AdapterView<?> adapterView, View view, int position, long id) {
mDrawerLayout.closeDrawer(GravityCompat.START);
onNavigationDrawerItemSelected(position);
}
});
updateNavDrawerUserInfo();
}
private void updateNavDrawerUserInfo() {
final DatabaseHelper db = DatabaseHelper.getInstance(this);
if (db.doesUserExist(SharedPrefs.getUserId())) {
final User currentUser = db.getUser(SharedPrefs.getUserId());
if (currentUser != null) {
if (currentUser.getAvatarType() != null) {
try {
mNavDrawerAvatarImageView.setImageDrawable(getResources().getDrawable(
ViewUtil.getAvatarHeadDrawableId(this,
currentUser.getAvatarType())));
} catch (Resources.NotFoundException e) {
e.printStackTrace();
}
}
if (currentUser.getUsername() != null) {
mNavDrawerUsernameTextView.setText(currentUser.getUsername());
}
}
}
}
}
BaseActivity
private void setupToolbar() {
mToolbar = (Toolbar) findViewById(R.id.toolbar);
setSupportActionBar(mToolbar);
if (getSupportActionBar() != null) {
getSupportActionBar().setTitle("");
getSupportActionBar().setSubtitle("");
getSupportActionBar().setLogo(R.drawable.logo_toolbar);
}
mUpdatingSpinner = (ProgressBar) getLayoutInflater().inflate(
R.layout.toolbar_updating_spinner, null, false);
int dpInPixels = (int) getResources().getDimension(R.dimen.toolbar_updating_spinner);
Toolbar.LayoutParams spinnerLp = new Toolbar.LayoutParams(dpInPixels, dpInPixels,
Gravity.END);
mToolbar.addView(mUpdatingSpinner, spinnerLp);
}
I found the answer although I don't fully understand it.
I basically called setupToolbar() again in my BaseDrawerActivity right before I call setupNavDrawer() and for some reason this fixed it.
I think the reference to the Toolbar from BaseActivity wasn't retrieving correctly (even though I debugged and it had a reference to it). Another thing I tried is setSupportActionBar(mToolbar) right before setting up the nav drawer but that didn't work.
If anyone has any ideas as to why I have to setup the toolbar again in order for it to show I'd be glad to hear it!
go to the AndroidManifest.xml file and replace
android:theme="#style/AppTheme"
with
android:theme="#android:style/Theme.Holo.Light.DarkActionBar"
you have to use setSupportActionBar(Toolbar toolbar).
This question should help.
I'm trying to use the DrawerLayout with ActionBarDrawerToggle.
see my code below:
public class MainActivity extends ActionBarActivity {
private static final String TAG = MainActivity.class.getName();
private ActionBarDrawerToggle mDrawerToggle;
private DrawerLayout mDrawerLayout;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.fragment_main);
FeedsFragment feeds = new FeedsFragment();
if (findViewById(R.id.main) != null) {
mDrawerLayout = (DrawerLayout) findViewById(R.id.drawer_layout);
getSupportActionBar().setDisplayHomeAsUpEnabled(true);
getSupportActionBar().setHomeButtonEnabled(true);
mDrawerToggle = new ActionBarDrawerToggle(
this,
mDrawerLayout,
R.drawable.ic_drawer,
R.string.drawer_open,
R.string.drawer_close);
mDrawerLayout.setDrawerListener(mDrawerToggle);
getSupportFragmentManager().beginTransaction().add(R.id.main, feeds).commit();
} else if (findViewById(R.id.content) != null) {
NavDrawerFragment nav = new NavDrawerFragment();
getSupportFragmentManager().beginTransaction()
.add(R.id.nav, nav)
.add(R.id.content, feeds)
.commit();
}
}
#Override
protected void onPostCreate(Bundle savedInstanceState) {
super.onPostCreate(savedInstanceState);
mDrawerToggle.syncState();
}
#Override
public void onConfigurationChanged(Configuration config) {
super.onConfigurationChanged(config);
mDrawerToggle.onConfigurationChanged(config);
}
}
and my view:
<?xml version="1.0" encoding="utf-8"?>
<android.support.v4.widget.DrawerLayout
xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:id="#+id/drawer_layout"
android:layout_width="match_parent"
android:layout_height="match_parent" >
<FrameLayout
android:id="#+id/main"
android:layout_width="match_parent"
android:layout_height="match_parent" />
<!--<include layout="#layout/nav" />-->
<fragment
android:layout_width="240dp"
android:layout_height="match_parent"
android:name="com.primeirochute.com.primeirochute.fragment.NavDrawerFragment"
tools:layout="#layout/nav" />
</android.support.v4.widget.DrawerLayout>
But when I run my project, the left menu (DrawerLayout) just show on my screen doesn't make the slider event.
Finaly works:
I just added the gravity="start" at my second view
<android.support.v4.widget.DrawerLayout
xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:id="#+id/drawer_layout"
android:layout_width="match_parent"
android:layout_height="match_parent" >
<FrameLayout
android:id="#+id/main"
android:layout_width="match_parent"
android:layout_height="match_parent" />
<!--<include layout="#layout/nav" />-->
<fragment
android:layout_width="240dp"
android:layout_height="match_parent"
android:layout_gravity="start"
android:name="com.primeirochute.com.primeirochute.fragment.NavDrawerFragment"
tools:layout="#layout/nav" />
</android.support.v4.widget.DrawerLayout>
Uses the function onOptionsItemSelected and control the drawer event:
public boolean onOptionsItemSelected(MenuItem item) {
int itemID = item.getItemId();
switch (itemID) {
case android.R.id.home: {
DrawerLayout drawerLayout = (DrawerLayout)findViewById(R.id.drawer_layout);
if (drawerLayout.isDrawerOpen(Gravity.LEFT)) {
drawerLayout.closeDrawers();
}
else {
drawerLayout.openDrawer(Gravity.LEFT);
}
}
break;
return true;
}
I hope it works for your case.