Eugene
Eugene

Reputation: 60184

IllegalStateException on LinearLayout.addView(View view) method call

can somebody tell me why this happens, please read below. I have my own class Data which extends Button. In my Activity's class I have a List which is appending with new Data object on each button click. I want to keep created objects of class Data on the screen after configuration changes, namely orientation change. So I've overrided onSaveInstanceState() and using it to restore my data in onCreate() method. In mentioned method I'm saving every Data object from the list of objects. In onCreate() method I'm trying to restore my data like this:

public void onCreate(Bundle savedInstanceState) {  
        super.onCreate(savedInstanceState);  
        setContentView(R.layout.main);  

        button = (Button) findViewById(R.id.Button01);  
        layout = (LinearLayout) findViewById(R.id.MyLayout);  
        dataList = new ArrayList<Data>();  

        if(savedInstanceState != null) {  
            int numberOfObjects = savedInstanceState.getInt("Number of objects");  
            for (int i = 1; i < numberOfObjects; i++) {  
                Data tmp = (Data)savedInstanceState.getSerializable("Button name " + i);  
                if (tmp != null) {  
                    dataList.add(tmp);  
                }  
                if (dataList.size() != 0) {  
// I'm using one of the lines at a time, uncommented here just for example:  
                    layout.addView((Data)dataList.get(i-1)); // IllegalStateException happens here with advice to invoke removeView() method. I tried to call it on the method beginning, but no success.  
                    layout.addView(new Data(getApplicationContext())); // This one is perfectly fine  
                }  
            }  
        }  

So in first case I'm getting IllegalStateException but it is working great for the second one. I don't understand the difference.

Just in case, here is my onSaveInstanceState() method:

@Override  
    protected void onSaveInstanceState(Bundle outState) {  
        super.onSaveInstanceState(outState);  
        Log.d("Dev", "onSaveInstanceState()");  
        outState.putInt("Number of objects", dataList.size());  
        for (Data object : dataList) {  
            outState.putSerializable("Button name " + object.getNumber() , object);  
        }  
    }  

And my Data class, but nothing special:

package as.as.as;  

import java.io.Serializable;  

import android.content.Context;  
import android.widget.Button;  

public class Data extends Button implements Serializable {  
    public static int counter;  
    public int number;  

    public Data(Context context) {  
        super(context);  
        counter++;  
        this.number = counter;   
        this.setText("Button number " + Integer.toString(number));  
    }  

    public String getNumber() {  
        return Integer.toString(number);  
    }  

}  

Upvotes: 0

Views: 1948

Answers (2)

Peter Knego
Peter Knego

Reputation: 80340

  1. The original problem:

    The IllegalStateException is in this case thrown because the child View (in your case Button/Data) already has a parent (a ViewGroup or in your case LinearLayout). This means that you can add Views to View group only once. If you want to add them to a new ViewGroup, then you must first call .removeView() on the original ViewGroup.

    Since you are saving Data objects to bundle I assume that you are calling .addView(data) multiple times without calling .removeView(data) in between.

  2. Additional problem:

    You are saving Data to a Bundle. Data extends Button which is not Serializable, so you should not mark Data as Serializable.

    Why are you saving the Buttons to a bundle in the first place?

Upvotes: 4

Falmarri
Falmarri

Reputation: 48577

The only thing I can say is don't save widgets or anything that requires a context like that. When the orientation changes, the activity is destroyed and created with a new context. That's why you see your error. What do these buttons do? Why are there so many and why are you subclassing buttons? And why are they called Data? Usually Data isn't associated with a button.

Upvotes: 0

Related Questions