Adapter not working inside asyncTask when notifyDataSetChanged? - java

i've got problem when trying to implement loadmore, exactly problem is adapter.notifyDataSetChanged inside AsyncTask. i trying to implement from this tuts https://github.com/shontauro/android-pulltorefresh-and-loadmore
, this tuts try implementing using extend ListActivity in Class, but i'm using extend Fragment, anyway this code is working, but just data not updated when trying to get data from loadmore. i'm sorry if my language is bad :)
this is my class :
import android.content.Intent;
import android.os.AsyncTask;
import android.os.Bundle;
import android.support.annotation.Nullable;
import android.support.v4.app.Fragment;
import android.support.v4.view.PagerAdapter;
import android.support.v4.view.ViewPager;
import android.util.Log;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.AdapterView;
import android.widget.ArrayAdapter;
import android.widget.BaseAdapter;
import android.widget.ListView;
import android.widget.TextView;
import com.bye.swipetab.adapter.ViewPagerAdapter;
import com.viewpagerindicator.CirclePageIndicator;
import com.viewpagerindicator.UnderlinePageIndicator;
import java.util.Arrays;
import java.util.LinkedList;
public class Tour extends Fragment {
private static final String TAG = Tour.class.getSimpleName();
View myView;
private String[] values ;
private static final String brand_value = "brand_value";
// Array of strings...
String[] mobileArray = {"Android","IPhone","WindowsMobile","Blackberry","WebOS"};
// list with the data to show in the listview
private LinkedList<String> mListItems;
// The data to be displayed in the ListView
private String[] mNames = { "Fabian", "Carlos", "Alex", "Andrea", "Karla",
"Freddy", "Lazaro", "Hector", "Carolina", "Edwin", "Jhon",
"Edelmira", "Andres" };
// Declare Variables
ViewPager viewPager;
PagerAdapter vAdapter;
String[] rank;
String[] country;
String[] population;
int[] flag;
UnderlinePageIndicator mIndicator;
ListView listView;
ArrayAdapter adapter;
#Nullable
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
myView = inflater.inflate(R.layout.tour_layout, null);
View header = inflater.inflate(R.layout.tour_header_layout, null);
//View footer = inflater.inflate(R.layout.tour_footer_layout, null);
listView = (ListView) myView.findViewById(android.R.id.list);
listView.addHeaderView(header, null, false); // header will not be clickable
mListItems = new LinkedList<String>();
mListItems.addAll(Arrays.asList(mNames));
adapter = new ArrayAdapter<String>(getActivity(), R.layout.tour_listview, R.id.MobileArray, mNames);
listView.setAdapter(adapter);
listView.setOnItemClickListener(new AdapterView.OnItemClickListener() {
public void onItemClick(AdapterView<?> parent, View view, int position, long id) {
// When clicked, show a toast with the TextView text
String brand_text = ((TextView) view.findViewById(R.id.MobileArray)).getText().toString();
//Toast.makeText(getApplicationContext(),brand_text, Toast.LENGTH_SHORT).show();
// Starting single contact activity
Intent in = new Intent(getActivity(), TourActivity.class);
in.putExtra(brand_value, brand_text);
in.addFlags(Intent.FLAG_ACTIVITY_NO_ANIMATION);
startActivity(in);
}
});
population = new String[] {
"1,354,040,000",
"1,210,193,422",
"315,761,000",
"315,123,000",
"363,752,000" };
flag = new int[] {
R.drawable.offline_ide_4,
R.drawable.offline_ide_1,
R.drawable.offline_ide_2,
R.drawable.offline_ide_3,
R.drawable.offline_ide_5 };
// Locate the ViewPager in viewpager_main.xml
viewPager = (ViewPager) myView.findViewById(R.id.pager);
// Pass results to ViewPagerAdapter Class
vAdapter = new ViewPagerAdapter(getContext(), rank, country, population, flag);
// Binds the Adapter to the ViewPager
viewPager.setAdapter(vAdapter);
CirclePageIndicator indicator = (CirclePageIndicator)myView.findViewById(R.id.indicator);
indicator.setViewPager(viewPager);
final float density = getResources().getDisplayMetrics().density;
indicator.setRadius(5 * density);
//indicator.setBackgroundColor(0x7f0c006a);
//indicator.setPageColor(R.color.black);
//indicator.setFillColor(R.color.tab_bg_yellow_deep);
//indicator.setStrokeColor(R.color.tab_bg_yellow_deep);
//indicator.setStrokeWidth(2 * density);
// set a listener to be invoked when the list reaches the end
((LoadMoreListView) listView)
.setOnLoadMoreListener(new LoadMoreListView.OnLoadMoreListener() {
public void onLoadMore() {
// Do the work to load more items at the end of list
// here
new LoadDataTask().execute();
}
});
return myView;
}
private class LoadDataTask extends AsyncTask<Void, Void, Void> {
#Override
protected Void doInBackground(Void... params) {
if (isCancelled()) {
return null;
}
// Simulates a background task
try {
Thread.sleep(1000);
} catch (InterruptedException e) {
}
for (int i = 0; i < mobileArray.length; i++) {
mListItems.add(mobileArray[i]);
}
return null;
}
#Override
protected void onPostExecute(Void result) {
mListItems.add("Added after load more");
// We need notify the adapter that the data have been changed
adapter.notifyDataSetChanged();
// Call onLoadMoreComplete when the LoadMore task, has finished
((LoadMoreListView) listView).onLoadMoreComplete();
super.onPostExecute(result);
}
#Override
protected void onCancelled() {
// Notify the loading more operation has finished
((LoadMoreListView) listView).onLoadMoreComplete();
}
}
}
please tell me why this is not working ?

mListItems is not used for anything.
mNames is the one linked to the adapter, not mListItems which you are filling in the AsyncTask, may be you should review that.
mListItems.addAll(Arrays.asList(mNames));
adapter = new ArrayAdapter<String>(getActivity(), R.layout.tour_listview, R.id.MobileArray, mNames);
and then you do
for (int i = 0; i < mobileArray.length; i++) {
mListItems.add(mobileArray[i]);
}

Related

how is onActivityResult is different from registerForActivityResult?

actually previously i wanted to pick image fromthe gallery so i came
to know that onActivityResult was deprecated and we should use
registerForActivityResult(). so i used it by defining the mime type
as "image/*" but now i want to import pdf from gallery but there is
no such mime type for that i want to understand how these mime
things works and how can i achieve my task by
registerForActivityResult() method
i also want to understand the how we define the datatype of the someActivityResultLauncher as a string ?? i want to understand how this whole things work...can we define custom mime type by our own ?? please help me in this
'''
package com.parth.iitktimes;
import androidx.activity.result.ActivityResultCallback;
import androidx.activity.result.ActivityResultLauncher;
import androidx.activity.result.contract.ActivityResultContracts;
import androidx.appcompat.app.AppCompatActivity;
import android.net.Uri;
import android.os.Bundle;
import android.provider.MediaStore;
import android.view.View;
import android.widget.AdapterView;
import android.widget.ArrayAdapter;
import android.widget.Button;
import android.widget.ImageView;
import android.widget.Spinner;
import android.widget.TextView;
import android.widget.Toast;
import com.google.android.material.card.MaterialCardView;
import java.io.IOException;
public class addBooks extends AppCompatActivity {
private MaterialCardView selectImage;
private TextView docName;
private Spinner semSpinner, branchSpinner;
private Button btnUpload;
private ActivityResultLauncher<String> someActivityResultLauncher; // why string
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_add_books);
selectImage = findViewById(R.id.select_image);
docName = findViewById(R.id.tvDocName);
semSpinner = findViewById(R.id.spinner_sem);
branchSpinner = findViewById(R.id.spinner_branch);
btnUpload = findViewById(R.id.btnUploadNotes);
btnUpload.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View view) {
Toast.makeText(getApplicationContext(), "uploaded notes successfully", Toast.LENGTH_SHORT).show();
}
});
selectImage.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View view) {
someActivityResultLauncher.launch("");//what used i fill here??
}
});
String[] semesterItems = {"First", "Second", "Third", "Fourth", "Fifth", "Sixth", "Seventh", "Eighth"};
//attaching array adapter to the spinner
//since we not using custom spinner therefore we are using the default array adapter
ArrayAdapter<String> adapter = new ArrayAdapter<String>(this, R.layout.support_simple_spinner_dropdown_item, semesterItems);
adapter.setDropDownViewResource(android.R.layout.simple_spinner_dropdown_item);
semSpinner.setAdapter(adapter);
//on item selected listener to the spinner
semSpinner.setOnItemSelectedListener(new AdapterView.OnItemSelectedListener() {
#Override
public void onItemSelected(AdapterView<?> adapterView, View view, int i, long l) {
imageCategory = eventSpinner.getSelectedItem().toString();
}
#Override
public void onNothingSelected(AdapterView<?> adapterView) {
//setting the default category as others
imageCategory = spinnerItems[0];
}
});
String[] branchItems = {"Mchanical", "Electrical", "CSE", "MTH"};
//attaching array adapter to the spinner
//since we not using custom spinner therefore we are using the default array adapter
ArrayAdapter<String> branchAdapter = new ArrayAdapter<String>(this, R.layout.support_simple_spinner_dropdown_item, branchItems);
adapter.setDropDownViewResource(android.R.layout.simple_spinner_dropdown_item);
branchSpinner.setAdapter(adapter);
//on item selected listener to the spinner
branchSpinner.setOnItemSelectedListener(new AdapterView.OnItemSelectedListener() {
#Override
public void onItemSelected(AdapterView<?> adapterView, View view, int i, long l) {
imageCategory = eventSpinner.getSelectedItem().toString();
}
#Override
public void onNothingSelected(AdapterView<?> adapterView) {
//setting the default category as others
imageCategory = spinnerItems[0];
}
});
//activity result launcher
someActivityResultLauncher = registerForActivityResult(
new ActivityResultContracts.GetContent(), new ActivityResultCallback<Uri>() {
#Override
public void onActivityResult(Uri result) {
try {
bitmap = MediaStore.Images.Media.getBitmap(getContentResolver(), result);
} catch (IOException e) {
e.printStackTrace();
}
preview_events_image.setImageBitmap(bitmap);
}
});
}
}

Scrape web's infinite scrolling “load more” button using Java in Android Studio

So far I can't find an article that explains how to handle scraping infinite scrolling page in Android Studio's Java. Maybe I'm not good at searching or else.
I'm doing a news app project that will display news using web scraping technique, and can also fetch data from the next page.
More on here : How to crawl a website with multiple pages using java
But, now I'm facing a new problem because one of my news source using infinite scrolling method for their site -> https://www.gameinformer.com/news
So, is there any way I can fetch the news data from this website's load more button ?
In case anyone need my code, here it is :
GameInformer's main activity :
package com.example.user.newsapp;
import android.app.ProgressDialog;
import android.os.AsyncTask;
import android.content.Intent;
import android.support.v7.app.AppCompatActivity;
import android.os.Bundle;
import android.support.v7.widget.Toolbar;
import android.view.Menu;
import android.view.MenuItem;
import android.support.v7.widget.CardView;
import android.support.v7.widget.LinearLayoutManager;
import android.support.v7.widget.RecyclerView;
import org.jsoup.Jsoup;
import org.jsoup.nodes.Document;
import org.jsoup.select.Elements;
import java.io.IOException;
import java.util.ArrayList;
public class News_GameInformer extends AppCompatActivity {
Toolbar toolbar;
private ProgressDialog mProgressDialog;
private String url = "https://www.gameinformer.com/news";
private ArrayList<String> mNewsTitleList = new ArrayList<>();
private ArrayList<String> mNewsDescList = new ArrayList<>();
private ArrayList<String> mNewsDateList = new ArrayList<>();
private CardView cardView;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_news__game_informer);
new Description().execute();
toolbar = findViewById(R.id.toolbar_news_gameinformer);
setSupportActionBar(toolbar);
getSupportActionBar().setDisplayHomeAsUpEnabled(true);
}
private class Description extends AsyncTask<Void,Void,Void> {
String desc;
#Override
protected void onPreExecute() {
super.onPreExecute();
mProgressDialog = new ProgressDialog(News_GameInformer.this);
mProgressDialog.setTitle("Connecting to GameInformer.com");
mProgressDialog.setMessage("Loading...");
mProgressDialog.setIndeterminate(true);
mProgressDialog.setCancelable(false);
mProgressDialog.setCanceledOnTouchOutside(false);
mProgressDialog.show();
}
#Override
protected Void doInBackground(Void... params) {
try {
Document mNewsDocument = Jsoup.connect(url).get();
Elements mElementDataSize = mNewsDocument.select("article[class=node teaser node--type-article node--promoted node--view-mode-teaser]");
int mElementSize = mElementDataSize.size();
for (int i=0;i<mElementSize;i++) {
Elements mElementNewsTitle = mNewsDocument.select("h2[class=page-title]").select("span").eq(i);
String mNewsTitle = mElementNewsTitle.text();
Elements mElementNewsDesc = mNewsDocument.select("div[class=field field--name-field-promo-summary field--type-string field--label-hidden field__item]").eq(i);
String mNewsDesc = mElementNewsDesc.text();
Elements mElementNewsDate = mNewsDocument.select("div[class=node__submitted author-details]").select("span[class=field field--name-created field--type-created field--label-hidden]").eq(i);
String mNewsDate = mElementNewsDate.text();
mNewsTitleList.add(mNewsTitle);
mNewsDescList.add(mNewsDesc);
mNewsDateList.add(mNewsDate);
}
} catch (IOException e) {
e.printStackTrace();
}
return null;
}
#Override
protected void onPostExecute(Void result) {
RecyclerView mRecyclerView = findViewById(R.id.act_recyclerview_gi_news);
gameinformer_DataAdapter mDataAdapter = new gameinformer_DataAdapter(News_GameInformer.this, mNewsTitleList, mNewsDescList, mNewsDateList, cardView);
RecyclerView.LayoutManager mLayoutManager = new LinearLayoutManager(getApplicationContext());
mRecyclerView.setLayoutManager(mLayoutManager);
mRecyclerView.setAdapter(mDataAdapter);
mProgressDialog.dismiss();
}
}
#Override
public boolean onCreateOptionsMenu(Menu menu) {
getMenuInflater().inflate(R.menu.menu_main,menu);
return true;
}
#Override
public boolean onOptionsItemSelected(MenuItem item) {
int id = item.getItemId();
if (id==R.id.gamezone) {
Intent i = new Intent(getApplicationContext(),News_GameZone.class);
startActivity(i);
} else if (id==R.id.gameinformer) {
Intent i = new Intent(getApplicationContext(),News_GameInformer.class);
startActivity(i);
} else if (id==R.id.gamespot) {
Intent i = new Intent(getApplicationContext(),News_GameSpot.class);
startActivity(i);
} else if (id==R.id.pcgamer) {
Intent i = new Intent(getApplicationContext(),News_PCGamer.class);
startActivity(i);
} else if (id==android.R.id.home) {
finish();
} else if (id==R.id.menuinfo) {
Intent i = new Intent(getApplicationContext(),Info.class);
startActivity(i);
} else if (id==R.id.menupeople) {
Intent i = new Intent(getApplicationContext(),People.class);
startActivity(i);
}
return super.onOptionsItemSelected(item);
}
}
Data Adapter's code :
package com.example.user.newsapp;
import android.app.Activity;
import android.content.Intent;
import android.support.v7.widget.CardView;
import android.support.v7.widget.RecyclerView;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.TextView;
import java.util.ArrayList;
public class gameinformer_DataAdapter extends RecyclerView.Adapter<gameinformer_DataAdapter.MyViewHolder> {
private ArrayList<String> mNewsTitleList = new ArrayList<>();
private ArrayList<String> mNewsDescList = new ArrayList<>();
private ArrayList<String> mNewsDateList = new ArrayList<>();
private Activity mActivity;
private int lastPosition=-1;
private CardView cardView;
public gameinformer_DataAdapter (News_GameInformer activity, ArrayList<String> mNewsTitleList, ArrayList<String> mNewsDescList, ArrayList<String> mNewsDateList, CardView cardView) {
this.mActivity = activity;
this.mNewsTitleList = mNewsTitleList;
this.mNewsDescList = mNewsDescList;
this.mNewsDateList = mNewsDateList;
this.cardView = cardView;
}
public class MyViewHolder extends RecyclerView.ViewHolder {
private TextView gameinformer_news_title, gameinformer_news_desc, gameinformer_news_date;
private CardView cardView_layout;
public MyViewHolder(View view) {
super(view);
gameinformer_news_title = view.findViewById(R.id.row_gi_news_title);
gameinformer_news_desc = view.findViewById(R.id.row_gi_news_desc);
gameinformer_news_date = view.findViewById(R.id.row_gi_news_date);
cardView_layout = view.findViewById(R.id.gi_cardview);
}
}
#Override
public MyViewHolder onCreateViewHolder(ViewGroup parent, int viewType) {
View itemView = LayoutInflater.from(parent.getContext())
.inflate(R.layout.gameinformer_row_data,parent,false);
return new MyViewHolder(itemView);
}
#Override
public void onBindViewHolder(MyViewHolder holder, final int position) {
holder.gameinformer_news_title.setText(mNewsTitleList.get(position));
holder.gameinformer_news_desc.setText(mNewsDescList.get(position));
holder.gameinformer_news_date.setText(mNewsDateList.get(position));
holder.cardView_layout.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
String title = mNewsTitleList.get(position);
Intent i = new Intent(mActivity, News_GameInformer_Webview.class);
i.putExtra("keytitle",title);
mActivity.startActivity(i);
}
});
}
#Override
public int getItemCount() {
return mNewsTitleList.size();
}
}

setOnItemClickListener() for ListView is not working

This is chat which is to be translate
This is the activity using listview to show languages and i have to select one language and save it to translate chat
I have an activity in which I'm using list view to show all languages using bing api, but on language selection activity crashed,I basically have to save the selected language in a variable for another use but its not working,
I have wrote the following code and don't know why this is not working while i tried all sort of methods but can't exactly understand the issue here
public void initViews() {
ArrayAdapter<String> adapter = new ArrayAdapter<String>(this, android.R.layout.simple_list_item_1, GetAllValues());
final ListView lang = (ListView) findViewById(R.id.select_lang);
lang.setAdapter(adapter);
loading = (ProgressBar) findViewById(R.id.pbLoading);
loading.setVisibility(ProgressBar.INVISIBLE);
lang.setOnItemClickListener(new AdapterView.OnItemClickListener(){
#Override
public void onItemClick(AdapterView<?> parent, View view,
int position, long id) {
// TODO Auto-generated method stub
// Selected_Language = languages[parent.getSelectedItemPosition()];
// Selected_Language = lang.getItemAtPosition(position).toString();
Selected_Language = languages[parent.getSelectedItemPosition()].toString();
new MessageChatAdapter(mcontext);
writeToFile(Selected_Language);
Toast.makeText(mcontext,"Language Saved", Toast.LENGTH_LONG).show();
// When clicked, show a toast with the TextView text
}
});
}
This is complete java file, The code was working fine with spinner but when i used listView it's not working:
package com.fyp.voicechat.ui;
import android.app.Activity;
import android.content.Context;
import android.os.Bundle;
import android.util.Log;
import android.view.View;
import android.widget.AdapterView;
import android.widget.ArrayAdapter;
import android.widget.ListView;
import android.widget.ProgressBar;
import android.widget.Toast;
import com.fyp.voicechat.R;
import com.fyp.voicechat.adapter.MessageChatAdapter;
import com.memetix.mst.language.Language;
import java.io.IOException;
import java.io.OutputStreamWriter;
import java.util.Arrays;
import java.util.Locale;
public class Setting_Activity extends Activity {
Language[] languages = Language.values();
public static String language;
ProgressBar loading;
public String Selected_Language;
public static Context mcontext;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_setting_);
mcontext = this;
initViews();
Locale loc = new Locale("en");
Log.i("-------------", Arrays.toString(loc.getAvailableLocales()));
}
public void initViews() {
ArrayAdapter<String> adapter = new ArrayAdapter<String>(this, android.R.layout.simple_list_item_1, GetAllValues());
final ListView lang = (ListView) findViewById(R.id.select_lang);
lang.setAdapter(adapter);
loading = (ProgressBar) findViewById(R.id.pbLoading);
loading.setVisibility(ProgressBar.INVISIBLE);
lang.setOnItemClickListener(new AdapterView.OnItemClickListener()
{
#Override
public void onItemClick(AdapterView<?> parent, View view,
int position, long id) {
// TODO Auto-generated method stub
// Selected_Language = languages[parent.getSelectedItemPosition()];
// Selected_Language = lang.getItemAtPosition(position).toString();
Selected_Language = languages[parent.getSelectedItemPosition()].toString();
new MessageChatAdapter(mcontext);
writeToFile(Selected_Language);
Toast.makeText(mcontext,"Language Saved", Toast.LENGTH_LONG).show();
// When clicked, show a toast with the TextView text
}
});
/* spin = (Spinner) findViewById(R.id.spin);
ArrayAdapter<String> dataAdapter = new ArrayAdapter<String>(this,
android.R.layout.simple_spinner_item, GetAllValues());
dataAdapter.setDropDownViewResource(android.R.layout.simple_spinner_dropdown_item);
spin.setAdapter(dataAdapter);
send = (ImageView) findViewById(R.id.ivSend);
//spin.setVisibility(Spinner.INVISIBLE);
loading = (ProgressBar) findViewById(R.id.pbLoading);
loading.setVisibility(ProgressBar.INVISIBLE);
send.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
Selected_Language = languages[spin.getSelectedItemPosition()].toString();
new MessageChatAdapter(mcontext);
writeToFile(Selected_Language);
Toast.makeText(mcontext,"Language Saved", Toast.LENGTH_LONG).show();
}
});*/
}
private void writeToFile(String data) {
try {
OutputStreamWriter outputStreamWriter = new OutputStreamWriter(openFileOutput("config.txt", Context.MODE_PRIVATE));
outputStreamWriter.write(data);
outputStreamWriter.close();
}
catch (IOException e) {
Log.e("Exception", "File write failed: " + e.toString());
}
}
public String[] GetAllValues(){
String lan[] = new String[languages.length];
for(int i = 0; i < languages.length; i++){
lan[i] = languages[i].name();
}
return lan;
}
}

Android after getting user's contacts into a list, Can't use them

I've manged to use the following code for retrieving user's contacts into a list, and now I'm working on the next step (getting individual info of each contact):
package com.example.mycontacts;
import android.app.LoaderManager;
import android.content.Context;
import android.content.CursorLoader;
import android.content.Loader;
import android.database.Cursor;
import android.graphics.Color;
import android.net.Uri;
import android.os.Bundle;
import android.provider.ContactsContract;
import android.support.v4.app.ListFragment;
import android.widget.CursorAdapter;
import android.widget.SimpleCursorAdapter;
/**
* Created by daniel on 28/02/2016.
*/
public class ContactListFragment extends ListFragment implements LoaderManager.LoaderCallbacks<Cursor> {
private CursorAdapter mAdapter;
#Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
// create adapter once
Context context = getActivity();
int layout = android.R.layout.simple_list_item_1;
Cursor c = null; // there is no cursor yet
int flags = 0; // no auto-requery! Loader requeries.
mAdapter = new SimpleCursorAdapter(context, layout, c, FROM, TO, flags);
}
#Override
public void onActivityCreated(Bundle savedInstanceState) {
super.onActivityCreated(savedInstanceState);
// each time we are started use our listadapter
setListAdapter(mAdapter);
// and tell loader manager to start loading
getActivity().getLoaderManager().initLoader(0, null, (android.app.LoaderManager.LoaderCallbacks<Cursor>) this);
}
// columns requested from the database
private static final String[] PROJECTION = {
ContactsContract.Contacts._ID, // _ID is always required
ContactsContract.Contacts.DISPLAY_NAME_PRIMARY // that's what we want to display
};
// and name should be displayed in the text1 textview in item layout
private static final String[] FROM = { ContactsContract.Contacts.DISPLAY_NAME_PRIMARY };
private static final int[] TO = { android.R.id.text1 };
#Override
public Loader<Cursor> onCreateLoader(int id, Bundle args) {
// load from the "Contacts table"
Uri contentUri = ContactsContract.Contacts.CONTENT_URI;
// no sub-selection, no sort order, simply every row
// projection says we want just the _id and the name column
return new CursorLoader(getActivity(),
contentUri,
PROJECTION,
null,
null,
null);
}
#Override
public void onLoadFinished(Loader<Cursor> loader, Cursor data) {
// Once cursor is loaded, give it to adapter
mAdapter.swapCursor(data);
}
#Override
public void onLoaderReset(Loader<Cursor> loader) {
// on reset take any old cursor away
mAdapter.swapCursor(null);
}
}
The problem is, I can't find a way to get the info from each contact, in the onItemClick() of the list.
Any idea?
EDIT
I actually added:
ListView newsList = new ListView(getActivity());
newsList.setOnItemClickListener(new AdapterView.OnItemClickListener() {
#Override
public void onItemClick(AdapterView<?> parent, View view, int position, long id) {
}
});
but didn't know how to proceed and how interact with cursor.
EDIT2
I changed it from listfragment to dialogFragment with a listview, but still I don't get the contact's number by pressing on the item (in list).
what am I misiing here?
> package com.example...;
import android.app.LoaderManager;
import android.content.Context;
import android.content.CursorLoader;
import android.content.Loader;
import android.database.Cursor;
import android.net.Uri;
import android.os.Bundle;
import android.provider.ContactsContract;
import android.support.annotation.Nullable;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.AdapterView;
import android.widget.ArrayAdapter;
import android.widget.Button;
import android.widget.CursorAdapter;
import android.widget.ListView;
import android.widget.SimpleCursorAdapter;
import android.widget.Spinner;
import android.widget.TextView;
import android.widget.TimePicker;
import android.widget.Toast;
/**
* Created by daniel on 28/02/2016.
*/
public class DialogFragment extends android.support.v4.app.DialogFragment implements LoaderManager.LoaderCallbacks<Cursor> {
private TextView dateView;
private Spinner actionSpinner;
private Button okButton;
private CursorAdapter mAdapter;
private TimePicker timePicker;
private static final String[] FROM = { ContactsContract.Contacts.DISPLAY_NAME_PRIMARY };
private static final int[] TO = { android.R.id.text1 };
private ListView list;
#Nullable
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
View v = inflater.inflate(R.layout.dialog,container,false);
Context context = getActivity();
int layout = android.R.layout.simple_list_item_1;
Cursor c = null; // there is no cursor yet
int flags = 0; // no auto-requery! Loader requeries.
mAdapter = new SimpleCursorAdapter(context, layout, c, FROM, TO, flags);
actionSpinner = (Spinner)v.findViewById(R.id.actionSpinner);
okButton = (Button)v.findViewById(R.id.saveButton);
list = (ListView)v.findViewById(R.id.listView);
ArrayAdapter<CharSequence> adapter = ArrayAdapter.createFromResource(getActivity(),
R.array.actions, android.R.layout.simple_spinner_item);
adapter.setDropDownViewResource(android.R.layout.simple_spinner_dropdown_item);
actionSpinner.setAdapter(adapter);
okButton.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
getDialog().dismiss();
Comm comm = (Comm) getActivity();
comm.pick();
}
});
list.setOnItemClickListener(new AdapterView.OnItemClickListener() {
#Override
public void onItemClick(AdapterView<?> parent, View view, int position, long id) {
mAdapter.getItem(position);
Toast.makeText(getActivity(), String.valueOf(position), Toast.LENGTH_SHORT).show();
}
});
return v;
}
#Override
public void onViewCreated(View view, #Nullable Bundle savedInstanceState) {
super.onViewCreated(view, savedInstanceState);
}
}
#Override
public void onActivityCreated(Bundle savedInstanceState) {
super.onActivityCreated(savedInstanceState);
list.setAdapter(mAdapter);
// and tell loader manager to start loading
getActivity().getLoaderManager().initLoader(0, null, (android.app.LoaderManager.LoaderCallbacks<Cursor>) this);
}
#Override
public Loader<Cursor> onCreateLoader(int id, Bundle args) {
// load from the "Contacts table"
Uri contentUri = ContactsContract.Contacts.CONTENT_URI;
// no sub-selection, no sort order, simply every row
// projection says we want just the _id and the name column
return new CursorLoader(getActivity(),
contentUri,
PROJECTION,
null,
null,
null); }
private static final String[] PROJECTION = {
ContactsContract.Contacts._ID, // _ID is always required
ContactsContract.Contacts.DISPLAY_NAME_PRIMARY // that's what we want to display
};
#Override
public void onLoadFinished(Loader<Cursor> loader, Cursor data) {
mAdapter.swapCursor(data);
}
#Override
public void onLoaderReset(Loader<Cursor> loader) {
mAdapter.swapCursor(null);
}
}

DialogFragment created by an event from a button in a custom ArrayAdapter always has same position

I'm a newb so try to be patient with me
Here is some background information about the problem I am having:
I have a fragment, ViewFragment, that consists of two components: a Spinner and a ListView. The Spinner is a default Spinner with a regular ArrayAdapter that fills the Spinner with values taken from an ArrayList called "metaList" that is basically and ArrayList of objects that each themselves have an ArrayList called "mainList".
The ListView has the custom ArrayAdapter (called "CustomAdapter") I mentioned in the title. The CustomAdapter fills the ListView with values taken from the "mainList" of the selected item in the Spinner.
Now, the CustomAdapter for the ListView has two buttons. The only button that does anything yet (called "viewButton") creates a DialogFragment when pushed.
The problem I am having relates to this DialogFragment. Each item in the ListView should create a unique DialogFragment when its viewButton is pressed. However, regardless of which item in the ListView has its button pressed, the DialogFragment is always the same and displays the DialogFragment for the last item in the ListView.
I think that this problem is due to the fact that the ListView items themselves are not being pressed, only their buttons, so the position value in the getView() method for the CustomAdapter never really changes.
How do I fix this problem?
Here is the code for the ViewFragment that contains the Spinner and ListView components:
package com.statbot;
import java.util.ArrayList;
import android.app.Activity;
import android.app.Fragment;
import android.os.Bundle;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.AdapterView;
import android.widget.ArrayAdapter;
import android.widget.ListView;
import android.widget.Spinner;
import android.widget.AdapterView.OnItemSelectedListener;
public class ViewFragment extends Fragment{
static int spinPos;
private ArrayList<String> names;
private ArrayList<String> nums;
private Spinner spinner;
private View view;
private ViewGroup container;
private ListView listView;
private Fragment frag;
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState) {
view = inflater.inflate(R.layout.view_layout, container, false);
this.container = container;
frag = this;
names = new ArrayList<String>();
nums = new ArrayList<String>();
spinner = (Spinner)view.findViewById(R.id.view_frag_spinner1);
listView = (ListView) view.findViewById(R.id.view_frag_listView2);
for(int k = 0; k < MainActivity.metaList.size(); k++)
{
names.add(MainActivity.metaList.get(k).getName());
}
ArrayAdapter<String> adapter = new ArrayAdapter<String> (container.getContext(),android.R.layout.simple_spinner_item, names);
adapter.setDropDownViewResource(android.R.layout.simple_spinner_dropdown_item);
spinner.setAdapter(adapter);
spinner.setOnItemSelectedListener(new SpinListener());
return view;
}
private class SpinListener extends Activity implements OnItemSelectedListener{
#Override
public void onItemSelected(AdapterView<?> parent, View view, int pos,
long id) {
// TODO Auto-generated method stub
spinPos = pos;
nums.clear();
for(int k = 0; k < MainActivity.metaList.get(pos).mainList.size(); k++)
{
nums.add("" + MainActivity.metaList.get(pos).mainList.get(k).quantity);
}
CustomAdapter adapter2 = new CustomAdapter(container.getContext(), android.R.layout.simple_spinner_item, nums);
adapter2.setFrag(frag);
listView.setAdapter(adapter2);
}
#Override
public void onNothingSelected(AdapterView<?> arg0) {
// TODO Auto-generated method stub
spinPos = 0;
}
}
}
Here is the code for the CustomAdapter:
package com.statbot;
import java.util.List;
import android.app.Fragment;
import android.content.Context;
import android.view.LayoutInflater;
import android.view.View;
import android.view.View.OnClickListener;
import android.view.ViewGroup;
import android.widget.ArrayAdapter;
import android.widget.Button;
import android.widget.ImageButton;
import android.widget.TextView;
public class CustomAdapter extends ArrayAdapter{
private TextView quantity;
private ImageButton editButton;
private ImageButton deleteButton;
private ImageButton viewButton;
private Context mContext;
private int id;
private Fragment frag;
private int pos;
private List<String> objects;
#SuppressWarnings("unchecked")
public CustomAdapter (Context context, int textViewResourceId, List<String> objects){
super(context, textViewResourceId, objects);
mContext = context;
id = textViewResourceId;
this.objects = objects;
}
public View getView(int position, View v, ViewGroup parent){
this.pos = position;
final int POSITION = position;
View mView = v;
if (mView == null){
LayoutInflater vi = (LayoutInflater)mContext.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
mView = vi.inflate(R.layout.cust_list_view, parent, false);
}
editButton = (ImageButton) mView.findViewById(R.id.cust_list_view_button1);
viewButton = (ImageButton) mView.findViewById(R.id.cust_list_view_button2);
quantity = (TextView) mView.findViewById(R.id.cust_list_view_textView1);
if(quantity == null)
{
System.out.println("The poop is a lie");
}
quantity.setText("" + pos + "," + ViewFragment.spinPos);
viewButton.setOnClickListener(new OnClickListener(){
#Override
public void onClick(View v) {
// TODO Auto-generated method stub
System.out.println("" + POSITION);
showContents(ViewFragment.spinPos, POSITION);
}
});
return mView;
}
private void showContents(int metaPos, int mainPos){
NumStatDialog contents = new NumStatDialog();
contents.setMainPosition(pos);
contents.setMetaPosition();
contents.show(frag.getFragmentManager(), "content_dialog");
}
public void setFrag(Fragment f){
frag = f;
}
}
Here is the code for the DialogFragment, called NumStatDialog:
package com.statbot;
import android.annotation.SuppressLint;
import android.app.DialogFragment;
import android.os.Bundle;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.TextView;
#SuppressLint("ValidFragment")
public class NumStatDialog extends DialogFragment{
private View view;
private int metaPosition;
private int mainPosition;
private TextView title;
private TextView info;
private boolean type;//if true, sets up a dialog to display information on a list. if false, displays information on an item of that list.
public NumStatDialog(int metaPos, int mainPos){
type = false;
metaPosition = metaPos;
mainPosition = mainPos;
}
public NumStatDialog(int metaPos){
type = true;
metaPosition = metaPos;
}
public NumStatDialog(){
}
public View onCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState) {
view = inflater.inflate(R.layout.numstat_dialog_layout, container);
info = (TextView) view.findViewById(R.id.numstat_dialog_textView2);
title = (TextView) view.findViewById(R.id.numstat_dialog_textView1);
if(!type){
//info.setText((CharSequence) MainActivity.metaList.get(metaPosition).mainList.get(mainPosition).toString());
info.setText((CharSequence) ("" + mainPosition));
//title.setText((CharSequence) ("" + MainActivity.metaList.get(metaPosition).mainList.get(mainPosition).quantity));
title.setText((CharSequence) ("" + metaPosition));
}
if(type){
info.setText((CharSequence) MainActivity.metaList.get(metaPosition).toString());
title.setText((CharSequence) MainActivity.metaList.get(metaPosition).getName());
}
return view;
}
public void setMainPosition(int mp){
mainPosition = mp;
}
public void setMetaPosition(){
metaPosition = ViewFragment.spinPos;
}
}
and here are some screenshots to make things easier to understand. The spinner is at the top with the ListView directly below it. The first number of each ListView item is its position, and the second number is the position of the Spinner. The button of interest is the paper-shaped one. ignore the pencil, it doesn't do anything yet.
and here is a DialogFragment. The title is the Spinner position and the bottom number is the position of the item whose button was pushed, but notice that even though the 1st item on the ListView had its button pushed to display this dialog, the number at the bottom of the fragment displays a three for the 4th item.
Any help on this problem would be greatly appreciated, this is one of the last major hurdles I need to overcome for this project, everything else should be pretty basic.
Thanks!
In your showContents(), you completely ignore the two parameters passed in and instead use this.pos, which would indeed be the position of the last view inflated by the ListView. Just use your parameters (and set up your IDE to warn you about unused variables and parameters).
On a different note, passing data to a fragment like this would not survive configuration changes (unless you have setRetainInstance everywhere, but that's riddled with different sorts of problems). Consider using setArguments, serializing state in onSaveInstanceState and deserializing it in onCreate (using getArguments or savedInstanceState, if that's available).

Categories