Cant setId for a view programatically with AndroidStudio - java

I want to add view programatically to my parent view, my view is a RadioButton. I also want to set an Id for the view that I add in RadioGroup. But when I do this it gives me an error in: mRadioButton.setId(321);
Reports two types of problems:
Supplying the wrong type of resource identifier. For example, when calling Resources.getString(int id), you should be passing R.string.something, not R.drawable.something.
Passing the wrong constant to a method which expects one of a specific set of constants. For example, when calling View#setLayoutDirection, the parameter must be android.view.View.LAYOUT_DIRECTION_LTR or android.view.View.LAYOUT_DIRECTION_RTL.
I dont know why it gives me this error.
I found that one solution would be to create MyRadioButton class which extends RadioButton and there I could add a variable int MYID; and then add getters and setters for this view.
But this is a workaround, does anyone know the solution of this problem ?
Thanks!
EDIT:
Another workaround is to use setTag()
(I have used it for a horizontal view with ImageView's added dynamically and it helps me to detect which one was clicked)

If you are only supporting API 17 and higher,
you can call View.generateViewId
ImageButton mImageButton = new ImageButton(this);
mImageButton.setId(View.generateViewId());
Otherwise for apis lower than 17,
open your project's res/values/ folder
create an xml file called ids.xml
with the following content:
<?xml version="1.0" encoding="utf-8"?>
<resources>
<item name="imageButtonId1" type="id" />
</resources>
then in your code,
ImageButton mImageButton = new ImageButton(this);
mImageButton.setId(R.id.imageButtonId1);

Related

nullpointerexception error I know which line has error but how can I fix? [duplicate]

First of all: yes, I read all the other threads on this topic. And not only those from this site... (you see, I'm a little frustrated)
Most of them come with the advice to use android:id instead of just id in the XML file. I did.
From others, I learned, that View.findViewById works different than Activity.findViewById. I handled that, too.
In my location_layout.xml, I use:
<FrameLayout .... >
<some.package.MyCustomView ... />
<LinearLayout ... >
<TextView ...
android:id="#+id/txtLat" />
...
</LinearLayout>
</FrameLayout>
In my Activity I do:
...
setContentView( R.layout.location_layout );
and in my custom view class:
...
TextView tv = (TextView) findViewById( R.id.txtLat );
which returns null. Doing this, my Activity works fine. So maybe it's because of the Activity.findViewById and View.findViewById differences. So I stored the context passed to the customs view constructor locally and tried:
...
TextView tv = (TextView) ((Activity) context).findViewById( R.id.txtLat );
which also returned null.
Then, I changed my custom view to extend ViewGroup instead View and changed the location_layout.xml to let the TextView be a direct child of my custom view, so that the View.findViewById should work as supposed. Suprise: it didn't solve anything.
So what the heck am I doing wrong?
I'll appreciate any comments.
which returns null
Possibly because you are calling it too early. Wait until onFinishInflate(). Here is a sample project demonstrating a custom View accessing its contents.
Possibly, you are calling findViewById before calling setContentView?
If that's the case, try calling findViewById AFTER calling setContentView
Make sure you don't have multiple versions of your layout for different screen densities. I ran into this problem once when adding a new id to an existing layout but forgot to update the hdpi version. If you forget to update all versions of the layout file it will work for some screen densities but not others.
FindViewById can be null if you call the wrong super constructor in a custom view. The ID tag is part of attrs, so if you ignore attrs, you delete the ID.
This would be wrong
public CameraSurfaceView(Context context, AttributeSet attrs) {
super(context);
}
This is correct
public CameraSurfaceView(Context context, AttributeSet attrs) {
super(context,attrs);
}
Alongside the classic causes, mentioned elsewhere:
Make sure you've called setContentView() before findViewById()
Make sure that the id you want is in the view or layout you've given to setContentView()
Make sure that the id isn't accidentally duplicated in different layouts
There is one I have found for custom views in standard layouts, which goes against the documentation:
In theory you can create a custom view and add it to a layout (see here). However, I have found that in such situations, sometimes the id attribute works for all the views in the layout except the custom ones. The solution I use is:
Replace each custom view with a FrameLayout with the same layout properties as you would like the custom view to have. Give it an appropriate id, say frame_for_custom_view.
In onCreate:
setContentView(R.layout.my_layout);
FrameView fv = findViewById(R.id.frame_for_custom_layout);
MyCustomView cv = new MyCustomView(context);
fv.addView(cv);
which puts the custom view in the frame.
In my case, I had 2 activites in my project, main.xml and main2.xml. From the beginning, main2 was a copy of main, and everything worked well, until I added new TextView to main2, so the R.id.textview1 became available for the rest of app. Then I tried to fetch it by standard calling:
TextView tv = (TextView) findViewById( R.id.textview1 );
and it was always null. It turned out, that in onCreate constructor I was instantiating not main2, but the other one. I had:
setContentView(R.layout.main);
instead of
setContentView(R.layout.main2);
I noticed this after I arrived here, on the site.
#Override
protected void onStart() {
// use findViewById() here instead of in onCreate()
}
A answer for those using ExpandableListView and run into this question based on it's title.
I had this error attempting to work with TextViews in my child and group views as part of an ExpandableListView implementation.
You can use something like the following in your implementations of the getChildView() and getGroupView() methods.
if (convertView == null) {
LayoutInflater inflater = (LayoutInflater) myContext.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
convertView = inflater.inflate(R.layout.child_layout, null);
}
I found this here.
FWIW, I don't see that anyone solved this in quite the same way as I needed to. No complaints at compile time, but I was getting a null view at runtime, and calling things in the proper order. That is,
findViewById()
after
setContentView().
The problem turned out that my view is defined in content_main.xml, but in my activity_main.xml, I lacked this one statement:
<include layout="#layout/content_main" />
When I added that to activity_main.xml, no more NullPointer.
I'm pretty new to Android/Eclipse, by mistake I added the UI stuff to activity_main.xml instead of fragment_main.xml. Took me some hours to figure that out...
I had this same problem. I was using a third-party library that allows you to override their adapter for a GridView and to specify your own layout for each GridView cell.
I finally realized what was happening. Eclipse was still using the library's layout xml file for each cell in the GridView, even though it gave no indication of this. In my custom adapter, it indicated that it was using the xml resource from my own project even though at runtime, it wasn't.
So what I did was to make sure my custom xml layouts and ids were different from those still sitting in the library, cleaned the project and then it started reading the correct custom layouts that were in my project.
In short, be careful if you're overriding a third-party library's adapter and specifying your own layout xml for the adapter to use. If your layout inside your project has the same file name as that in the library, you might encounter a really difficult-to-find bug!
In my particular case, I was trying to add a footer to a ListView. The following call in onCreate() was returning null.
TextView footerView = (TextView) placesListView.findViewById(R.id.footer);
Changing this to inflate the footer view instead of finding it by ID solved this issue.
View footerView = ((LayoutInflater) getSystemService(Context.LAYOUT_INFLATER_SERVICE)).inflate(R.layout.footer_view, null, false);
Just wanted to throw my specific case in here. Might help someone down the line.
I was using the directive in my Android UI XML like this:
Parent view:
<FrameLayout
xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:tag="home_phone"
android:background="#color/colorPrimary">
...
<include
layout="#layout/retry_button"
android:visibility="gone" />
Child view (retry_button):
<com.foo.RetryButton
xmlns:android="http://schemas.android.com/apk/res/android"
android:id="#+id/retry"
android:layout_gravity="center"
android:orientation="vertical"
android:layout_width="100dp"
android:layout_height="140dp">
.findViewById(R.id.retry) would always return null. But, if I moved the ID from the child view into the include tag, it started working.
Fixed parent:
<FrameLayout
xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:tag="home_phone"
android:background="#color/colorPrimary">
...
<include
layout="#layout/retry_button"
android:id="#+id/retry"
android:visibility="gone" />
Fixed child:
<com.foo.RetryButton
xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_gravity="center"
android:orientation="vertical"
android:layout_width="100dp"
android:layout_height="140dp">
In my case, I was using ExpandableListView and I had set android:transcriptMode="normal". This was causing few children in expandable group to disappear and I used to get NULL exception when ever I used scroll the list.
For me I had two xml layouts for the same activity - one in portrait mode and one in landscape. Of course I had changed the id of an object in the landscape xml but had forgotten to make the same change in the portrait version. Make sure if you change one you do the same to the other xml or you will not get an error until you run/debug it and it can't find the id you didn't change. Oh dumb mistakes, why must you punish me so?
Set the activity content from a layout resource.
ie.,setContentView(R.layout.basicXml);
In addition of the above solutions you make sure the
tools:context=".TakeMultipleImages"
in the layout is same value in the mainfest.xml file :
android:name=".TakeMultipleImages" for the same activity element.
it is occur when use copy and paste to create new activity
I have the same problem, but I think its worth sharing with you guys.
If you have to findViewById in custom layout, for example:
public class MiniPlayerControllBar extends LinearLayout {
//code
}
you cannot get the view in constructor.
You should call findViewById after view has inflated.
Their is a method you can override onFinishInflate
My case is none like above, no solutions worked. I assume my view was too deep into layout hierarchy. I moved it one level up and it was not null anymore.
INFLATE THE LAYOUT !! (which contains the id)
In my case findViewById() returned null, because the layout in which the element was written, was not inflated...
Eg.
fragment_layout.xml
<ListView
android:id="#+id/listview">
findViewById(R.id.listview) returned null, because I had not done
inflater.inflate(R.layout.fragment_layout, ..., ...);
before it.
Hope this answer helps some of y'all.
In my case I had inflated the layout but the child views were returning null. Originally I had this:
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_history);
footerView = ((LayoutInflater) getApplicationContext().getSystemService(Context.LAYOUT_INFLATER_SERVICE)).inflate(R.layout.listview_footer, null, false);
pbSpinner = (ProgressBar) findViewById(R.id.pbListviewFooter);
tvText = (TextView) findViewById(R.id.tvListviewFooter);
...
}
However, when I changed it to the following it worked:
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_history);
footerView = ((LayoutInflater) getApplicationContext().getSystemService(Context.LAYOUT_INFLATER_SERVICE)).inflate(R.layout.listview_footer, null, false);
pbSpinner = (ProgressBar) footerView.findViewById(R.id.pbListviewFooter);
tvText = (TextView) footerView.findViewById(R.id.tvListviewFooter);
...
}
The key was to specifically reference the already inflated layout in order to get the child views. That is, to add footerView:
footerView.findViewById...
It crashed for me because one of fields in my activity id was matching with id in an other activity. I fixed it by giving a unique id.
In my loginActivity.xml password field id was "password". In my registration activity I just fixed it by giving id r_password, then it returned not null object:
password = (EditText)findViewById(R.id.r_password);
In my experience, it seems that this can also happen when your code is called after OnDestroyView (when the fragment is on the back stack.) If you are updating the UI on input from a BroadCastReceiver, you ought to check if this is the case.
findViewById also can return null if you're inside a Fragment. As described here: findViewById in Fragment
You should call getView() to return the top level View inside a Fragment. Then you can find the layout items (buttons, textviews, etc)
In my case, findViewById returned null when I moved the call from a parent object into an adapter object instantiated by the parent. After trying tricks listed here without success, I moved the findViewById back into the parent object and passed the result as a parameter during instantiation of the adapter object.
For example, I did this in parent object:
Spinner hdSpinner = (Spinner)view.findViewById(R.id.accountsSpinner);
Then I passed the hdSpinner as a parameter during creation of the adapter object:
mTransactionAdapter = new TransactionAdapter(getActivity(),
R.layout.transactions_list_item, null, from, to, 0, hdSpinner);
I was facing a similar problem when I was trying to do a custom view for a ListView.
I solved it simply by doing this:
public View getView(int i, View view, ViewGroup viewGroup) {
// Gets the inflater
LayoutInflater inflater = LayoutInflater.from(this.contexto);
// Inflates the layout
ConstraintLayout cl2 = (ConstraintLayout)
inflater.inflate(R.layout.custom_list_view, viewGroup, false);
//Insted of calling just findViewById, I call de cl2.findViewById method. cl2 is the layout I have just inflated.
TextView tv1 = (TextView)cl2.findViewById(cl2);
Ways to debug and find the issue:
Comment out all findViewById in your activity.
Comment out everything except onCreate and setContentView
Run the project and see if any layout is set
In my case, I was using activity_main.xml in both my app module and also my library module. So when I performed the above steps, instead of the layout which I designed in the library, the layout inside app module was inflated.
So I changed the activity_main.xml file name to activity_main_lib.xml.
So make sure you do not have any duplicate layout names in your whole project.
The issue for me was that I had two layouts with the same file name activity_main.xml. (The layouts were in different libraries but in the same app) The issue was solved by renaming one of them to a unique name.
For me it returned null because the given control was (programmatically) hidden. When I put a condition to call findViewByID(id) only when the control is visible, it started working again.
For me it was only null when using Evaluate Expression or the Debug Watch View of the IDE.

Activity null object reference [duplicate]

First of all: yes, I read all the other threads on this topic. And not only those from this site... (you see, I'm a little frustrated)
Most of them come with the advice to use android:id instead of just id in the XML file. I did.
From others, I learned, that View.findViewById works different than Activity.findViewById. I handled that, too.
In my location_layout.xml, I use:
<FrameLayout .... >
<some.package.MyCustomView ... />
<LinearLayout ... >
<TextView ...
android:id="#+id/txtLat" />
...
</LinearLayout>
</FrameLayout>
In my Activity I do:
...
setContentView( R.layout.location_layout );
and in my custom view class:
...
TextView tv = (TextView) findViewById( R.id.txtLat );
which returns null. Doing this, my Activity works fine. So maybe it's because of the Activity.findViewById and View.findViewById differences. So I stored the context passed to the customs view constructor locally and tried:
...
TextView tv = (TextView) ((Activity) context).findViewById( R.id.txtLat );
which also returned null.
Then, I changed my custom view to extend ViewGroup instead View and changed the location_layout.xml to let the TextView be a direct child of my custom view, so that the View.findViewById should work as supposed. Suprise: it didn't solve anything.
So what the heck am I doing wrong?
I'll appreciate any comments.
which returns null
Possibly because you are calling it too early. Wait until onFinishInflate(). Here is a sample project demonstrating a custom View accessing its contents.
Possibly, you are calling findViewById before calling setContentView?
If that's the case, try calling findViewById AFTER calling setContentView
Make sure you don't have multiple versions of your layout for different screen densities. I ran into this problem once when adding a new id to an existing layout but forgot to update the hdpi version. If you forget to update all versions of the layout file it will work for some screen densities but not others.
FindViewById can be null if you call the wrong super constructor in a custom view. The ID tag is part of attrs, so if you ignore attrs, you delete the ID.
This would be wrong
public CameraSurfaceView(Context context, AttributeSet attrs) {
super(context);
}
This is correct
public CameraSurfaceView(Context context, AttributeSet attrs) {
super(context,attrs);
}
Alongside the classic causes, mentioned elsewhere:
Make sure you've called setContentView() before findViewById()
Make sure that the id you want is in the view or layout you've given to setContentView()
Make sure that the id isn't accidentally duplicated in different layouts
There is one I have found for custom views in standard layouts, which goes against the documentation:
In theory you can create a custom view and add it to a layout (see here). However, I have found that in such situations, sometimes the id attribute works for all the views in the layout except the custom ones. The solution I use is:
Replace each custom view with a FrameLayout with the same layout properties as you would like the custom view to have. Give it an appropriate id, say frame_for_custom_view.
In onCreate:
setContentView(R.layout.my_layout);
FrameView fv = findViewById(R.id.frame_for_custom_layout);
MyCustomView cv = new MyCustomView(context);
fv.addView(cv);
which puts the custom view in the frame.
In my case, I had 2 activites in my project, main.xml and main2.xml. From the beginning, main2 was a copy of main, and everything worked well, until I added new TextView to main2, so the R.id.textview1 became available for the rest of app. Then I tried to fetch it by standard calling:
TextView tv = (TextView) findViewById( R.id.textview1 );
and it was always null. It turned out, that in onCreate constructor I was instantiating not main2, but the other one. I had:
setContentView(R.layout.main);
instead of
setContentView(R.layout.main2);
I noticed this after I arrived here, on the site.
#Override
protected void onStart() {
// use findViewById() here instead of in onCreate()
}
A answer for those using ExpandableListView and run into this question based on it's title.
I had this error attempting to work with TextViews in my child and group views as part of an ExpandableListView implementation.
You can use something like the following in your implementations of the getChildView() and getGroupView() methods.
if (convertView == null) {
LayoutInflater inflater = (LayoutInflater) myContext.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
convertView = inflater.inflate(R.layout.child_layout, null);
}
I found this here.
FWIW, I don't see that anyone solved this in quite the same way as I needed to. No complaints at compile time, but I was getting a null view at runtime, and calling things in the proper order. That is,
findViewById()
after
setContentView().
The problem turned out that my view is defined in content_main.xml, but in my activity_main.xml, I lacked this one statement:
<include layout="#layout/content_main" />
When I added that to activity_main.xml, no more NullPointer.
I'm pretty new to Android/Eclipse, by mistake I added the UI stuff to activity_main.xml instead of fragment_main.xml. Took me some hours to figure that out...
I had this same problem. I was using a third-party library that allows you to override their adapter for a GridView and to specify your own layout for each GridView cell.
I finally realized what was happening. Eclipse was still using the library's layout xml file for each cell in the GridView, even though it gave no indication of this. In my custom adapter, it indicated that it was using the xml resource from my own project even though at runtime, it wasn't.
So what I did was to make sure my custom xml layouts and ids were different from those still sitting in the library, cleaned the project and then it started reading the correct custom layouts that were in my project.
In short, be careful if you're overriding a third-party library's adapter and specifying your own layout xml for the adapter to use. If your layout inside your project has the same file name as that in the library, you might encounter a really difficult-to-find bug!
In my particular case, I was trying to add a footer to a ListView. The following call in onCreate() was returning null.
TextView footerView = (TextView) placesListView.findViewById(R.id.footer);
Changing this to inflate the footer view instead of finding it by ID solved this issue.
View footerView = ((LayoutInflater) getSystemService(Context.LAYOUT_INFLATER_SERVICE)).inflate(R.layout.footer_view, null, false);
Just wanted to throw my specific case in here. Might help someone down the line.
I was using the directive in my Android UI XML like this:
Parent view:
<FrameLayout
xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:tag="home_phone"
android:background="#color/colorPrimary">
...
<include
layout="#layout/retry_button"
android:visibility="gone" />
Child view (retry_button):
<com.foo.RetryButton
xmlns:android="http://schemas.android.com/apk/res/android"
android:id="#+id/retry"
android:layout_gravity="center"
android:orientation="vertical"
android:layout_width="100dp"
android:layout_height="140dp">
.findViewById(R.id.retry) would always return null. But, if I moved the ID from the child view into the include tag, it started working.
Fixed parent:
<FrameLayout
xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:tag="home_phone"
android:background="#color/colorPrimary">
...
<include
layout="#layout/retry_button"
android:id="#+id/retry"
android:visibility="gone" />
Fixed child:
<com.foo.RetryButton
xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_gravity="center"
android:orientation="vertical"
android:layout_width="100dp"
android:layout_height="140dp">
In my case, I was using ExpandableListView and I had set android:transcriptMode="normal". This was causing few children in expandable group to disappear and I used to get NULL exception when ever I used scroll the list.
For me I had two xml layouts for the same activity - one in portrait mode and one in landscape. Of course I had changed the id of an object in the landscape xml but had forgotten to make the same change in the portrait version. Make sure if you change one you do the same to the other xml or you will not get an error until you run/debug it and it can't find the id you didn't change. Oh dumb mistakes, why must you punish me so?
Set the activity content from a layout resource.
ie.,setContentView(R.layout.basicXml);
In addition of the above solutions you make sure the
tools:context=".TakeMultipleImages"
in the layout is same value in the mainfest.xml file :
android:name=".TakeMultipleImages" for the same activity element.
it is occur when use copy and paste to create new activity
I have the same problem, but I think its worth sharing with you guys.
If you have to findViewById in custom layout, for example:
public class MiniPlayerControllBar extends LinearLayout {
//code
}
you cannot get the view in constructor.
You should call findViewById after view has inflated.
Their is a method you can override onFinishInflate
My case is none like above, no solutions worked. I assume my view was too deep into layout hierarchy. I moved it one level up and it was not null anymore.
INFLATE THE LAYOUT !! (which contains the id)
In my case findViewById() returned null, because the layout in which the element was written, was not inflated...
Eg.
fragment_layout.xml
<ListView
android:id="#+id/listview">
findViewById(R.id.listview) returned null, because I had not done
inflater.inflate(R.layout.fragment_layout, ..., ...);
before it.
Hope this answer helps some of y'all.
In my case I had inflated the layout but the child views were returning null. Originally I had this:
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_history);
footerView = ((LayoutInflater) getApplicationContext().getSystemService(Context.LAYOUT_INFLATER_SERVICE)).inflate(R.layout.listview_footer, null, false);
pbSpinner = (ProgressBar) findViewById(R.id.pbListviewFooter);
tvText = (TextView) findViewById(R.id.tvListviewFooter);
...
}
However, when I changed it to the following it worked:
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_history);
footerView = ((LayoutInflater) getApplicationContext().getSystemService(Context.LAYOUT_INFLATER_SERVICE)).inflate(R.layout.listview_footer, null, false);
pbSpinner = (ProgressBar) footerView.findViewById(R.id.pbListviewFooter);
tvText = (TextView) footerView.findViewById(R.id.tvListviewFooter);
...
}
The key was to specifically reference the already inflated layout in order to get the child views. That is, to add footerView:
footerView.findViewById...
It crashed for me because one of fields in my activity id was matching with id in an other activity. I fixed it by giving a unique id.
In my loginActivity.xml password field id was "password". In my registration activity I just fixed it by giving id r_password, then it returned not null object:
password = (EditText)findViewById(R.id.r_password);
In my experience, it seems that this can also happen when your code is called after OnDestroyView (when the fragment is on the back stack.) If you are updating the UI on input from a BroadCastReceiver, you ought to check if this is the case.
findViewById also can return null if you're inside a Fragment. As described here: findViewById in Fragment
You should call getView() to return the top level View inside a Fragment. Then you can find the layout items (buttons, textviews, etc)
In my case, findViewById returned null when I moved the call from a parent object into an adapter object instantiated by the parent. After trying tricks listed here without success, I moved the findViewById back into the parent object and passed the result as a parameter during instantiation of the adapter object.
For example, I did this in parent object:
Spinner hdSpinner = (Spinner)view.findViewById(R.id.accountsSpinner);
Then I passed the hdSpinner as a parameter during creation of the adapter object:
mTransactionAdapter = new TransactionAdapter(getActivity(),
R.layout.transactions_list_item, null, from, to, 0, hdSpinner);
I was facing a similar problem when I was trying to do a custom view for a ListView.
I solved it simply by doing this:
public View getView(int i, View view, ViewGroup viewGroup) {
// Gets the inflater
LayoutInflater inflater = LayoutInflater.from(this.contexto);
// Inflates the layout
ConstraintLayout cl2 = (ConstraintLayout)
inflater.inflate(R.layout.custom_list_view, viewGroup, false);
//Insted of calling just findViewById, I call de cl2.findViewById method. cl2 is the layout I have just inflated.
TextView tv1 = (TextView)cl2.findViewById(cl2);
Ways to debug and find the issue:
Comment out all findViewById in your activity.
Comment out everything except onCreate and setContentView
Run the project and see if any layout is set
In my case, I was using activity_main.xml in both my app module and also my library module. So when I performed the above steps, instead of the layout which I designed in the library, the layout inside app module was inflated.
So I changed the activity_main.xml file name to activity_main_lib.xml.
So make sure you do not have any duplicate layout names in your whole project.
The issue for me was that I had two layouts with the same file name activity_main.xml. (The layouts were in different libraries but in the same app) The issue was solved by renaming one of them to a unique name.
For me it returned null because the given control was (programmatically) hidden. When I put a condition to call findViewByID(id) only when the control is visible, it started working again.
For me it was only null when using Evaluate Expression or the Debug Watch View of the IDE.

Attempt to invoke 'void android.widget.ListView.setOnItemClickListener on a null object reference [duplicate]

First of all: yes, I read all the other threads on this topic. And not only those from this site... (you see, I'm a little frustrated)
Most of them come with the advice to use android:id instead of just id in the XML file. I did.
From others, I learned, that View.findViewById works different than Activity.findViewById. I handled that, too.
In my location_layout.xml, I use:
<FrameLayout .... >
<some.package.MyCustomView ... />
<LinearLayout ... >
<TextView ...
android:id="#+id/txtLat" />
...
</LinearLayout>
</FrameLayout>
In my Activity I do:
...
setContentView( R.layout.location_layout );
and in my custom view class:
...
TextView tv = (TextView) findViewById( R.id.txtLat );
which returns null. Doing this, my Activity works fine. So maybe it's because of the Activity.findViewById and View.findViewById differences. So I stored the context passed to the customs view constructor locally and tried:
...
TextView tv = (TextView) ((Activity) context).findViewById( R.id.txtLat );
which also returned null.
Then, I changed my custom view to extend ViewGroup instead View and changed the location_layout.xml to let the TextView be a direct child of my custom view, so that the View.findViewById should work as supposed. Suprise: it didn't solve anything.
So what the heck am I doing wrong?
I'll appreciate any comments.
which returns null
Possibly because you are calling it too early. Wait until onFinishInflate(). Here is a sample project demonstrating a custom View accessing its contents.
Possibly, you are calling findViewById before calling setContentView?
If that's the case, try calling findViewById AFTER calling setContentView
Make sure you don't have multiple versions of your layout for different screen densities. I ran into this problem once when adding a new id to an existing layout but forgot to update the hdpi version. If you forget to update all versions of the layout file it will work for some screen densities but not others.
FindViewById can be null if you call the wrong super constructor in a custom view. The ID tag is part of attrs, so if you ignore attrs, you delete the ID.
This would be wrong
public CameraSurfaceView(Context context, AttributeSet attrs) {
super(context);
}
This is correct
public CameraSurfaceView(Context context, AttributeSet attrs) {
super(context,attrs);
}
Alongside the classic causes, mentioned elsewhere:
Make sure you've called setContentView() before findViewById()
Make sure that the id you want is in the view or layout you've given to setContentView()
Make sure that the id isn't accidentally duplicated in different layouts
There is one I have found for custom views in standard layouts, which goes against the documentation:
In theory you can create a custom view and add it to a layout (see here). However, I have found that in such situations, sometimes the id attribute works for all the views in the layout except the custom ones. The solution I use is:
Replace each custom view with a FrameLayout with the same layout properties as you would like the custom view to have. Give it an appropriate id, say frame_for_custom_view.
In onCreate:
setContentView(R.layout.my_layout);
FrameView fv = findViewById(R.id.frame_for_custom_layout);
MyCustomView cv = new MyCustomView(context);
fv.addView(cv);
which puts the custom view in the frame.
In my case, I had 2 activites in my project, main.xml and main2.xml. From the beginning, main2 was a copy of main, and everything worked well, until I added new TextView to main2, so the R.id.textview1 became available for the rest of app. Then I tried to fetch it by standard calling:
TextView tv = (TextView) findViewById( R.id.textview1 );
and it was always null. It turned out, that in onCreate constructor I was instantiating not main2, but the other one. I had:
setContentView(R.layout.main);
instead of
setContentView(R.layout.main2);
I noticed this after I arrived here, on the site.
#Override
protected void onStart() {
// use findViewById() here instead of in onCreate()
}
A answer for those using ExpandableListView and run into this question based on it's title.
I had this error attempting to work with TextViews in my child and group views as part of an ExpandableListView implementation.
You can use something like the following in your implementations of the getChildView() and getGroupView() methods.
if (convertView == null) {
LayoutInflater inflater = (LayoutInflater) myContext.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
convertView = inflater.inflate(R.layout.child_layout, null);
}
I found this here.
FWIW, I don't see that anyone solved this in quite the same way as I needed to. No complaints at compile time, but I was getting a null view at runtime, and calling things in the proper order. That is,
findViewById()
after
setContentView().
The problem turned out that my view is defined in content_main.xml, but in my activity_main.xml, I lacked this one statement:
<include layout="#layout/content_main" />
When I added that to activity_main.xml, no more NullPointer.
I'm pretty new to Android/Eclipse, by mistake I added the UI stuff to activity_main.xml instead of fragment_main.xml. Took me some hours to figure that out...
I had this same problem. I was using a third-party library that allows you to override their adapter for a GridView and to specify your own layout for each GridView cell.
I finally realized what was happening. Eclipse was still using the library's layout xml file for each cell in the GridView, even though it gave no indication of this. In my custom adapter, it indicated that it was using the xml resource from my own project even though at runtime, it wasn't.
So what I did was to make sure my custom xml layouts and ids were different from those still sitting in the library, cleaned the project and then it started reading the correct custom layouts that were in my project.
In short, be careful if you're overriding a third-party library's adapter and specifying your own layout xml for the adapter to use. If your layout inside your project has the same file name as that in the library, you might encounter a really difficult-to-find bug!
In my particular case, I was trying to add a footer to a ListView. The following call in onCreate() was returning null.
TextView footerView = (TextView) placesListView.findViewById(R.id.footer);
Changing this to inflate the footer view instead of finding it by ID solved this issue.
View footerView = ((LayoutInflater) getSystemService(Context.LAYOUT_INFLATER_SERVICE)).inflate(R.layout.footer_view, null, false);
Just wanted to throw my specific case in here. Might help someone down the line.
I was using the directive in my Android UI XML like this:
Parent view:
<FrameLayout
xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:tag="home_phone"
android:background="#color/colorPrimary">
...
<include
layout="#layout/retry_button"
android:visibility="gone" />
Child view (retry_button):
<com.foo.RetryButton
xmlns:android="http://schemas.android.com/apk/res/android"
android:id="#+id/retry"
android:layout_gravity="center"
android:orientation="vertical"
android:layout_width="100dp"
android:layout_height="140dp">
.findViewById(R.id.retry) would always return null. But, if I moved the ID from the child view into the include tag, it started working.
Fixed parent:
<FrameLayout
xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:tag="home_phone"
android:background="#color/colorPrimary">
...
<include
layout="#layout/retry_button"
android:id="#+id/retry"
android:visibility="gone" />
Fixed child:
<com.foo.RetryButton
xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_gravity="center"
android:orientation="vertical"
android:layout_width="100dp"
android:layout_height="140dp">
In my case, I was using ExpandableListView and I had set android:transcriptMode="normal". This was causing few children in expandable group to disappear and I used to get NULL exception when ever I used scroll the list.
For me I had two xml layouts for the same activity - one in portrait mode and one in landscape. Of course I had changed the id of an object in the landscape xml but had forgotten to make the same change in the portrait version. Make sure if you change one you do the same to the other xml or you will not get an error until you run/debug it and it can't find the id you didn't change. Oh dumb mistakes, why must you punish me so?
Set the activity content from a layout resource.
ie.,setContentView(R.layout.basicXml);
In addition of the above solutions you make sure the
tools:context=".TakeMultipleImages"
in the layout is same value in the mainfest.xml file :
android:name=".TakeMultipleImages" for the same activity element.
it is occur when use copy and paste to create new activity
I have the same problem, but I think its worth sharing with you guys.
If you have to findViewById in custom layout, for example:
public class MiniPlayerControllBar extends LinearLayout {
//code
}
you cannot get the view in constructor.
You should call findViewById after view has inflated.
Their is a method you can override onFinishInflate
My case is none like above, no solutions worked. I assume my view was too deep into layout hierarchy. I moved it one level up and it was not null anymore.
INFLATE THE LAYOUT !! (which contains the id)
In my case findViewById() returned null, because the layout in which the element was written, was not inflated...
Eg.
fragment_layout.xml
<ListView
android:id="#+id/listview">
findViewById(R.id.listview) returned null, because I had not done
inflater.inflate(R.layout.fragment_layout, ..., ...);
before it.
Hope this answer helps some of y'all.
In my case I had inflated the layout but the child views were returning null. Originally I had this:
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_history);
footerView = ((LayoutInflater) getApplicationContext().getSystemService(Context.LAYOUT_INFLATER_SERVICE)).inflate(R.layout.listview_footer, null, false);
pbSpinner = (ProgressBar) findViewById(R.id.pbListviewFooter);
tvText = (TextView) findViewById(R.id.tvListviewFooter);
...
}
However, when I changed it to the following it worked:
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_history);
footerView = ((LayoutInflater) getApplicationContext().getSystemService(Context.LAYOUT_INFLATER_SERVICE)).inflate(R.layout.listview_footer, null, false);
pbSpinner = (ProgressBar) footerView.findViewById(R.id.pbListviewFooter);
tvText = (TextView) footerView.findViewById(R.id.tvListviewFooter);
...
}
The key was to specifically reference the already inflated layout in order to get the child views. That is, to add footerView:
footerView.findViewById...
It crashed for me because one of fields in my activity id was matching with id in an other activity. I fixed it by giving a unique id.
In my loginActivity.xml password field id was "password". In my registration activity I just fixed it by giving id r_password, then it returned not null object:
password = (EditText)findViewById(R.id.r_password);
In my experience, it seems that this can also happen when your code is called after OnDestroyView (when the fragment is on the back stack.) If you are updating the UI on input from a BroadCastReceiver, you ought to check if this is the case.
findViewById also can return null if you're inside a Fragment. As described here: findViewById in Fragment
You should call getView() to return the top level View inside a Fragment. Then you can find the layout items (buttons, textviews, etc)
In my case, findViewById returned null when I moved the call from a parent object into an adapter object instantiated by the parent. After trying tricks listed here without success, I moved the findViewById back into the parent object and passed the result as a parameter during instantiation of the adapter object.
For example, I did this in parent object:
Spinner hdSpinner = (Spinner)view.findViewById(R.id.accountsSpinner);
Then I passed the hdSpinner as a parameter during creation of the adapter object:
mTransactionAdapter = new TransactionAdapter(getActivity(),
R.layout.transactions_list_item, null, from, to, 0, hdSpinner);
I was facing a similar problem when I was trying to do a custom view for a ListView.
I solved it simply by doing this:
public View getView(int i, View view, ViewGroup viewGroup) {
// Gets the inflater
LayoutInflater inflater = LayoutInflater.from(this.contexto);
// Inflates the layout
ConstraintLayout cl2 = (ConstraintLayout)
inflater.inflate(R.layout.custom_list_view, viewGroup, false);
//Insted of calling just findViewById, I call de cl2.findViewById method. cl2 is the layout I have just inflated.
TextView tv1 = (TextView)cl2.findViewById(cl2);
Ways to debug and find the issue:
Comment out all findViewById in your activity.
Comment out everything except onCreate and setContentView
Run the project and see if any layout is set
In my case, I was using activity_main.xml in both my app module and also my library module. So when I performed the above steps, instead of the layout which I designed in the library, the layout inside app module was inflated.
So I changed the activity_main.xml file name to activity_main_lib.xml.
So make sure you do not have any duplicate layout names in your whole project.
The issue for me was that I had two layouts with the same file name activity_main.xml. (The layouts were in different libraries but in the same app) The issue was solved by renaming one of them to a unique name.
For me it returned null because the given control was (programmatically) hidden. When I put a condition to call findViewByID(id) only when the control is visible, it started working again.
For me it was only null when using Evaluate Expression or the Debug Watch View of the IDE.

How do you add your eclipse view plugin to a specific pre-existing JDT views category?

I wrote a new eclipse view plugin and when you select Window -> Show View --> Other
you can see it in its own folder/category (the view defines a new category)
Is it possible to code the plugin.xml of this view so that when the user clicks on Show View
the view is shown in one of the preexisting JDT folders/categories, like "Java" or "Java Browsing"?
if so, assuming i just need to specify the preexisting category's id
in my view's 'category' attribute, where can one find the list of JDT view categories and their associated ID's?
More Info:
my plugin.xml contains this:
<category
name="MyCat"
id="com.mine">
</category>
which specifies in which category the view will show. so, when deployed, the user can add my new view by: Window - Show View - Other
and there, among all pre-existing categories/folders, the user will see my category
"MyCat" and when opened, it contains my newly developed/contributed view.
my back to my question... i don't want to create a new category, but instead, i want my
new view to show in the existing Java category. can i do that and if so how?
i assume that, if it is possible to do, i would probably need to 1) not use the 'name' attribute in my 'category'
element, and 2) the 'id' attribute should contain the id of the Java category.
(which is what?).
so perhaps there is a place where all pre-existing jdt view categories
are defined, but i couldn't find it....
Define a perspective extension with your views. Here is an example with the debug perspective
org.eclipse.ui.perspectiveExtensions
The category for Java is org.eclipse.jdt.ui.java

Logcat error onclicklistener android

I get an error like this in logcat when i try to run my script. I compared it and it is the onClickListener. Any suggestions to fix this problem? Still a beginner.
The problem exists here:
View splashscreen = (View) findViewById(R.layout.splash);
splashscreen.setOnClickListener(this);
You are getting an exception because splashscreen is null, and calling setOnClickListener() on a null pointer is not allowed. The reason that pointer is null is because you need to obtain a reference to the view from your XML using a proper ID. Your splash.xml file located in res/layout is being loaded as the content view for the Activity, but you should have a proper R.id value associated with that particular view.
In splash.xml, the View you declare for this purpose should have an android:id="#+id/something" attribute in it's XML declaration (I picked "something" out of the air, this identifier can be whatever you want). You would then call:
//Hint: You don't have to cast the result if the pointer is a plain vanilla View
View splashscreen = findViewById(R.id.something);
splashscreen.setOnClickListener(this);
Then you will get a valid reference to the view and your set method will not fail.
HTH
As Devunwired said, I think maybe you wrong about layout and id.
See http://developer.android.com/reference/android/view/View.html
Yes, Devunwired is right. You must have to give the Resource id to the Perticular view. Instead of that you are going to give the reference of the Layout file name as "splash.xml".
Also try to make the Id name different from the layout file name. Its not and error but sometimes happend that make possible to arrise problem to understand and to give the resource id to different reference.
Thanks.
Instead of using Thread, you can try Handler:
Handler handler = new Handler();
handler.post(new Runnable(){
public void run(){
//TODO
}
});
By the way, posting more exception stack traces would be more helpful.

Categories

Resources