I am using handler in my code to update the app on every specific time interval.
For that i written follwing code:
public class Messages extends Activity {
protected Handler handler = new Handler();
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_messages);
Intent intent = getIntent();
String message = intent.getStringExtra(MainActivity.EXTRA_MESSAGE);
String id = intent.getStringExtra(MainActivity.EXTRA_ID);
String[] lst = null;
ListView lm=(ListView)findViewById(R.id.listView1);
TextView tv = (TextView)findViewById(R.id.textView1);
tv.setText("Welcome " + message);
handler.postDelayed(new UpdateTask(),500);
}
#Override
public boolean onCreateOptionsMenu(Menu menu) {
// Inflate the menu; this adds items to the action bar if it is present.
getMenuInflater().inflate(R.menu.messages, menu);
return true;
}
class UpdateTask implements Runnable {
#Override
public void run() {
// TODO Auto-generated method stub
setContentView(R.layout.activity_messages);
Intent intent = getIntent();
String message = intent.getStringExtra(MainActivity.EXTRA_MESSAGE);
String id = intent.getStringExtra(MainActivity.EXTRA_ID);
String[] lst = null;
ListView lm=(ListView)findViewById(R.id.listView1);
TextView tv = (TextView)findViewById(R.id.textView1);
tv.setText("Welcome " + message);
CallSoap cs=new CallSoap();
lst=cs.GetMessage(id);
ArrayAdapter<String> adpt = new ArrayAdapter<String>(this, android.R.layout.simple_list_item_1,lst);
lm.setAdapter(adpt);
handler.postDelayed(this, 500);
}
}
}
But it is giving me error on :
ArrayAdapter<String> adpt = new ArrayAdapter<String>(this, android.R.layout.simple_list_item_1,lst);
Text: Constructor ArrayAdapter is undefined.
Please help me.
ArrayAdapter<String> adpt = new ArrayAdapter<String>(Messages.this, android.R.layout.simple_list_item_1,lst);
But i don't understand why you put all those inside a handler.
Also i see setContentView twice for the same activity which is not a good design.
If you need to update the listview update the underlying data that populates listview and call notifyDataSetchanged on your adapter.
Also setContentView and intializing views everytime is not a good idead
you shold change this
ArrayAdapter<String> adpt = new ArrayAdapter<String>(this, android.R.layout.simple_list_item_1,lst);
by
ArrayAdapter<String> adpt = new ArrayAdapter<String>(YourActivity.this, android.R.layout.simple_list_item_1,lst);
Relace "this" reference in the constructor with ActivityName.this.
Changing
ArrayAdapter<String> adpt = new ArrayAdapter<String>(this, android.R.layout.simple_list_item_1,lst);
to
ArrayAdapter<String> adpt = new ArrayAdapter<String>(Messages.this, android.R.layout.simple_list_item_1,lst);
should work.
That being said, if you are looking for periodic update only, then the above code need not be necessary to be called all the times.
Instead simply calling adapter.notifyDataSetChanged(); should do the work,.
Related
this is my very first question so go easy on me :)
I am new to android, and I am trying to make a simple list. On the first Activity the user can enter data, which should display as a list on the second Activity.
I am using Intents to pass the data from one Activity to another, but I know I am missing something crucial in my ClassB Activity as nothing displays.
Here is my main code:
public class ClassA extends AppCompatActivity {
EditText note;
Button saveNoteB, goToNotesB;
public final static String EXTRA_NOTE = "com.lisa.currys.userlistarray.note";
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
saveNoteB = (Button) findViewById(R.id.saveNote);
saveNoteB.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
Intent i = new Intent(ClassA.this, ClassB.class);
note = (EditText) findViewById(R.id.note);
String userInput = note.getText().toString();
ArrayList<String> arr = new ArrayList<String>();
arr.add(userInput);
i.putStringArrayListExtra("note", arr);
startActivity(i);
}
});
and for my second activity:
public class ClassB extends AppCompatActivity {
public static android.widget.ListView displayNotes;
ArrayList<String> arr = new ArrayList<String>();
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main2);
arr = getIntent().getExtras().getStringArrayList(ClassA.EXTRA_NOTE);
displayNotes = (ListView)findViewById(R.id.listView);
Intent i = getIntent();
arr = i.getStringArrayListExtra("note");
ArrayAdapter<String> adapter = new ArrayAdapter<String>(ClassB.this, android.R.layout.simple_list_item_1);
displayNotes.setAdapter(adapter);
}
}
Any pointers or advice would be most welcome.
Thank you.
You are never actually adding the elements in arr to the ArrayAdapter. Use the three argument constructor for ArrayAdapter like below which will add the elements:
ArrayAdapter<String> adapter =
new ArrayAdapter<String>(ClassB.this, android.R.layout.simple_list_item_1, arr);
In ClassA try this:
i.putStringArrayListExtra(EXTRA_NOTE, arr);
or in ClassB try this:
arr = getIntent().getExtras().getStringArrayList("note");
You have to use the same key to set and get the values.
By the way, why are you assign values to "arr" two times?
Try this
ArrayAdapter<String> adapter = new ArrayAdapter<String>(ClassB.this, android.R.layout.simple_list_item_1);
Above statement you are pass the context and layout in which your data
display but you are not give the data which is store
in your **arr** arraylist so you not show anything.
replace this statement to
ArrayAdapter<String> adapter =
new ArrayAdapter<String>(ClassB.this, android.R.layout.simple_list_item_1, arr);
How can i get user inputs from one activity and populate the listView with user data in another activity. I am able to get user input and populate the listView in the same activity. but now i want to get user inputs in one form and populate the list in another activity.
the code that i used to populate the listView by getting user input is as follows
public class MainActivity extends ListActivity {
ArrayList<String> list = new ArrayList<String>();
/** Declaring an ArrayAdapter to set items to ListView */
ArrayAdapter<String> adapter;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
Button btn = (Button) findViewById(R.id.btnAdd);
/** Defining the ArrayAdapter to set items to ListView */
adapter = new ArrayAdapter<String>(this, android.R.layout.simple_list_item_1, list);
/** Defining a click event listener for the button "Add" */
View.OnClickListener listener = new View.OnClickListener() {
#Override
public void onClick(View v) {
EditText edit = (EditText) findViewById(R.id.txtItem);
String name=edit.getText().toString();
list.add(name);
edit.setText("");
adapter.notifyDataSetChanged();
}
};
/** Setting the event listener for the add button */
btn.setOnClickListener(listener);
you can store your user input / data into a local database; that will allow you to access your data anywhere in the app
(recommended since you are dealing with listview).
you can use shared preferences to store data if your data is relatively small.
In your current Activity (activity contains your button), create a new Intent:
String name = "";
name = edit.getText().toString();
Intent i = new Intent(getApplicationContext(), NewActivity.class);
i.putExtra("keyword",name);
startActivity(i);
Then in the NewActivity (activity contains your Listview), retrieve those values:
Bundle extras = getIntent().getExtras();
if (extras != null) {
String name = extras.getString("keyword");
if(name != ""){
// adapter.notifyDataSetChanged();
}
}
It is simple way, hope this help
Declare a public method in second Activity like
SecondActivity.class
public static ArrayList<String> list = new ArrayList<String>();
/** Declaring an ArrayAdapter to set items to ListView */
ArrayAdapter<String> adapter
onCreate()
{
...
;
adapter = new ArrayAdapter<String>(this, android.R.layout.simple_list_item_1, list);
listview.setAdapter(adapter);
...
}
public static void ModifyList()
{
adapter.notifyDataSetChanged();
}
FirstActivity.class
View.OnClickListener listener = new View.OnClickListener() {
#Override
public void onClick(View v) {
EditText edit = (EditText) findViewById(R.id.txtItem);
String name=edit.getText().toString();
SecondActivity.list.add(name);
edit.setText("");
SecondActivity.ModifyList();
}
};
Send your ArrayList like this from FirstActivity :
Intent intent = new Intent(FirstActivity.this, SecondActivity.class);
intent.putStringArrayListExtra("Datalist",list);
startActivity(intent);
In secondActivity Recieve the list using :
Intent i = getIntent();
list = i.getStringArrayListExtra("Datalist");
Then display it in your SecondActivitys listview
scenario:
First mainactivity launches and from the menu option user launches second activity using intent and there he adds some text to edittext and get that edittext value using intent to the first activity and add that value to the listview.
FirstActivity:
public class MainActivity extends Activity {
ListView lv;
EditText et;
String AddedTask ;
ArrayList<Model> modelList;
CustomAdapter adapter;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.main);
Intent intent = getIntent();
if (intent.hasExtra("NewTask")) {
AddedTask = this.getIntent().getExtras().getString("NewTask");
lv = (ListView) findViewById(R.id.listViewData);
String name = AddedTask;
Model md = new Model(name);
modelList.add(md);
adapter = new CustomAdapter(getApplicationContext(), modelList);
lv.setAdapter(adapter);
adapter.notifyDataSetChanged();
}
}
#Override
public boolean onCreateOptionsMenu(Menu menu) {
getMenuInflater().inflate(R.menu.main, menu);
return true;
}
#Override
public boolean onOptionsItemSelected(MenuItem item) {
// Handle action bar actions click
switch (item.getItemId()) {
case R.id.action_settings:
return true;
case R.id.action_add_task:
Intent i = new Intent(MainActivity.this, AddTask.class);
startActivity(i);
return true;
default:
return super.onOptionsItemSelected(item);
}
}
}
Second Activity:
public class AddTask extends Activity {
Button addtask;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.add_task);
// get action bar
ActionBar actionBar = getActionBar();
// Enabling Up / Back navigation
actionBar.setDisplayHomeAsUpEnabled(true);
addtask = (Button) findViewById(R.id.btnaddlist);
findViewById(R.id.btnaddlist).setOnClickListener(
new View.OnClickListener() {
public void onClick(View arg0) {
EditText edit = (EditText) findViewById(R.id.tskname);
Intent i = new Intent(AddTask.this,
MainActivity.class);
//Bundle bundle = new Bundle();
String TaskName = edit.getText().toString();
//bundle.putString("NewTask", TaskName);
i.putExtra("NewTask", TaskName);
i.setFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP);
//i.putExtras(bundle);
startActivity(i);
}
});
}
}
Now my problem is I'm able to add the data to the listview but each time I come back to mainactivity the previous data which was added is lost and updating the old data with my new data.
I have searched for many SO answers and most of them suggest to add adapter.notifyDataSetChanged(); which I have already tried and nothing worked.
I have done by checking the adapter is null or updating the data this way and getting null pointer exception:
if ( adapter== null )
{
adapter = new CustomAdapter(getApplicationContext(), modelList);
lv.setAdapter(adapter);
}
Can anyone say me how do I get this working ?
new View.OnClickListener() {
public void onClick(View arg0) {
EditText edit = (EditText) findViewById(R.id.tskname);
Intent i = new Intent(AddTask.this,
MainActivity.class);
//Bundle bundle = new Bundle();
String TaskName = edit.getText().toString();
//bundle.putString("NewTask", TaskName);
i.putExtra("NewTask", TaskName);
i.setFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP);
//i.putExtras(bundle);
startActivity(i);
}
});
You are starting a new Activity each time you want to add an item.
Consider using
startActivityForResult()
Link to Android Documentation
Even if startActivityForResult() is IMHO the best way to fix your problem, i'll give you a hint why it doesn't show your "old" data.
You don't finish your first Activity when going to the Second. You could aswell just finish your second activity and your MainActivity would run into
onResume()
therefor check the Android lifecycle
Don't use putextra and intent techniques. Follow below technique.
In main activity create sharedpref as follows:
public static final String SharedPref = "MyPreferences";
In activity 2 insert this code.
SharedPreferences settings=null;//declaration
settings=getSharedPreferences(SharedPref,0);//initialization
String TaskName= edit.getText().toString();
SharedPreferences.Editor editor = settings.edit();
editor.putString("NewTask", TaskName);
editor.commit();
finishfromchild(AddTask.this);
In main activity:
SharedPreferences settings=null;//declaration
In onCreate
//now initialise settings
settings=getSharedPreferences(SharedPref,0);//SharedPref is the foldername
//of your sharedpreferences(you create it first)
//Now create onResume method
public void onResume()
{
super.onResume();
AddedTask=settings.getString("NewTask", "");
lv = (ListView) findViewById(R.id.listViewData);
String name = AddedTask;
Model md = new Model(name);
modelList.add(md);
adapter = new CustomAdapter(getApplicationContext(), modelList);
lv.setAdapter(adapter);
}
Hope this works. I did the same in my previous project.
My XML:
<AutoCompleteTextView
android:id="#+id/searchAutoCompleteTextView_feed"
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:clickable="true"
android:completionThreshold="2"
android:hint="#string/search" />
MY java code:
AutoCompleteTextView eT = (AutoCompleteTextView)findViewById(R.id.searchAutoCompleteTextView_feed);
eT.addTextChangedListener(this);
String[] sa = new String[]{"apple", "mango", "banana", "apple mango", "mango banana"};
ArrayAdapter<String> aAdapter = new ArrayAdapter<String>(this,android.R.layout.simple_dropdown_item_1line, sa);
eT.setAdapter(aAdapter);
This is not working atall....i mean its just working like an EditTextView. Where am i wrong??
complete code:
public class FeedListViewActivity extends ListActivity implements TextWatcher{
private AutoCompleteTextView eT;
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.feed);
eT = (AutoCompleteTextView) findViewById(R.id.searchAutoCompleteTextView_feed);
eT.addTextChangedListener(this);
Thread thread = new Thread(null, loadMoreListItems);
thread.start();
}
private Runnable returnRes = new Runnable() {
public void run() {
//code for other purposes
}
};
private Runnable loadMoreListItems = new Runnable() {
public void run() {
getProductNames();
// Done! now continue on the UI thread
runOnUiThread(returnRes);
}
};
protected void getProductNames() {
String[] sa = new String[]{"apple", "mango", "banana", "apple mango", "mango banana"};
ArrayAdapter<String> aAdapter = new ArrayAdapter<String>(getApplicationContext(),
android.R.layout.simple_dropdown_item_1line, sa);
eT.setAdapter(aAdapter);
}
public void afterTextChanged(Editable s) {
// TODO Auto-generated method stub
}
public void beforeTextChanged(CharSequence s, int start, int count,
int after) {
// TODO Auto-generated method stub
}
public void onTextChanged(CharSequence s, int start, int before, int count) {
// TODO Auto-generated method stub
}
}
I just saw your other question before seeing this one. I was struggling with autocomplete for some time and I almost reverted to your new implementation of downloading all the keywords until I finally got it to work. What I did was;
//In the onCreate
//The suggestArray is just a static array with a few keywords
this.suggestAdapter = new ArrayAdapter<String>(this, this.suggestionsView, suggestArray);
//The setNotifyOnChange informs all views attached to the adapter to update themselves
//if the adapter is changed
this.suggestAdapter.setNotifyOnChange(true);
In my textwatcher's onTextChanged method, I get the suggests using an asynctask
//suggestsThread is an AsyncTask object
suggestsThread.cancel(true);
suggestsThread = new WertAgentThread();
suggestsThread.execute(s.toString());
In the AsyncTask's onPostExecute I then update the autocompletetextview
//suggestions is the result of the http request with the suggestions
this.suggestAdapter = new ArrayAdapter<String>(this, R.layout.suggestions, suggestions);
this.suggestions.setAdapter(this.suggestAdapter);
//notifydatasetchanged forces the dropdown to be shown.
this.suggestAdapter.notifyDataSetChanged();
See setNotifyOnChange and notifyDataSetChanged for more information
this is a snippet from my project. I think after you got data from services all you have to do is to:
clear your previous data.
clear the previous adapter values.
then add values to your list of data using add() or addAll() method.
notify the data changed by calling notifyDataSetChanged() on adapter.
#Override
public void onGetPatient(List<PatientSearchModel> patientSearchModelList) {
//here we got the raw data traverse it to get the filtered names data for the suggestions
stringArrayListPatients.clear();
stringArrayAdapterPatient.clear();
for (PatientSearchModel patientSearchModel:patientSearchModelList){
if (patientSearchModel.getFullName()!=null){
stringArrayListPatients.add(patientSearchModel.getFullName());
}
}
//update the array adapter for patient search
stringArrayAdapterPatient.addAll(stringArrayListPatients);
stringArrayAdapterPatient.notifyDataSetChanged();
}
but before all this make sure you have attached the adapter to the auto complete textview if don't do it as follows:
ArrayAdapter<String> stringArrayAdapterPatient= new ArrayAdapter<String>(getActivity(),android.support.v7.appcompat.R.layout.select_dialog_item_material,stringArrayListPatients);
completeTextViewPatient.setAdapter(stringArrayAdapterPatient);
Use adapter.notifyDataSetChanged() method to notify the changes in the list, If that is not working then you can show DropDown manually like autoCompleteTextView.showDropDown()
AutoCompleteTextView eT = (AutoCompleteTextView)findViewById(R.id.searchAutoCompleteTextView_feed);
// eT.addTextChangedListener(this);
String[] sa = new String[]{"apple", "mango", "banana", "apple mango", "mango banana"};
ArrayAdapter<String> aAdapter = new ArrayAdapter<String>(this,android.R.layout.simple_dropdown_item_1line, sa);
eT.setAdapter(aAdapter);
its working just comment on et.addtext line...
The only working solution after updating adapter and notifying about changes instantly show dropDown is reseting AutoCompleteTextView text again, Kotlin example:
with(autoCompleteTextView) {
text = text
// Place cursor to end
}
Java something like:
autoCompleteTextView.setText(autoCompleteTextView.getText());
// Place cursor to end
AutoCompleteTextView.Invalidate()
will do it.
If anyone is using a custom object array list, and facing this issue, check your model class and see if you have override the correct variable in toString. Overriede toString if you have not override yet.
public class MyModalClass {
public int id;
public String path;
#Override
public String toString() { //include this in your model and return what you need in your drop down
return path;
}
}
I am trying to create a refesh function for my main page. I have searched many site but i can't seem to find a (for me) acccesseble exaple. I am loading information from a sQLLite database. When i use my add activity and i return to the MainScreen activity the item i have added do not appear. How could i refresh this data the moment de activity is resumed.
Any help is welcome, thx in advance.
public ListView whiskeylist;
String[] DataArryWhiskey;
#Override
protected void onCreate(Bundle savedInstanceState) {
// TODO Auto-generated method stub
super.onCreate(savedInstanceState);
setContentView(R.layout.main);
// Start db view of whiskey
DBConfig info = new DBConfig(this);
info.open();
DataArryWhiskey = info.getDataInArray();
info.close();
whiskeylist = (ListView) findViewById(R.id.listofWhiskey);
whiskeylist.setOnItemClickListener(this);
whiskeylist.setAdapter(new ArrayAdapter<String>(this, android.R.layout.simple_list_item_1, DataArryWhiskey));
}// end onCreate
On The advice of Adil i change the code to
public ListView whiskeylist;
String[] DataArryWhiskey;
ListAdapter Adapter;
#Override
protected void onCreate(Bundle savedInstanceState) {
// TODO Auto-generated method stub
super.onCreate(savedInstanceState);
setContentView(R.layout.main);
// Start db view of whiskey
DBConfig info = new DBConfig(this);
info.open();
DataArryWhiskey = info.getDataInArray();
info.close();
whiskeylist = (ListView) findViewById(R.id.listofWhiskey);
Adapter = new ArrayAdapter<String>(this, android.R.layout.simple_list_item_1, DataArryWhiskey);
whiskeylist.setAdapter(Adapter);
// End db view of whiskey
}// end onCreate
#Override
public void onResume()
{
super.onResume();
DBConfig info = new DBConfig(this);
info.open();
DataArryWhiskey = info.getDataInArray();
info.close();
Adapter.notifyDataSetChanged(); // refresh adapter
}
however i get a error on notifyDataSetChanged "the method notifyDataSetChanged is undefined for the type ListAdapter" <- fixed it by changing the ListAdapter to ArrayAdapter but the app still crashes.
//made changes in your oncreate method, see below
DBConfig info;
#Override
protected void onCreate(Bundle savedInstanceState) {
// TODO Auto-generated method stub
super.onCreate(savedInstanceState);
setContentView(R.layout.main);
// Start db view of whiskey
info = new DBConfig(this);
whiskeylist = (ListView) findViewById(R.id.listofWhiskey);
whiskeylist.setOnItemClickListener(this);
}// end onCreate
another method give below, call this method from on ActivityResult(), but before doing that ensure that
the field you added with another activity also saved into database.
call show Data() from onActivityResult method or from onResume()
private void showData()
{
info.open();
DataArryWhiskey = info.getDataInArray();
info.close();
whiskeylist.setAdapter(new ArrayAdapter<String>(this, android.R.layout.simple_list_item_1, DataArryWhiskey));
}
Get a class level variable of ArrayAdapter adapter; and initialize it like this way:
adapter = new ArrayAdapter<String>(this, android.R.layout.simple_list_item_1, DataArryWhiskey);
hiskeylist.setAdapter(adapter);
and inside onResume() do like this way.
public void onResume()
{
super.onResume();
info.open();
DataArryWhiskey = info.getDataInArray();
info.close();
adapter.notifyDataSetChanged(); // refresh adapter
}
My Recommendation:
Since you are getting your values from database, use SimpleCursorAdapter instead of ArrayAdapter. which will do lots of other work also for you.
Here is a tutorial how to use SimpleCursorAdapter
You can try using adapter.clear(); before adding items.