I am getting an object of RadioButton by using findViewById() and then setting an `onclicklistener' for it.The code goes like :
final EditText editTextView = (EditText)findViewById(2001);
RadioButton rb = (RadioButton) findViewById(R.id.radio3);
rb.setOnClickListener(new View.OnClickListener() {
public void onClick(View v) {
LinearLayout linearLayout = (LinearLayout) findViewById(R.id.editTextGroupLayout);
LayoutParams params = new LayoutParams(LayoutParams.MATCH_PARENT,LayoutParams.MATCH_PARENT);
editTextView.setLayoutParams(params);
editTextView.setInputType(InputType.TYPE_NUMBER_FLAG_DECIMAL| InputType.TYPE_NUMBER_FLAG_SIGNED);
editTextView.setId(2001);
linearLayout.addView(editTextView);
}
});
When i click Once on the radiobutton it works fine.But when i click it twice,it generates
java.lang.IllegalStateException: The specified child already has a parent. You must call removeView() on the child's parent first.
By clicking it twice why this exception occurs?
What i tried
I tried to remove the line final EditText editTextView = (EditText)findViewById(2001);
and add this line inside the onClick(),EditText editTextView = (EditText)findViewById(2001);.But by doing this it doesn't get executed even once.It shows exception too.
It is beacouse you got only one instance of edittext which alerady has a parent after first click. Try to remove view from parent and than place it again.
Or maybe try to show/hide it?
You should propably do something like this.
linearLayout.removeAllViews(); or linearLayout.removeView(editTextView);
...
linearLayout.addView(editTextView);
Related
This seems to have been asked in stackoverflow a bit before with no convincing answers for most questions. anyways, i attempt again.
I have an Android App where am displaying a list where each row has an Edittext and Button component as seen below
The Edittext is non-editable when the view appears. I do this with the code below:
private void setNameAsEditable (View rowView, boolean setToEditable) {
EditText textView = (EditText) rowView
.findViewById(R.id.edittext_name);
textView.setFocusableInTouchMode(setToEditable);
textView.setFocusable(setToEditable);
ImageButton button = (ImageButton) rowView
.findViewById(R.id.button_save_name);
if ( setToEditable ) {
button.setVisibility (View.VISIBLE); // nullpointerexception here
} else {
button.setVisibility (View.GONE);
}
When I long-press, and setToEditable is true, it throws nullpointerexception in the line indicated above. it doesn't seem to find the button component. However, 'button.setVisibility (View.GONE);' is executed when setToEditable is false without any issue.
Can someone please help?
rowView appears to be your EditText while you actually want the parent view that has the button inside of it. If you call findViewById and the id doesn't exist inside of that view, it will return null.
I think issue is initialization of view control. You should initialize EditText & ImageButton at the top.
EditText textView;
ImageButton button ;
...
...
...
EditText textView = (EditText) rowView.findViewById(R.id.edittext_name);
ImageButton button = (ImageButton) rowView.findViewById(R.id.button_save_name);
And next thing is try to write your code in try & catch block so you get exact idea what is wrong and where is bug.
I'm getting
E/AndroidRuntime(855): Caused by: java.lang.IllegalStateException:
The specified child already has a parent. You must call removeView()
on the child's parent first.
The code I'm running, the error happens on linearLayout.addView(view);
view = getFieldControl(field);
linearLayout.addView(view);
Where getFieldControl looks like this(simplified):
private android.view.View getFieldControl(ControlTemplate control)
{
View view =null;
view = (EditText)findViewById(R.id.edit_message);
((EditText) view).setHint(control.getName());
((EditText) view).setText(control.getValue());
return view;
}
I don't understand what the views parent could be, where should I remove it from?
Create your EditText programmatically as below
private android.widget.EditText getFieldControl(ControlTemplate control)
{
EditText edittext = new EditText(this);
edittext.setHint(control.getName());
edittext.setText(control.getValue());
return edittext;
}
Note : If the EditText is in XML which is set as Content View modify the code as below by removing the line linearLayout.addView(view); because already the EditText is added in the layout through XML.
EditText edittext = (EditText) findViewById(R.id.edit_message);;
getFieldControl(edittext, field);
private void getFieldControl(EditText edittext, ControlTemplate control)
{
edittext.setHint(control.getName());
edittext.setText(control.getValue());
}
If you call the getFieldControl(field) method more than once, you are trying to get the EditText of R.id.edit_message from XML and adding that more than once to the layout. Hence it's giving this error. Make sure that you add this EditText only once to any of the layouts.
Your EditText R.id.edit_message must be in an .xml file or say layout, that layout is the parent of the EditText.
Create a dynamic EditText instead.
So I generated some button. The numbers it depends on the user (when clicked a button, create a new one).
This is how I made it:
RelativeLayout layout = (RelativeLayout) findViewById(R.id.layoutcprompt);
RelativeLayout.LayoutParams OBJ = new RelativeLayout.LayoutParams (140,80);
if ((commandsi%6)==0) {adjust=adjust+86; commandsi=1;}
OBJ.leftMargin =(140*(commandsi-1))+10;
OBJ.topMargin =250+adjust;
Button command = new Button(this);
command.setLayoutParams(OBJ);
command.setId(ID);
command.setText(edittxt.getText().toString());
edittxt.setText("");
command.setBackgroundResource(R.drawable.costum_button);
command.setTextColor(Color.WHITE);
command.setTextSize(14);
layout.addView(command);
command.setOnClickListener(new View.OnClickListener() {
public void onClick(View view) {
Button b = (Button)view;
scommand=b.getText().toString();
}
});
command.setVisibility(View.VISIBLE);
I want to remove/delete them, but I don't know how.... I gave them a unique id, but I still dunno how can I remove them :/
I cannot comment another post, but using
command = new Button(this)
might involve an implicit memory Leak on this! (which can be the Activity). Rather use Context object. Or remove the button at least.
Then because you have the parent of your Button. Just remove it:
ViewGroup layout = (ViewGroup) findViewById(R.id.layoutcprompt);
View command = layout.findViewById(ID);
layout.removeView(command);
Make command a global variable. Then you can access it later, and call command.setVisibility(View.GONE);
So at the top, of your class file, you would declare the global variable:
Button command;
Then remove the redefinition later on and instead assign to the global variable:
command = new Button(this);
Then when you want to hide it, call:
command.setVisibility(View.GONE);
Try using the documentation, 5 seconds of research can lead you to the RemoveView method.
layout.removeView(command);
Update
If you have a null pointer exception on this line, means your layout is null, not your command. Make your layout variable global for that class.
Also be sure to keep different variables for each of your created buttons. If you have a global variable, and create 10 buttons using the same variable you will only have a reference to the last one created. If you explain exactly when you want to remove the button we might be able to help you further.
As an example, if you want to remove the button when the user clicks on it you can change your clickListener:
command.setOnClickListener(new View.OnClickListener() {
public void onClick(View view) {
Button b = (Button)view;
scommand=b.getText().toString();
layout.removeView(view);
}
});
One other implementation that may help others who view this thread is that you can consider removing all the child elements in the parent layout. Once you get the view's parent (which I assume is a layout container),you can remove all the child elements.
command.setOnClickListener(new View.OnClickListener() {
public void onClick(View view) {
ViewGroup vg = (ViewGroup)view.getParent();
vg.removeAllViews();
}
});
You can also do it like this for security purpose:
ViewGroup layout = (ViewGroup) command.getParent();
if(null!=layout) //for safety only as you are doing onClick
layout.removeView(command);
You can also use this snipper
For Adding the Button
LinearLayout dynamicview = (LinearLayout)findViewById(R.id.buttonlayout);
LinearLayout.LayoutParams lprams = new LinearLayout.LayoutParams( LinearLayout.LayoutParams.WRAP_CONTENT,
LinearLayout.LayoutParams.WRAP_CONTENT);
Button btn = new Button(this);
btn.setId(count);
final int id_ = btn.getId();
btn.setText("Capture Image" + id_);
btn.setTextColor(Color.WHITE);
btn.setBackgroundColor(Color.rgb(70, 80, 90));
dynamicview.addView(btn, lprams);
btn = ((Button) findViewById(id_));
btn.setOnClickListener(this);
For removing the button
ViewGroup layout = (ViewGroup) findViewById(R.id.buttonlayout);
View command = layout.findViewById(count);
layout.removeView(command);
In my app, i am loading a layout dynamically with text views ,on a button's onclick event. when i click the button for the first time , i got my layout with text views. when i click it again ,it should display the layout again. but its showing error. my code is
private OnClickListener some_name = new OnClickListener(){
public void onClick(View v) {
LinearLayout my_list_layout = (LinearLayout)findViewById(R.id.my_list_layout);
my_list_layout.setOrientation(1);
my_list_layout.setId(50);
my_textview = new TextView[length];
for(int i=0; i<length ; i++)
{
my_textview[i]= new TextView(getApplicationContext());
my_textview[i].setText("sample text");
my_textview[i].setId(i);
if(i==0)
{
RelativeLayout.LayoutParams my_textviewparams = new RelativeLayout.LayoutParams(LinearLayout.LayoutParams.FILL_PARENT,LinearLayout.LayoutParams.WRAP_CONTENT);
my_textviewparams.addRule(RelativeLayout.ALIGN_PARENT_TOP,my_list_layout.getId());
my_list_layout.addView(my_textview[i],my_textviewparams);
}
else
{
RelativeLayout.LayoutParams my_textviewparams = new RelativeLayout.LayoutParams(LinearLayout.LayoutParams.FILL_PARENT,LinearLayout.LayoutParams.WRAP_CONTENT);
my_textviewparams.addRule(RelativeLayout.BELOW,my_textview[i-1].getId());
my_list_layout.addView(my_textview[i],my_textviewparams);
}
}
}
and my error log is
quick response is needed. anyone tell me, what is my wrong in coding, or what changes i have to do for my requirement?
You should remove this line:
my_list_layout.setId(50);
because once you set the id to 50, and again when you click the Button, the LinearLayout is null because you call findViewById(R.id. my_list_layout); its id has been changed to 50.
Cheers!
I got the answer.Here while i was doing first time the btn click, the child view will added to my parent view dynamically.
During the second click the i removed previously added child from my parent view and added the new child. So this will updates my content and displays clearly every time when I click the btn.
I got error in removing the views from my child, now I clear the error by assigning some variables for identifying btn click, whether user clicks it for first time or not. thank you all for your time here and for your answers.
I have a LinearLayout comprising of a few Buttons and I add this to my activity in the onCreate(..) method with setContentView(R.layout.myscreen). No surprises so far.
How do I get a reference to an iterator to these buttons? I'd like to add listeners to them but I'd rather not directly reference the Button's using their android:id.
Similar questions have been asked here and here but they don't quite answer my question.
Try something like this provide an id root_layout in xml to LinearLayout
LinearLayout mLayout = (LinearLayout) findViewById(R.id.root_layout);
for(int i = 0; i < mLayout.getChildCount(); i++)
{
Button mButton = (Button) mLayout.getChildAt(i);
mButton.setOnClickListener(this);
}
Where mLayout is object of you Linear Layout and Your activity must implements OnClickListener and here goes general listener
#Override
public void onClick(View v)
{
Button mButton = (Button)v;
String buttonText = mButton.getText().toString();
}
NOTE: For this to work properly you Linear Layout must only contains button no other views
You should take a look at my answer here.
In short. I'd assign the buttons a listener by setting the onClick attribute in the XML layout on each Button.
Inside of your Activity you'll need a public method like the one below which basically is what you want to do in your listener.
public void myFancyMethod(View v) {
// do something interesting here
}
If you want to go for accessing other elements you may try following syntax:
<ElementClass> <referencevariable> = (<ElementClass>) findViewById(R.id.<id_of_the_element>);
For Example:
TextView textView= (TextView) findViewById(R.id.t1); //I used t1 to refer my textview in the Layout.
This might work.
Then you can use these views with their inbuilt methods to perform as many as work you want.