My app contains 25 edittexts. I am getting this 25 edittexts with the help of adapter class by giving count=25 and fitting in gridView by gridView.setAdapter(new TextAdapter(this)); in the activity class. So, the edittexts are dynamically generated. But the thing is I am unable to set the initial values in the edittexts. This is because the edittext objects are unavailable to set the values.
Suppose if I don't set any initial values in the edittexts and continue with my app. The same problem repeats while setting the values back in the edittexts which are entered in previous mode after changing the orientation. Because change in orientation creates new activity. Even I tried android:configChanges="orientation|keyboardHidden", but no use while I am setting the values back in the **onConfigurationChanged()**. Because I am setting the setContentView(); in the onConfigurationChanged() as I need the respective view, but still the edittext objects are unavailable to set their values.
Is there any solution to set back the values? If not, I am thinking(Might be completely wrong way, but as a newbie please go easy) to move the onCreate() method content to Application class. So the initial part goes to Application class including the creation of edittexts. and getting that edittext objects in the onCreate() method to set the values. Is it possible? Please suggest. Code snippet would be appreciated.
You will need to modify TextAdapter. Store the initial values in a String array, with the position of the String array element aligned to the position of the EditText in your GridView.
Pseudo-code (untested):
public class TextAdapter extends BaseAdapter {
String [] initial_value = {"Initial Value 1", "Initial Value 2", "Initial Value 3", ..., };
public View getView(int pos, View view, ViewGroup viewGroup) {
if (view == null) {
LayoutInflater inflater = (LayoutInflater) this.context.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
view = inflater.inflate(R.layout.edit_text_container, null);
}
(EditText) edtTemp = (EditText) view.findViewById(R.id.edit_text_id);
edtTemp.setText(initial_value[pos]);
}
}
Related
I am adding a layout on a Button click that layout contains a TextView and the 2 Spinners name spGrades and spMarks.
User can add multiple layout. So all I want is to get the value of Spinners on the TextView click . well I am getting of values of Spinner but I am facing following problems.
In Case1: Suppose there is just one layout added by the user let say
Student1MarksLayout then on the click of the TextView I am getting
the values of Spinners.
In Case 2: Suppose now user has added and other layout let say
Student2MarksLayout with same 2 spinners and a TextView . Now in
this case on the click listener of TextView I am getting the value
of spinners which are currently added. even though i click on the
TextView of the Student1MarksLayout. It brings the values of
Student2MarksLayout values.
Question:
So in fact I want to get the values of spinners differently from the
same view group in which the TextView click has been originated by the
user.
Please help me and any suggestion about this on how to maintain this .
On the function that creates the layout, add to final variables that hold the 2 Spinners. Then create the onClick function, and reference these 2 final variables. I have written a quick example (in a bit of shorthand)
void createLayout()
{
View v = inflate....
final Spinner a = v.findViewById...
final Spinner b = v.findViewById...
TextView t = v.findById...
t.setOnClickListener( new View.OnClickListener() {
#Override
public void onClick(View v) {
int val = a.get....
}
});
}
Maybe there is a simple solution to my problem, but i´m not able to find it.
I have a ListView with a list of users. Each row has an EditText to enter the username. I want to set hint text for each user like: "user1, user2, user3, etc", used as default name. The user can click on the EditText and change this name, so the hint text dissapears and the user can enter his name, or leave this default name if he wants.
When the ListView is too long, I have the problem of the view recycling, that duplicates the names. I solved it by using a setOnFocusChangeListener for the EditText, and storing the name for each row, and it´s working fine, but I´d like that when I have a long list, keep the hint text or text introduced by the user for each EditText when scrolling the list.
I don´t know how to modify my adapter to set the name/hint for each EditText.
Any idea?
Thanks a lot.
Create one list in your activity
List<String> yourlist = new ArrayList();
yourlist.add("user1");
yourlist.add("user2");
yourlist.add("user3");....
pass this list to adapter then in adapter,
holder.youredittext.setHint(yourlist.get(position));
if your passing number of items to adapter then create one model class then pass to adapter.
I have an adapter like this:
public View getView(final int position, View convertView, ViewGroup parent)
{
View item = convertView;
if(item == null)
{
LayoutInflater inflater = context.getLayoutInflater();
item = inflater.inflate(R.layout.setup_jugador, null);
holder = new ViewHolder();
holder.nombre = (EditText) item.findViewById(R.id.nombre);
// Establecemos el tag
item.setTag(holder);
}
else
{
holder = (ViewHolder)item.getTag();
}
holder.nombre.setOnFocusChangeListener(new View.OnFocusChangeListener() {
#Override
public void onFocusChange(View v, boolean hasFocus) {
if(!hasFocus){
EditText et = (EditText) v.findViewById(R.id.nombre);
// Here I store the name
jugadores.get(position).setNombre(et.getText().toString());
}
}
});
// Update EditText
holder.nombre.setText(jugadores.get(position).getNombre());
// Another option is
holder.nombre.setHint(jugadores.get(position).getNombre());
return(item);
}
jugadores is a list that stores the names. Initially it has user1, user2, etc.
I could setHint when Item==null, but I have to update the text at the end of the adapter, and when scrolling, the view recycling changes the items that are invisible.
I only see 8 items, and when scrolling, if I change first item, item number 9 also change. If I use setText, it becomes black, and if I use setHint, first item becomes grey.
I can´t put hint value in layout because I´d like to add the row number to the name. I tried using a boolean value in the class used as model in the adapter to show that the name has been modified, check this value using position index in the list, and use setText or setHint according to that, but doesn´t work.
I have a set of View States that each contain a CheckBox view and an EditText View. When the user checks the CheckBox, I'd like to set the visibility of the EditText.
To get a handle of the EditText from the CheckBox, I just put the EditText as a tag on the CheckBox in OnCreate():
// In OnCreate()
v = f1.findViewById(R.id.imgNotes);
v.setTag(f1.findViewById(R.id.noteText));
v.setOnClickListener(this);
Later, in onClick() I retrieve the EditText from the tag:
public void onClick(View v)
{
super.onClick(v);
switch (v.getId())
{
case R.id.imgNotes:
View noteText = (View) v.getTag();
if (null != noteText)
{
if (noteText.getVisibility() == View.VISIBLE)
noteText.setVisibility(View.GONE);
else
noteText.setVisibility(View.VISIBLE);
}
break;
…
Everything is working fine. I was just wondering if there is a better way. Or is this okay? Or is this the ideal way?
Thanks!
This would work, no issues, but as a practice, avoid tagging views to other views. Few other ways you can try.
Field variable
Declare two private members, for EditText and CheckBox, and directly access them, whenever a checkbox is clicked. It works fine if lets say you have one pair of CheckBox and EditText, but the code gets messy if too many check_box and edit_text ids are wired around.
Custom view
Define a custom view class which holds such View state pairs, that way you can manage multiple such pairs, with each custom view holding business logic inside that view, thereby providing flexibility to add more behaviours in future, just edit this class.
Hope that helps. :)
In onCreate save EditText to a global variable likes this:
mEditText = (EditText) f1.findViewById(R.id.noteText)
Then in your onClick just use mEditText instead of noteText
I am dynamically adding views to Android and am seeing a really weird result which makes little to no sense. Here is the code that shows the bug:
private static int count = 0;
#Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
count++;
// Allow 'up' action for actionBar
getSupportActionBar().setDisplayHomeAsUpEnabled(true);
getSupportActionBar().setTitle("TEST");
setContentView(R.layout.test);
LinearLayout testLinear = (LinearLayout)findViewById(R.id.testLinear);
LayoutInflater inflater = (LayoutInflater)this.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
View view = inflater.inflate(R.layout.job_step_text, null, false);
TextView title = (TextView) view.findViewById(R.id.jobStepTextTextView);
final EditText editText = (EditText)view.findViewById(R.id.jobStepEditText);
title.setText("Field 1");
editText.setText("Value 1");
testLinear.addView(view);
if(count == 1) {
View view2 = inflater.inflate(R.layout.job_step_text, null, false);
TextView title2 = (TextView) view2.findViewById(R.id.jobStepTextTextView);
final EditText editText2 = (EditText)view2.findViewById(R.id.jobStepEditText);
title2.setText("Field 2");
editText2.setText("Value 2");
testLinear.addView(view2);
}
}
First time round the Activity is as follows:
Field 1: [ Value 1 ]
Field 2: [ Value 2 ]
Then when the device rotates the following is shown:
Field 1: [ Value 2 ]
Can anyone help? It seems that after the first time round the line:
final EditText editText = (EditText)view.findViewById(R.id.jobStepEditText);
is fetching an old reference and not calling setText()? When the screen rotates the line of code which sets the text field to 'Value 2' isn't even called and yet that's the result in the Field 1 text box.
Can anyone help?
By the way - a way to fix this is to give each EditText a unique ID before adding it to the view... but that makes no sense... Surely the inflated View has no knowledge of any other views (past or present) until testLinear.addView(view); is added?
Thanks in advance.
The onSaveInstanceState in the Activity (your super class) captures information about the attached content view and reloads it for you during onCreate() So when the Activity gets recreated after the device rotates, values are put into views found by ID as soon as you call setContentView(). This can produce surprising results if you are changing your layout on-the-fly.
One approach I have used is to call findViewById to see if the child view is already present, before adding it "by hand".
Another approach would be to inflate the layout first, make your adjustments to it, then call setContentView.
[I don't quite understand Android's reason for doing this -- maybe to allow super-simple applications to skip the onSaveInstanceState/reload from bundle process??)
I have a ListView that is filled with items of an ArrayAdapter.
Now I want to strike them out when click and also check in the beginning if they are already struck through(calling an external api etc).
But it only works in the onItemClickListener the method above it doesn't.
to understand it better, here is some code:
public void machListe() {
listViewArrayAdapter = new ArrayAdapter(getApplicationContext(),R.layout.task_item, ti);
taskListe.setAdapter(listViewArrayAdapter);
TextView ab=(TextView) taskListe.getChildAt(0);
So if I Debugg now I see that ab is null.
taskListe.setOnItemClickListener(new OnItemClickListener() {
public void onItemClick(AdapterView<?> arg0, View arg1,int arg2, long arg3) {
TextView ab=(TextView) taskListe.getChildAt(0);
If I debug here, ab is NOT null.
You are trying to saft the state of the tasks inside your Views.
You should try to separate Model and View at this point.
Create a Model Object that contains a single task then extend ArrayAdapter and overwrite getView. In the getView you retrieve the correct task from the task list. Create the textview for the task and if the task is marked as done in your model you cancel out the text.
If you try to change the views in a list after they are created you would have to do this every time the list stops scrolling because the list will only hold childviews for the items that are shown on the screen, the other views are created during scrolling to save memory.
The only correct place to change a listview Item is in the getView method of the corresponding Adapter.
Have a look at the ListsView Tutorial on vogella.de for more information.
Setting the adapter will trigger a requestLayout but the actual layout is not done yet.
So taskListe won't have child-views yet when you call getChildAt(0) immediately after calling setAdapter
Here is the code and 2 is the index value
View view=adapter.getView(2, null, null);
TextView textView = (TextView) view.findViewById(R.id.textView1);
String value = textView.getText().toString();