whenever I create my activity initially, everything goes fine as I am able to inflate my layouts correctly. However, the issue is whenever I switch to using another app, then go back to my own app, I get an error saying that the TabLayout is null, causing my app to crash. If I switch to another app for a few minutes, my DrawerLayout is null, also causing my app to crash.
If I understand the Android Life Cycle correctly, I realize that the activity is recreated when it goes from background to foreground, and the onCreate method is called again as referenced from this: Android activity life cycle - what are all these methods for?. However, I don't understand why when the app starts, everything works fine, but when I go into the background, either the TabLayout or the DrawerLayout is set to null. Here is my attempt:
news_feed.java:
private static DrawerLayout drawer;
private static TabLayout tabLayout;
public class news_feed extends BatchAppCompatActivity implements NavigationView.OnNavigationItemSelectedListener {
#Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.news_feed);
drawer = (DrawerLayout) findViewById(R.id.drawer_layout);
toolbar = (Toolbar) findViewById(R.id.toolbar);
setSupportActionBar(toolbar);
//Listen for navigation events
ActionBarDrawerToggle toggle = new ActionBarDrawerToggle(
this, drawer, toolbar, R.string.navigation_drawer_open, R.string.navigation_drawer_close){
public void onDrawerOpened(View view) {
super.onDrawerOpened(view);
}
/** Called when a drawer has settled in a completely closed state. */
public void onDrawerClosed(View view) {
super.onDrawerClosed(view);
}
};
System.out.println("news_feed: toolbar: " + toolbar);
System.out.println("news_feed: Drawer: " + drawer);
System.out.println("news_feed: toggle: " + toggle);
drawer.setDrawerListener(toggle);
toggle.syncState();
TabLayout tabLayout = (TabLayout) findViewById(R.id.tab_layout);
System.out.println("news_feed: Tab Layout: " + tabLayout);
tabLayout.addTab(tabLayout.newTab().setText("First"));
tabLayout.addTab(tabLayout.newTab().setText("Second"));
tabLayout.addTab(tabLayout.newTab().setText("Third"));
tabLayout.setTabGravity(TabLayout.GRAVITY_FILL);
}
}
news_feed.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_news_feed" android:layout_width="match_parent"
android:layout_height="match_parent" android:id="#+id/app_bar_main" />
<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">
<LinearLayout
android:orientation="vertical"
android:layout_width="match_parent"
android:layout_height="match_parent">
<include
layout="#layout/nav_header_friends_list"
android:id="#+id/navigation_header"/>
<ListView
android:id="#+id/friends_list"
android:layout_width="match_parent"
android:layout_height="wrap_content"></ListView>
</LinearLayout>
</android.support.design.widget.NavigationView>
</android.support.v4.widget.DrawerLayout>
app_bar_news_feed.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"
xmlns:tools="http://schemas.android.com/tools" android:layout_width="match_parent"
android:layout_height="match_parent" android:fitsSystemWindows="true"
tools:context=".news_feed">
<RelativeLayout
android:id="#+id/main_layout"
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.support.design.widget.AppBarLayout android:layout_height="wrap_content"
android:layout_width="match_parent" android:theme="#style/AppTheme.AppBarOverlay" android:id="#+id/app_bar">
<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_news_feed" /> -->
<android.support.design.widget.TabLayout
android:id="#+id/tab_layout"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_below="#+id/app_bar"
android:background="?attr/colorPrimary"
android:elevation="6dp"
android:minHeight="?attr/actionBarSize"
android:theme="#style/ThemeOverlay.AppCompat.Dark.ActionBar"/>
<android.support.v4.view.ViewPager
android:id="#+id/pager"
android:layout_width="match_parent"
android:layout_height="fill_parent"
android:layout_below="#id/tab_layout"/>
</RelativeLayout>
<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"
android:src="#android:drawable/ic_dialog_email" />
</android.support.design.widget.CoordinatorLayout>
I made sure that the findViewById's are all referencing the correct id's, but I can't seem to figure what is going wrong. It's strange: if I quickly switch from app -> another app -> app, then the TabLayout is null. If I switch from app -> another app -> wait a few minutes -> app, then DrawerLayout is null. I have no idea why this is occuring! Any help would be appreciated.
Edit: The app crashes on the onCreate method of my activity. Moreover, I have provided a stacktrace: as followed here:
03-16 09:31:21.116 25852-25852/com.test.tabs.tabs I/System.out: news_feed: toolbar: android.support.v7.widget.Toolbar{380bcc25 V.E..... ......ID 0,0-0,0 #7f0d009c app:id/toolbar}
03-16 09:31:21.116 25852-25852/com.test.tabs.tabs I/System.out: news_feed: Drawer: android.support.v4.widget.DrawerLayout{3ed761fa VFE..... ......I. 0,0-0,0 #7f0d0095 app:id/drawer_layout}
03-16 09:31:21.116 25852-25852/com.test.tabs.tabs I/System.out: news_feed: toggle: com.test.tabs.tabs.com.tabs.activity.news_feed$1#22eb13ab
03-16 09:31:21.116 25852-25852/com.test.tabs.tabs I/System.out: news_feed: Tab Layout: null
03-16 09:31:21.116 25852-25852/com.test.tabs.tabs E/AndroidRuntime: FATAL EXCEPTION: main
Process: com.test.tabs.tabs, PID: 25852
java.lang.RuntimeException: Unable to start activity ComponentInfo{com.test.tabs.tabs/com.test.tabs.tabs.com.tabs.activity.news_feed}: java.lang.NullPointerException: Attempt to invoke virtual method 'android.support.design.widget.TabLayout$Tab android.support.design.widget.TabLayout.newTab()' on a null object reference
at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:2661)
at android.app.ActivityThread.handleLaunchActivity(ActivityThread.java:2726)
at android.app.ActivityThread.access$900(ActivityThread.java:172)
at android.app.ActivityThread$H.handleMessage(ActivityThread.java:1421)
at android.os.Handler.dispatchMessage(Handler.java:102)
at android.os.Looper.loop(Looper.java:145)
at android.app.ActivityThread.main(ActivityThread.java:5835)
at java.lang.reflect.Method.invoke(Native Method)
at java.lang.reflect.Method.invoke(Method.java:372)
at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:1399)
at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:1194)
Caused by: java.lang.NullPointerException: Attempt to invoke virtual method 'android.support.design.widget.TabLayout$Tab android.support.design.widget.TabLayout.newTab()' on a null object reference
at com.test.tabs.tabs.com.tabs.activity.news_feed.onCreate(news_feed.java:174)
at android.app.Activity.performCreate(Activity.java:6221)
at android.app.Instrumentation.callActivityOnCreate(Instrumentation.java:1119)
at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:2614)
at android.app.ActivityThread.handleLaunchActivity(ActivityThread.java:2726)
at android.app.ActivityThread.access$900(ActivityThread.java:172)
at android.app.ActivityThread$H.handleMessage(ActivityThread.java:1421)
at android.os.Handler.dispatchMessage(Handler.java:102)
at android.os.Looper.loop(Looper.java:145)
at android.app.ActivityThread.main(ActivityThread.java:5835)
at java.lang.reflect.Method.invoke(Native Method)
at java.lang.reflect.Method.invoke(Method.java:372)
at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:1399)
at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:1194)
Edit: Included BatchAppCompatActivity class:
public class BatchAppCompatActivity extends AppCompatActivity {
#Override
protected void onStart()
{
super.onStart();
Batch.onStart(this);
}
#Override
protected void onStop()
{
Batch.onStop(this);
super.onStop();
}
#Override
protected void onDestroy()
{
Batch.onDestroy(this);
super.onDestroy();
}
#Override
protected void onNewIntent(Intent intent)
{
Batch.onNewIntent(this, intent);
super.onNewIntent(intent);
}
}
Your declaration of the drawer and tabLayout variables seems a bit strange. Unless it's a typo I'm surprised it even works. Something like
public class news_feed extends BatchAppCompatActivity implements NavigationView.OnNavigationItemSelectedListener {
private DrawerLayout drawer;
private TabLayout tabLayout;
#Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.news_feed);
drawer = (DrawerLayout) findViewById(R.id.drawer_layout);
toolbar = (Toolbar) findViewById(R.id.toolbar);
setSupportActionBar(toolbar);
//Listen for navigation events
ActionBarDrawerToggle toggle = new ActionBarDrawerToggle(
this, drawer, toolbar, R.string.navigation_drawer_open, R.string.navigation_drawer_close){
public void onDrawerOpened(View view) {
super.onDrawerOpened(view);
}
/** Called when a drawer has settled in a completely closed state. */
public void onDrawerClosed(View view) {
super.onDrawerClosed(view);
}
};
System.out.println("news_feed: toolbar: " + toolbar);
System.out.println("news_feed: Drawer: " + drawer);
System.out.println("news_feed: toggle: " + toggle);
drawer.setDrawerListener(toggle);
toggle.syncState();
tabLayout = (TabLayout) findViewById(R.id.tab_layout);
System.out.println("news_feed: Tab Layout: " + tabLayout);
tabLayout.addTab(tabLayout.newTab().setText("First"));
tabLayout.addTab(tabLayout.newTab().setText("Second"));
tabLayout.addTab(tabLayout.newTab().setText("Third"));
tabLayout.setTabGravity(TabLayout.GRAVITY_FILL);
}
}
should work assuming toolbar is defined somewhere else in your class.
Related
Toolbar menu is inflated in fragment but then cleared later.
When activity is first created (or rotated) the toolbar menu is inflated properly in the fragment, but then gets cleared before it can be displayed.
I set the toolbar menu in my fragment's onActivityCreated, and it stays set through onResume in the activity. The next call I've found is in onCreateOptionsMenu in the activity, but at this point toolbar.getMenu().size() = 0
Somewhere between onResume and onCreateOptionsMenu the toolbar menu is getting reset.
Edit:
I'm not sure what is necessary to reproduce it, but here is all(?) of the relevant code.
Activity:
private Toolbar toolbar;
private DrawerLayout drawer;
private ActionBarDrawerToggle toggle;
private FloatingActionButton fab;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.drawer_main);
toolbar = findViewById(R.id.toolbar);
setSupportActionBar(toolbar);
fab = findViewById(R.id.main_fab);
drawer = findViewById(R.id.drawer_layout);
toggle = new ActionBarDrawerToggle(this, drawer,toolbar,R.string.nav_drawer_open,R.string.nav_drawer_close);
drawer.addDrawerListener(toggle);
NavigationView navigationView = findViewById(R.id.nav_view);
navigationView.setNavigationItemSelectedListener(this);
if (savedInstanceState == null) {
showFragment(ScheduleFragment.newInstance());
}
}
#Override
public boolean onOptionsItemSelected(MenuItem item) {
if(toggle.onOptionsItemSelected(item)) {
return true;
}
return super.onOptionsItemSelected(item);
}
#Override
protected void onPostCreate(Bundle savedInstanceState) {
CharSequence retainTitle = toolbar.getTitle();
super.onPostCreate(savedInstanceState);
toggle.syncState();
toolbar.setTitle(retainTitle);
}
Fragment:
#Override
public void onActivityCreated(Bundle savedInstanceState) {
super.onActivityCreated(savedInstanceState);
toolbar = ((MainActivity)getActivity()).getToolbar();
setMenuAction(MENU_ACTION_DELETE);
}
protected void setMenuAction(int menuAction) {
Log.d(logger, "setting the menu");
switch(menuAction) {
case MENU_ACTION_DELETE:
toolbar.getMenu().clear();
toolbar.inflateMenu(R.menu.menu_delete);
break;
case MENU_ACTION_NONE:
Log.d(logger, "clearing menu");
toolbar.getMenu().clear();
break;
}
}
Layouts:
<?xml version="1.0" encoding="utf-8"?>
<android.support.v4.widget.DrawerLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="match_parent"
xmlns:app="http://schemas.android.com/apk/res-auto"
android:id="#+id/drawer_layout">
<include
layout="#layout/activity_main"/>
<android.support.design.widget.NavigationView
android:id="#+id/nav_view"
android:layout_width="wrap_content"
android:layout_height="match_parent"
android:layout_gravity="start"
app:headerLayout="#layout/nav_header"
app:menu="#menu/menu_nav" />
</android.support.v4.widget.DrawerLayout>
<?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:layout_scrollFlags="scroll|snap|enterAlways"
app:popupTheme="#style/AppTheme.PopupOverlay" />
</android.support.design.widget.AppBarLayout>
<android.support.design.widget.FloatingActionButton
android:id="#+id/main_fab"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="end|bottom"
android:src="#drawable/ic_baseline_add_24px"
android:layout_margin="16dp" />
<include layout="#layout/content_main"/>
</android.support.design.widget.CoordinatorLayout>
<?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/activity_main">
<FrameLayout
android:id="#+id/fragmentHolder"
android:layout_width="0dp"
android:layout_height="0dp"
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintLeft_toLeftOf="parent"
app:layout_constraintRight_toRightOf="parent"
app:layout_constraintTop_toTopOf="parent" />
</android.support.constraint.ConstraintLayout>
The problem in my current code as posted was the line setSupportActionBar(toolbar);
This was not needed, and was in fact causing the troubling lifecycle problems stated above.
I am trying to toggle the navigation view by the hamburger icon. The navigation view is appearing on sliding from the left. The following is the code that I have included in my MainActivity "onCreate Function"
Toolbar toolbar = (Toolbar) findViewById(R.id.toolbar);
toolbar.setVisibility(View.VISIBLE);
setSupportActionBar(toolbar);
NavigationView navigationView = (NavigationView) findViewById(R.id.nav_view);
navigationView.setNavigationItemSelectedListener(this);
mDrawerLayout = (DrawerLayout) findViewById(R.id.drawer_layout);
ActionBarDrawerToggle toggle = new ActionBarDrawerToggle(
this, mDrawerLayout, toolbar, R.string.navigation_drawer_open, R.string.navigation_drawer_close);
mDrawerLayout.addDrawerListener(toggle);
getSupportActionBar().setHomeButtonEnabled(true);
toggle.syncState();
I also have tried this code block which doesn't seem to work.
#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);
}
I also tried this
#Override
public boolean onOptionsItemSelected(MenuItem item) {
switch (item.getItemId()) {
case android.R.id.home:
mDrawerLayout = findViewById(R.id.drawer_layout);
mDrawerLayout.openDrawer(GravityCompat.START); // OPEN DRAWER
return true;
}
return super.onOptionsItemSelected(item);
}
My main_activity.xml is this
<?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">
>
<RelativeLayout
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/activity_main"
android:layout_width="match_parent"
android:layout_height="match_parent">
<include
layout="#layout/app_bar_main"
android:layout_height="match_parent"
android:layout_width="match_parent" />
<android.support.design.widget.BottomNavigationView
android:id="#+id/bottom_navigation"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_alignParentBottom="true"
app:itemBackground="#color/colorPrimary"
app:itemIconTint="#drawable/bottom_navigation_bar"
app:itemTextColor="#drawable/bottom_navigation_bar"
app:menu="#menu/my_navigation_items" />
<android.support.v4.view.ViewPager
android:id="#+id/viewpager"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:layout_above="#+id/bottom_navigation"
android:layout_alignParentTop="true"
app:layout_behavior="#string/appbar_scrolling_view_behavior" />
</RelativeLayout>
<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>
This is my app_bar_main.xml which is where I define the ui of toolbar.
enter code here
<?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"
android:fitsSystemWindows="true"
tools:context="com.example.android.moodindigo.MainActivity">
<!--<RelativeLayout-->
<!--android:id="#+id/relativelayout_for_fragment"-->
<!--android:layout_width="match_parent"-->
<!--android:layout_height="match_parent"-->
<!--></RelativeLayout>-->
<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"
app:title="Mood Indigo"
/>
</android.support.design.widget.AppBarLayout>
<!--<include layout="#layout/content_main" />-->
</android.support.design.widget.CoordinatorLayout>
Any help would be highly appreciated. I don't know what I am doing wrong. Please let me know if anything else is needed. I didn't paste the whole code here as the project is quite big. I checked many StackOverflow post for this and I tried to do the same thing but it doesn't seem to work.
try this in the onCreate of your main activity :
DrawerLayout drawer = (DrawerLayout) findViewById(R.id.drawer_layout);
ActionBarDrawerToggle toggle = new ActionBarDrawerToggle(
this, drawer, toolbar, R.string.navigation_drawer_open, R.string.navigation_drawer_close);
drawer.setDrawerListener(toggle);
toggle.syncState();
i hope it will help you!
In your ActionBarDrawerToggle constructor you use toolbar as third parameter. I am not sure if it is valid, since the official documentation for ActionBarDrawerToggle constructor parameters quotes:
Parameters:
activity - Activity: the Activity hosting the drawer
drawerLayout - Drawerlayout: the DrawerLayout to link to the given Activity's
ActionBar
drawerImageRes - int: A Drawable resource to use as the drawer
indicator
openDrawerContentDescRes - int: A String resource to describe the
"open drawer" action for accessibility
closeDrawerContentDescRes - int: A String resource to describe the
"close drawer" action for accessibility
So, the third parameter should be Drawable Resource but toolbar is a View.
Edit:
As you are using v7 and not v4, there is one sentence from official documentation https://developer.android.com/reference/android/support/v7/app/ActionBarDrawerToggle.html I think is important:
Please use ActionBarDrawerToggle(Activity, DrawerLayout, int, int) if you are setting the Toolbar as the ActionBar of your activity.
So it seems you should use differnt constructor from the one you are using now.
Hope this will help.
I have imported the scanner control module in my app. I have also added the module dependency correctly. I can even access the classes of imported module. But the problem is, whenever I try to open that module (I have added that as in main app navigation drawer item) it looks like there is a problem with setContentView(R.layout.activity_active_scanner). I think that the main problem is in tablayout(or else in other xml parts).
The logcat is shown below:
Caused by: java.lang.RuntimeException: Failed to resolve attribute at index 60
at android.content.res.TypedArray.getColor(TypedArray.java:401)
at android.support.design.widget.TabLayout.<init>(TabLayout.java:348)
at android.support.design.widget.TabLayout.<init>(TabLayout.java:290)
at java.lang.reflect.Constructor.newInstance(Native Method)
at java.lang.reflect.Constructor.newInstance(Constructor.java:288)
at android.view.LayoutInflater.createView(LayoutInflater.java:607)
at android.view.LayoutInflater.createViewFromTag(LayoutInflater.java:743)
at android.view.LayoutInflater.rInflate(LayoutInflater.java:806)
at android.view.LayoutInflater.rInflate(LayoutInflater.java:809)
at android.view.LayoutInflater.parseInclude(LayoutInflater.java:916)
at android.view.LayoutInflater.rInflate(LayoutInflater.java:802)
at android.view.LayoutInflater.inflate(LayoutInflater.java:504)
at android.view.LayoutInflater.inflate(LayoutInflater.java:414)
at android.view.LayoutInflater.inflate(LayoutInflater.java:365)
at android.support.v7.app.AppCompatDelegateImplV9.setContentView(AppCompatDelegateImplV9.java:284)
at android.support.v7.app.AppCompatActivity.setContentView(AppCompatActivity.java:143)
at ****com.zebra.scannercontrol.app.activities.ActiveScannerActivity.onCreate(ActiveScannerActivity.java:79)****
at android.app.Activity.performCreate(Activity.java:6092)
and the code for activity_active_scanner is:
<?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_activescanner"
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_home"
app:menu="#menu/activity_home_drawer" />
</android.support.v4.widget.DrawerLayout>
and below is the app_bar_active_scanner which I have included in activity_active_scanner:
<?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"
android:fitsSystemWindows="true"
tools:context="com.zebra.scannercontrol.app.activities.ActiveScannerActivity">
<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.TabLayout
android:id="#+id/tablayout"
android:layout_width="match_parent"
android:layout_height="?attr/actionBarSize"
android:layout_weight="#integer/abc_max_action_buttons"
app:tabBackground="#color/blue"
app:tabGravity="fill"
app:tabIndicatorColor="#color/yellow"
app:tabMaxWidth="0dp"
app:tabMode="fixed"
app:tabTextAppearance="#style/AppTabTextAppearance"/>
</android.support.design.widget.AppBarLayout>
<include layout="#layout/content_activescanner" />
</android.support.design.widget.CoordinatorLayout>
and given below is the ActiveScannerActivity in which, I have declared/initialized and set the tablayout with view pager. You can ignore other codes (I think main problem is with tablayout).
public class ActiveScannerActivity extends BaseActivity implements NavigationView.OnNavigationItemSelectedListener,
ActionBar.TabListener,ScannerAppEngine.IScannerAppEngineDevEventsDelegate,ScannerAppEngine.IScannerAppEngineDevConnectionsDelegate{
private ViewPager viewPager;
ActiveScannerAdapter mAdapter;
TabLayout tabLayout;
private NavigationView navigationView;
static int picklistMode;
public boolean isPagerMotorAvailable() {
return pagerMotorAvailable;
}
static boolean pagerMotorAvailable;
private int scannerID;
TextView barcodeCount;
int iBarcodeCount;
int BARCODE_TAB = 1;
int ADVANCED_TAB = 2;
static MyAsyncTask cmdExecTask=null;
Button btnFindScanner = null;
static final int ENABLE_FIND_NEW_SCANNER =1;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_active_scanner);
Configuration configuration = getResources().getConfiguration();
if(configuration.orientation == Configuration.ORIENTATION_LANDSCAPE){
if(configuration.smallestScreenWidthDp<Application.minScreenWidth){
setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_PORTRAIT);
}
}else{
if(configuration.screenWidthDp<Application.minScreenWidth){
setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_PORTRAIT);
}
}
Toolbar toolbar = (Toolbar) findViewById(R.id.toolbar);
setSupportActionBar(toolbar);
DrawerLayout drawer = (DrawerLayout) findViewById(R.id.drawer_layout);
ActionBarDrawerToggle toggle = new ActionBarDrawerToggle(
this, drawer, toolbar, R.string.navigation_drawer_open, R.string.navigation_drawer_close);
drawer.setDrawerListener(toggle);
toggle.syncState();
navigationView = (NavigationView) findViewById(R.id.nav_view);
navigationView.setNavigationItemSelectedListener(this);
addDevConnectionsDelegate(this);
scannerID = getIntent().getIntExtra(Constants.SCANNER_ID, -1);
BaseActivity.lastConnectedScannerID = scannerID;
String scannerName = getIntent().getStringExtra(Constants.SCANNER_NAME);
String address = getIntent().getStringExtra(Constants.SCANNER_ADDRESS);
picklistMode = getIntent().getIntExtra(Constants.PICKLIST_MODE, 0);
pagerMotorAvailable = getIntent().getBooleanExtra(Constants.PAGER_MOTOR_STATUS,false);
Application.CurScannerId = scannerID;
Application.CurScannerName = scannerName;
Application.CurScannerAddress = address;
// Initilization
viewPager = (ViewPager) findViewById(R.id.activeScannerPager);
mAdapter= new ActiveScannerAdapter(getSupportFragmentManager());
viewPager.setAdapter(mAdapter);
tabLayout = (TabLayout) findViewById(R.id.tablayout);
tabLayout.setupWithViewPager(viewPager);
I am trying to open an activity which has recyclerView in it on the click of recyclerView of first activity. But now when I'm clicking the recyclerView app is crashing with the following message.
10-18 09:30:49.912 13018-13018/in.mumbaitravellers.mtleaders
E/AndroidRuntime: FATAL EXCEPTION: main
Process: in.mumbaitravellers.mtleaders, PID: 13018
java.lang.RuntimeException: Unable to start activity
ComponentInfo{in.mumbaitravellers.mtleaders/in.mumbaitravellers.mtleaders.activity.DetailActivity}:
java.lang.NullPointerException: Attempt to invoke virtual method 'void
android.support.v7.widget.RecyclerView.setHasFixedSize(boolean)' on a
null object reference
at
android.app.ActivityThread.performLaunchActivity(ActivityThread.java:2426)
at
android.app.ActivityThread.handleLaunchActivity(ActivityThread.java:2490)
at android.app.ActivityThread.-wrap11(ActivityThread.java)
at
android.app.ActivityThread$H.handleMessage(ActivityThread.java:1354)
at android.os.Handler.dispatchMessage(Handler.java:102)
at android.os.Looper.loop(Looper.java:148)
at android.app.ActivityThread.main(ActivityThread.java:5443)
at java.lang.reflect.Method.invoke(Native Method)
at
com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:728)
at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:618)
Caused by: java.lang.NullPointerException: Attempt to invoke virtual
method 'void
android.support.v7.widget.RecyclerView.setHasFixedSize(boolean)' on a
null object reference
at
in.mumbaitravellers.mtleaders.activity.DetailActivity.setupRecycler(DetailActivity.java:120)
at
in.mumbaitravellers.mtleaders.activity.DetailActivity.onCreate(DetailActivity.java:52)
at android.app.Activity.performCreate(Activity.java:6245)
at
android.app.Instrumentation.callActivityOnCreate(Instrumentation.java:1130)
at
android.app.ActivityThread.performLaunchActivity(ActivityThread.java:2379)
at
android.app.ActivityThread.handleLaunchActivity(ActivityThread.java:2490)
at android.app.ActivityThread.-wrap11(ActivityThread.java)
at
android.app.ActivityThread$H.handleMessage(ActivityThread.java:1354)
at android.os.Handler.dispatchMessage(Handler.java:102)
at android.os.Looper.loop(Looper.java:148)
at android.app.ActivityThread.main(ActivityThread.java:5443)
at java.lang.reflect.Method.invoke(Native Method)
at
com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:728)
at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:618)
10-18 09:31:13.376 1801-2412/? E/native: do suspend false
The java code is as follows:
public class DetailActivity extends AppCompatActivity {
private ExpenseAdapter adapter;
private Realm realm;
private LayoutInflater inflater;
private FloatingActionButton fab;
private RecyclerView recycler;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_detail);
fab = (FloatingActionButton) findViewById(R.id.fab);
recycler = (RecyclerView) findViewById(R.id.recycler);
//get realm instance
this.realm = RealmController.with(this).getRealm();
Toolbar toolbar = (Toolbar) findViewById(R.id.toolbar);
setSupportActionBar(toolbar);
/*String event = getIntent().getStringExtra("eventName");
TextView tv = (TextView) findViewById(R.id.txt_EventName);
tv.setText(event);*/
setupRecycler();
if (!Prefs.with(this).getPreLoad()) {
setRealmData();
}
// refresh the realm instance
RealmController.with(this).refresh();
// get all persisted objects
// create the helper adapter and notify data set changes
// changes will be reflected automatically
setRealmAdapter(RealmController.with(this).getExpenses());
fab.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View view) {
inflater = DetailActivity.this.getLayoutInflater();
View content = inflater.inflate(R.layout.activity_add_new_expense, null);
final EditText editExpense = (EditText) content.findViewById(R.id.edtxt_expense);
final EditText editDescription = (EditText) content.findViewById(R.id.edtxt_description);
AlertDialog.Builder builder = new AlertDialog.Builder(DetailActivity.this);
builder.setView(content)
.setTitle("Add Expense")
.setPositiveButton(android.R.string.ok, new DialogInterface.OnClickListener() {
#Override
public void onClick(DialogInterface dialog, int which) {
Expense expense = new Expense();
expense.setId((int) (RealmController.getInstance().getExpenses().size() + System.currentTimeMillis()));
expense.setAmount(editExpense.getText().toString());
expense.setDescription(editDescription.getText().toString());
realm.beginTransaction();
realm.copyToRealm(expense);
realm.commitTransaction();
adapter.notifyDataSetChanged();
// scroll the recycler view to bottom
recycler.scrollToPosition(RealmController.getInstance().getExpenses().size() - 1);
}
})
.setNegativeButton(android.R.string.cancel, new DialogInterface.OnClickListener() {
#Override
public void onClick(DialogInterface dialog, int which) {
dialog.dismiss();
}
});
AlertDialog dialog = builder.create();
dialog.show();
}
});
}
public void setRealmAdapter(RealmResults<Expense> expenses) {
RealmExpenseAdapter realmExpenseAdapter = new RealmExpenseAdapter(this.getApplicationContext(), expenses, true);
adapter.setRealmAdapter(realmExpenseAdapter);
adapter.notifyDataSetChanged();
}
private void setupRecycler() {
// use this setting to improve performance if you know that changes
// in content do not change the layout size of the RecyclerView
recycler.setHasFixedSize(true);
// use a linear layout manager since the cards are vertically scrollable
final LinearLayoutManager layoutManager = new LinearLayoutManager(this);
layoutManager.setOrientation(LinearLayoutManager.VERTICAL);
recycler.setLayoutManager(layoutManager);
// create an empty adapter and add it to the recycler view
adapter = new ExpenseAdapter(this);
recycler.setAdapter(adapter);
}
private void setRealmData() {
ArrayList<Expense> expenses = new ArrayList<>();
for (Expense e : expenses) {
// Persist your data easily
realm.beginTransaction();
realm.copyToRealm(e);
realm.commitTransaction();
}
Prefs.with(this).setPreLoad(true);
}
}
And the xml file is as follows:
<?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"
android:fitsSystemWindows="true"
tools:context="in.mumbaitravellers.mtleaders.activity.DetailActivity">
<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_detail" />
<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"
android:src="#drawable/ic_action_add" />
</android.support.design.widget.CoordinatorLayout>
Recycler View Code:
<?xml version="1.0" encoding="utf-8"?>
<android.support.v7.widget.CardView xmlns:android="http://schemas.android.com/apk/res/android"
android:id="#+id/card_expense"
style="#style/AppTheme.Card.Margins"
android:layout_width="match_parent"
android:layout_height="wrap_content">
<LinearLayout
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical">
<TextView
android:id="#+id/text_amount"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_marginBottom="#dimen/margin_small"
android:paddingBottom="#dimen/margin_normal"
android:paddingLeft="#dimen/margin_large"
android:paddingRight="#dimen/margin_large"
android:paddingTop="#dimen/margin_large"
android:textColor="#555555"
android:text="\u20B9"
android:textSize="40dp"
android:textStyle="bold" />
<TextView
android:layout_width="match_parent"
android:layout_height="25dp"
android:id="#+id/text_description"
android:textSize="20dp"/>
</LinearLayout>
</android.support.v7.widget.CardView>
Content Detail.xml
<?xml version="1.0" encoding="utf-8"?>
<android.support.v7.widget.RecyclerView 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/recyclerExpense"
android:layout_width="match_parent"
android:layout_height="match_parent"
tools:showIn="#layout/activity_detail"
tools:context="in.mumbaitravellers.mtleaders.activity.DetailActivity"
app:layout_behavior="#string/appbar_scrolling_view_behavior" />
What is wrong in code, please help.
Thanks in advance!
Your problem lies in incorrect search of RecyclerView
Change your code:
recycler = (RecyclerView) findViewById(R.id.recycler);
to
recycler = (RecyclerView) findViewById(R.id.recyclerExpense);
I have an 2 activity and a service, in first I have navigation drawer, and 2 textviews in its header, and I must change their text sometimes, in service there is some data that i need
On first run everything is perfect, but when I go to the first activity from second, I have nullpointerexception in textviews. What causes it, and how to fix?
//First
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
//Navigation drawer init
Toolbar toolbar = (Toolbar) findViewById(R.id.toolbarMain);
setSupportActionBar(toolbar);
DrawerLayout drawer = (DrawerLayout) findViewById(R.id.drawer_layout);
ActionBarDrawerToggle toggle = new ActionBarDrawerToggle(
this, drawer, toolbar, R.string.navigation_drawer_open, R.string.navigation_drawer_close);
drawer.addDrawerListener(toggle);
toggle.syncState();
NavigationView navigationView = (NavigationView) findViewById(R.id.nav_view_main);
navigationView.setNavigationItemSelectedListener(this);
intent = new Intent("playbackservice");
sConn = new ServiceConnection() {
public void onServiceConnected(ComponentName name, IBinder binder) {
Log.d(LOG_TAG, "MainActivity onServiceConnected");
service = ((PlaybackService.PlaybackServiceBinder) binder).getService();
bound = true;
prepareLayout();
}
public void onServiceDisconnected(ComponentName name) {
Log.d(LOG_TAG, "MainActivity onServiceDisconnected");
bound = false;
}
};
}
private void prepareLayout() {
Log.d(LOG_TAG, "prepareLayout: Running");
((TextView) findViewById(R.id.songNameNavhead)).setText(currentSong.getName());
((TextView) findViewById(R.id.artistNavhead)).setText(currentSong.getArtist());
}
And
//Layout nav_header_main.xml
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="#dimen/nav_header_height"
android:gravity="bottom"
android:orientation="vertical"
android:background="#color/colorPrimaryDark"
android:paddingBottom="#dimen/activity_vertical_margin"
android:paddingLeft="#dimen/activity_horizontal_margin"
android:paddingRight="#dimen/activity_horizontal_margin"
android:paddingTop="#dimen/activity_vertical_margin"
android:theme="#style/ThemeOverlay.AppCompat.Dark">
<TextView
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:textAppearance="?android:attr/textAppearanceLarge"
android:text="#string/default_song_name"
android:id="#+id/songNameNavhead"/>
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="#string/default_artist"
android:id="#+id/artistNavhead"/>
</LinearLayout>
And
//activity_main.xml
<?xml version="1.0" encoding="utf-8"?>
<android.support.v4.widget.DrawerLayout
android:id="#+id/drawer_layout"
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: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_main"
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>
Error
05-12 19:34:05.001 11086-11086/iskandarovlev.myitschool.ru.lyricplayer E/AndroidRuntime: FATAL EXCEPTION: main
Process: iskandarovlev.myitschool.ru.lyricplayer, PID: 11086
java.lang.NullPointerException
//MainActivity.java:302 is
//((TextView) header.findViewById(R.id.songNameNavhead)).setText(currentSong.getName());
//this line
at iskandarovlev.myitschool.ru.lyricplayer.MainActivity.prepareLayout(MainActivity.java:302)
at iskandarovlev.myitschool.ru.lyricplayer.MainActivity.access$700(MainActivity.java:48)
at iskandarovlev.myitschool.ru.lyricplayer.MainActivity$3.onServiceConnected(MainActivity.java:355)
at android.app.LoadedApk$ServiceDispatcher.doConnected(LoadedApk.java:1140)
at android.app.LoadedApk$ServiceDispatcher$RunConnection.run(LoadedApk.java:1157)
at android.os.Handler.handleCallback(Handler.java:808)
at android.os.Handler.dispatchMessage(Handler.java:103)
at android.os.Looper.loop(Looper.java:193)
at android.app.ActivityThread.main(ActivityThread.java:5542)
at java.lang.reflect.Method.invokeNative(Native Method)
at java.lang.reflect.Method.invoke(Method.java:515)
at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:841)
at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:657)
at dalvik.system.NativeStart.main(Native Method)
To successfuly find any widget in Navigation Drawer's header, you need to obtain header view first. This can be achieved by using getHeaderView() method:
View header = ((NavigationView)findViewById(R.id.navigation_view)).getHeaderView(0);
Then, having header pointing to the right ViewGroup with our widgets in it, you can use findViewById() as usual:
TextView tv = header.findViewById(R.id.songNameNavhead);
tv.setText(currentSong.getName());
Or in more compact manner:
((TextView)header.findViewById(R.id.songNameNavhead))
.setText(currentSong.getName());
private void prepareLayout() {
Log.d(LOG_TAG, "prepareLayout: Running");
((TextView) findViewById(R.id.songNameNavhead)).setText(currentSong.getName());
((TextView) findViewById(R.id.artistNavhead)).setText(currentSong.getArtist());
}
These need to use the navigationDrawer's view and then it's header, not your activity's view, so it should be
View header = navigationView.getHeaderView(0)
((TextView) navigationViewHeader.findViewById(R.id.songNameNavhead)).setText(currentSong.getName());
((TextView) navigationViewHeader.findViewById(R.id.artistNavhead)).setText(currentSong.getArtist());