I have the following code which displays a ListFragment. Once a row is selected i turn the row's background to red. If i click another row then that turns red but the first selected row remains red.
How can i turn the colour back for the deselected rows? I've tried a few things like, clearCoices(), list.invalidate(), list.requestLayout(), list.refreshDrawableState. None of them seem to work.
Thanks in advance, Matt
public class CarerDetailsFragment extends ListFragment{
private static final String TAG = CarerDetailsFragment.class.getSimpleName();
MySimpleArrayAdapter myAdapter;
TwoDimensionalArrayList rotaArray;
#Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
Bundle b = getArguments();
if(b != null){
rotaArray = (TwoDimensionalArrayList) b.get("rotaArray");
Log.e(TAG, "rotaArray in CarerDetailsFragment has size " + rotaArray.size());
}else{
Log.e(TAG, "Bundle b = null!!!!!!!!!!!");
}
}
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
// Inflate the layout for this fragment
return inflater.inflate(R.layout.carerdetailsfragmentlayout, container, false);
}
#Override
public void onActivityCreated(Bundle savedInstanceState) {
super.onActivityCreated(savedInstanceState);
myAdapter = (MySimpleArrayAdapter) new MySimpleArrayAdapter(getActivity(), rotaArray);
setListAdapter(myAdapter);
}
#Override
public void onListItemClick(ListView l, View v, int position, long id) {
super.onListItemClick(l, v, position, id);
Log.e(TAG, "onListItemClick");
l.clearChoices();
v.setBackgroundColor(Color.parseColor("#FF0000"));
String name;
String actTimeIn;
String actTimeOut;
String doubleUpValue;
String status;
String startTime;
String clientID;
String notes;
Bundle b = new Bundle();
b.putString("name", name);
b.putString("actTimeIn", actTimeIn);
Fragment newFragment = new CarerPurposeOfCallFragment();
newFragment.setArguments(b);
FragmentTransaction transaction = getFragmentManager().beginTransaction();
// Replace whatever is in the fragment_container view with this fragment,
// and add the transaction to the back stack
transaction.replace(R.id.carerpurposeofcall, newFragment);
//transaction.addToBackStack(null);
// Commit the transaction
transaction.commit();
}
private class MySimpleArrayAdapter extends ArrayAdapter<String> {
private final Context context;
private final ArrayList<?> list;
String justTime;
String statusField;
String callID;
String needName;
public MySimpleArrayAdapter(Context context, ArrayList<?> list) {
super(context, R.layout.rotarowlayout);
Log.e(TAG, "inside adapter constructor");
this.context = context;
this.list = list;
//Log.e(TAG, "list has size of " + this.list.size());
}
#Override
public View getView(int position, View convertView, ViewGroup parent) {
LayoutInflater inflater = (LayoutInflater) context.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
View rowView = inflater.inflate(R.layout.rotarowlayout, parent, false);
TextView startTime = (TextView) rowView.findViewById(R.id.rowstarttime);
TextView duration = (TextView) rowView.findViewById(R.id.rowduration);
TextView status = (TextView) rowView.findViewById(R.id.rowstatus);
TextView name = (TextView) rowView.findViewById(R.id.rowclientname);
final ImageView noteStatus = (ImageView)rowView.findViewById(R.id.notestatus);
return rowView;
}
#Override
public int getCount() {
if(this.list != null){
return this.list.size();
}else{
return 0;
}
}
}// end of adapter class
}//end of CarerListFragment
Use myAdapter.toggleSelection(position); to select or unselect.
You probably need to have selectedList and do checks when you toggle.
Related
I have an array of 3 elements which I try to draw in a listview. The issue is that it only draws the first entry because getView always returns a position = 0.
Why is that? What do I do wrong?
my main java (fragment):
public class PSGlobalFragment extends Fragment {
List<PSGitem> listPSGitem;
ListView list;
PSGadaptater psgAdapter;
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState) {
return inflater.inflate(R.layout.psglobal, container, false);
}
#Override
public void onActivityCreated(final Bundle savedInstanceState) {
super.onActivityCreated(savedInstanceState);
String ip;
listPSGitem = new ArrayList<>();
psgAdapter = new PSGadaptater(getActivity(), listPSGitem);
listPSGitem.clear();
StoreDevDiscovery store = new StoreDevDiscovery();
// this is where I store the data
int count = store.getMax();
for(int i=0;i<count;i++){
ip = store.getIPDiscovery(i);
PSGitem item = new PSGitem();
item.setIp(ip);
listPSGitem.add(item);
list.setAdapter(psgAdapter);
}
}
and my adapter:
public class PSGadaptater extends BaseAdapter {
private int size = 0;
private List<PSGitem> listIp;
private LayoutInflater layoutInflater;
Context context;
public PSGadaptater(Context c, List<PSGitem> objects) {
context = c;
listIp = objects;
layoutInflater = LayoutInflater.from(context);
}
#Override
public void notifyDataSetChanged() {
size = listIp.size();
super.notifyDataSetChanged();
}
#Override
public int getCount() {
return listIp.size();
}
public Object getItem(int position) {
return listIp.get(position);
}
public long getItemId(int position) {
return position;
}
private class ViewIPHolder {
TextView ip_psg;
}
public View getView(int position, View convertView, ViewGroup parent) {
ViewIPHolder viewHolder;
if(convertView == null) {
viewHolder = new ViewIPHolder();
convertView = layoutInflater.inflate(R.layout.listview_item_psg, null);
viewHolder.ip_psg = (TextView) convertView.findViewById(R.id.ipaddr_psg);
convertView.setTag(viewHolder);
} else {
viewHolder = (ViewIPHolder) convertView.getTag();
}
viewHolder.ip_psg.setText(listIp.get(position).getIpaddr());
// position always = 0 this is my issue
return convertView;
}
}
and the PSCitem.java:
public class PSGitem {
private String ip1;
public String getIp(){
return ip1;
}
public void setIp(String ip){
ip1 = ip;
}
}
The problem is that you are creating your Adapter from an empty set of items:
listPSGitem = new ArrayList<>();
psgAdapter = new PSGadaptater(getActivity(), listPSGitem);
If you wish to add items to the adapter later, you should add the items to the adapter listIp list variable, and then let the adapter know about this change with notifyDataSetChanged() method.
Change your onActivityCreated method like below.
#Override
public void onActivityCreated(final Bundle savedInstanceState) {
super.onActivityCreated(savedInstanceState);
String ip;
listPSGitem = new ArrayList<>();
listPSGitem.clear();
StoreDevDiscovery store = new StoreDevDiscovery();
// this is where I store the data
int count = store.getMax();
for(int i=0;i<count;i++){
ip = store.getIPDiscovery(i);
PSGitem item = new PSGitem();
item.setIp(ip);
listPSGitem.add(item);
}
psgAdapter = new PSGadaptater(getActivity(), listPSGitem);
list.setAdapter(psgAdapter);
}
I am new to Android and I am trying to do this. I have an ArrayAdapter, a Fragment using this adapter and a class that runs a timer task every 15 mins to hit an api and update my cached superobject. This superobject contains a field list. Also, I am using a calendar to filter from this list and my fragment displays the filtered list. So when i click on a date on calendar, SampleObjects with that creation date will be shown in the fragment. I want to force update this list whenever my timer task updates the superobject. Is it possible and if so, how?
public class ScheduleAdapter extends ArrayAdapter<SampleObject> {
private List<SampleObject> objects;
public void setObjects(List<SampleObject> objects) {
this.objects = objects;
}
public ScheduleAdapter(Context context, List<SampleObject> objects) {
super(context, R.layout.schedule_list_item, R.id.schedule_list_layout, objects);
this.objects = objects;
}
#Override
public View getView(int position, View convertView, ViewGroup parent) {
View row = LayoutInflater.from(getContext()).inflate(R.layout.schedule_list_item, parent, false);
ViewHolder holder = new ViewHolder(row);
row.setTag(holder);
final SampleObject sam = objects.get(position);
if (row == null) {
LayoutInflater inflater = ((Activity) getContext()).getLayoutInflater();
row = inflater.inflate(R.layout.schedule_list_item, parent, false);
row.setTag(holder);
} else {
holder = (ViewHolder) row.getTag();
}
holder.customerView.setText(sampleObject.getStatus());
holder.addressView.setText(cleaningJob.getShortenedAddress());
holder.timingView.setText(sampleObject.getFormattedStartTime() + "-" + cleaningJob.getFormattedEndTime());
holder.iconView.setImageResource(R.drawable.ic_clear);
return row;
}
public static class ViewHolder {
public final ImageView iconView;
public final TextView customerView;
public final TextView addressView;
public final TextView timingView;
public ViewHolder(View view) {
iconView = (ImageView) view.findViewById(R.id.list_item_icon);
customerView = (TextView) view.findViewById(R.id.list_item_customer_textview);
addressView = (TextView) view.findViewById(R.id.list_item_address_textview);
timingView = (TextView) view.findViewById(R.id.list_item_timing_textview);
}
}
}
}
public class ScheduleFragment extends Fragment {
private static final String LOG_TAG = "ScheduleFragment";
private ScheduleAdapter mScheduleAdapter;
public static final String ARGS_CLEANING_JOB_ID = "id";
#Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
}
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState) {
Bundle args = getArguments();
Date requestedDate = null;
if (args != null) {
int day = args.getInt("date");
int month = args.getInt("month");
int year = args.getInt("year");
requestedDate = BasicUtility.constructDate(day, month, year);
}
List<SampleObject> sampleObjs = Collections.EMPTY_LIST;
if (requestedDate != null) {
List<SampleObject> sampleObjsFromController = ScheduleController.getSampleObjByDate(requestedDate);
if (CollectionUtils.isNotEmpty(sampleObjsFromController)) {
sampleObjs = sampleObjsFromController;
}
}
mScheduleAdapter =
new ScheduleAdapter(getActivity(), sampleObjs);
View scheduleListView = inflater.inflate(R.layout.schedule_list_fragment, container, false);
ListView listView = (ListView) scheduleListView.findViewById(R.id.schedule_list);
listView.setAdapter(mScheduleAdapter);
listView.setOnItemClickListener(new AdapterView.OnItemClickListener() {
#Override
public void onItemClick(AdapterView<?> adapterView, View view, int position, long l) {
SampleObject job = mScheduleAdapter.getItem(position);
Bundle bundle = new Bundle();
bundle.putString(ARGS_CLEANING_JOB_ID, job.getUniqueIdentifier());
Intent intent = new Intent(getActivity(), DetailActivity.class).putExtras(bundle);
startActivity(intent);
}
});
return scheduleListView;
}
}
public class CalendarFragment extends Fragment {
private static final String LOG_TAG = "CalendarFragment";
#Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
}
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState) {
View rootView = inflater.inflate(R.layout.calendar_view, container, false);
CalendarView calendarView = (CalendarView) rootView.findViewById(R.id.calendarView);
calendarView.setOnDateChangeListener(new CalendarView.OnDateChangeListener() {
#Override
public void onSelectedDayChange(CalendarView calendarView, int i, int i1, int i2) {
Log.d(LOG_TAG, "Showing item for date " + i + "::" + i1+ "::" + i2);
Bundle args = new Bundle();
Fragment frag = new ScheduleFragment();
frag.setArguments(args);
args.putInt("date", i2);
args.putInt("month", i1 + 1);
args.putInt("year", i);
getActivity().getSupportFragmentManager().beginTransaction()
.replace(R.id.schedule_list_container,frag, MainActivity.SCHEDULEFRAGMENT_TAG)
.commit();
}
});
return rootView;
}
}
public class ScheduleController {
private static Map<String, List<String>> sampleObjsByDate = new HashMap<>();
private static final String LOG_TAG = "ScheduleController";
static {
TimerTask timerTask = new TimerTask() {
#Override
public void run() {
Log.i(LOG_TAG, "updating schedule...");
populateSchedule();
}
};
Timer timer = new Timer(true);
timer.scheduleAtFixedRate(timerTask, 0, 15*60*1000);
}
public static void populateSchedule() {
//populate SuperObject here
}
public static List<SampleObject> getCleaningJobByDate(Date date) {
//filter list here
}
I should not have used a timerTask in the first place. I am using the IntentService now with AlarmManager and ResultReceiver and it worked like a charm. If someone else is looking for the same funcitonality, follow the tutorial https://guides.codepath.com/android/Starting-Background-Services
i have a listview for showing products (product Name, product Price and product Description).
I want to show the product description in a webview because i use html code (images,tables,video etc).
Everything is ok on the products list except the product description on the WebView.
When i scroll the listview on the products that they are not visible, the product Description(WebView) is completely wrong, actually it shows descriptions from previous products.
The problem it is inside the GetView function, and although i use a viewHolder class , it still the problem remailns. Below i show the code snippet of the Getview and the viewholder class :
/////THE VIEWHOLDER CLASS THAT HOLDS THE UI COMPONENTS//////////////////
private class ViewHolder {
TextView prName;
WebView prDescription;
TextView product_descr2;//for test, this shows always the correct pr. descr.
TextView prfprice;
ImageView prImage;
ProgressBar prProgressBar;
int ProdPosition;
}
//////THE GETVIEW() FUNCTION , WHERE I LOAD EACH PRODUCT VALUES///////
#Override
public View getView(int position, View convertView, ViewGroup parent) {
final ViewHolder viewHolder;
View view = convertView;
final ProductsData info = getItem(position);
if (view == null) {
// Product row
view = mInflater.inflate(R.layout.productslistitem_layout, null);
viewHolder = new ViewHolder();
assert view != null;
viewHolder.prName = (TextView) view.findViewById(R.id.product_name);
viewHolder.prDescription = (WebView) view.findViewById(R.id.webView1);
viewHolder.product_descr2 = (TextView)view.findViewById(R.id.product_descr2);
viewHolder.prDescription.setFocusable(false);
//final price
viewHolder.prfprice = (TextView) view.findViewById(R.id.product_fprice);
viewHolder.prImage = (ImageView) view.findViewById(R.id.product_image);
viewHolder.prProgressBar = (ProgressBar)view.findViewById(R.id.pbProduct);
view.setTag(viewHolder);
}else
viewHolder = (ViewHolder) view.getTag();
MainActivity.imageLoaderProducts.displayImage(info.getPrUrl(), viewHolder.prImage, options, new SimpleImageLoadingListener(){
#Override
public void onLoadingStarted(String imageUri, View view) {
viewHolder.prProgressBar.setProgress(0);
viewHolder.prProgressBar.setVisibility(View.VISIBLE);
}
#Override
public void onLoadingFailed(String imageUri, View view,
FailReason failReason) {
viewHolder.prProgressBar.setVisibility(View.GONE);
}
#Override
public void onLoadingComplete(String imageUri, View view, Bitmap loadedImage) {
viewHolder.prProgressBar.setVisibility(View.GONE);
viewHolder.prName.setText(info.getPrName()); //PRODUCT NAME
viewHolder.product_descr2.setText(info.getPrDescr()));//PRODUCT DESCR, CORRECT VALUES
String header = "<?xml version=\"1.0\" encoding=\"UTF-8\" ?>";
viewHolder.prDescription.setWebViewClient(new WebViewClient());
viewHolder.prDescription.getSettings().setJavaScriptEnabled(true);
//ENCODING UTF-8
viewHolder.prDescription.getSettings().setDefaultTextEncodingName("utf-8");
viewHolder.prDescription.loadData(header +"<div style='background-color:#fff'>"+ info.getPrDescr()+"</div>", "text/html; charset=utf-8", null);//WBVIEW SHOW WRONG PR.DESCR.
}, new ImageLoadingProgressListener() {
#Override
public void onProgressUpdate(String imageUri, View view, int current,int total) {
viewHolder.prProgressBar.setProgress(Math.round(100.0f * current / total));
}
}
);
return view;
}
The product_descr2(TextView) shows the correct product description but the prDescription(WebView) shows the correct description only for the first product of the list. Is it a bug of WebView component or am i doing something wrong?
If anyone knows any solution please give a hand.
/*******************************/
I noticed that if i add convertview = null; into the getView, it loads the correct values into the WebViews but it is too slow.
i show the code of the products file. I use the universal image loader for lazy loading of the product images.
/******************PRODUCTS FILE************************************************************/
import java.util.ArrayList;
public class FragmentProducts extends Fragment implements
OnItemClickListener {
private ArrayList<ProductsData> productsList;
private ArrayList<ProductBitmapData> ProductBitmapList;
private LayoutInflater mInflater;
private ProductsListAdapter pAdapter;
private GridView lvProducts;
private ImageButton btnRefreshProducts;
private String VarTitle;//vartitle for the cart
private String VarId;//varId for the cart
private float VarPrice;//varPrice for the cart
//NEW for universal image loader
private DisplayImageOptions options;
#Override
public void onViewCreated(View view, Bundle savedInstanceState) {
// TODO Auto-generated method stub
super.onViewCreated(view, savedInstanceState);
//change fonts
TextView tvProductsHeader = (TextView)getActivity().findViewById(R.id.tvProductsHeader);
Utils.TypeFace(tvProductsHeader, getActivity().getAssets());
}
#Override
public void onActivityCreated(Bundle savedInstanceState) {
// TODO Auto-generated method stub
super.onActivityCreated(savedInstanceState);
mInflater = getActivity().getLayoutInflater();
pAdapter = new ProductsListAdapter(getActivity(), productsList);
lvProducts.setAdapter(pAdapter);
}
public static final FragmentProducts newInstance(
ArrayList<ProductsData> productsList,
ArrayList<ProductBitmapData> ProductBitmapList) {
FragmentProducts fr = new FragmentProducts();
Bundle args = new Bundle();
args.putSerializable("products", productsList);
args.putSerializable("bitmaps", ProductBitmapList);
fr.setArguments(args);
return fr;
}
public static final FragmentProducts newInstance(
ArrayList<ProductsData> productsList) {
//OLD FragmentProductsList fr = new FragmentProductsList();
FragmentProducts fr = new FragmentProducts();
Bundle args = new Bundle();
args.putSerializable("products", productsList);
fr.setArguments(args);
return fr;
}
#Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
this.productsList = (ArrayList<ProductsData>) (getArguments() != null ? getArguments()
.getSerializable("products") : null);
this.ProductBitmapList = (ArrayList<ProductBitmapData>) (getArguments() != null ? getArguments()
.getSerializable("bitmaps") : null);
//display options
options = new DisplayImageOptions.Builder()
.showImageOnLoading(R.drawable.ic_stub)
.showImageForEmptyUri(R.drawable.ic_empty)
.showImageOnFail(R.drawable.ic_error)
.cacheInMemory(true)
.cacheOnDisk(true)
.considerExifParams(true)
.bitmapConfig(Bitmap.Config.RGB_565)
.build();
}
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState) {
View view = inflater.inflate(R.layout.productslist_layout, container,
false);
lvProducts = (GridView) view.findViewById(R.id.glist);
lvProducts.setOnItemClickListener(this);
btnRefreshProducts = (ImageButton) view
.findViewById(R.id.btnRefreshProducts);
btnRefreshProducts.setOnClickListener(new OnClickListener() {
#Override
public void onClick(View v) {
pAdapter = new ProductsListAdapter(getActivity(), productsList);
lvProducts.setAdapter(pAdapter);
}
});
return view;
}
// CUSTOM ARRAY ADAPTER FOR THE LIST of CATEGORY ITEMS
public class ProductsListAdapter extends ArrayAdapter<ProductsData> {
public ProductsListAdapter(Context context, ArrayList<ProductsData> data) {
super(context, 0, data);
}
private class ViewHolder {
TextView prName;
WebView prDescription;
TextView prfprice;
ImageView prImage;
ProgressBar prProgressBar;
Spinner PrVariants1;
Spinner PrVariants2;
int ProdPosition;
//adapters
ArrayAdapter<String> var1Adapter;
ArrayAdapter<String> var2Adapter;
}
#Override
public int getCount() {
return super.getCount();
}
#Override
public ProductsData getItem(int position) {
return super.getItem(position);
}
#Override
public long getItemId(int position) {
return super.getItemId(position);
}
#Override
public View getView(int position, View convertView, ViewGroup parent) {
final ViewHolder viewHolder;
/*Clear convert view , and the WEBVIEW(DESCRIPTION) WORKS FINE! **/
/*BUT IT IS TOO SLOW BECAUSE, IT LOADS FROM THE START EACH TIME*/
convertView = null;
/*************************/
View view = convertView;
final ProductsData info = getItem(position);
if (view == null) {
// Product row
view = mInflater.inflate(R.layout.productslistitem_layout, null);
viewHolder = new ViewHolder();
assert view != null;
viewHolder.prName = (TextView) view.findViewById(R.id.product_name);
viewHolder.prDescription = (WebView) view.findViewById(R.id.webView1);
viewHolder.prDescription.setFocusable(false);
//starting price
/*viewHolder.prsprice = (TextView) view.findViewById(R.id.product_sprice);*/
//final price
viewHolder.prfprice = (TextView) view.findViewById(R.id.product_fprice);
viewHolder.prImage = (ImageView) view.findViewById(R.id.product_image);
viewHolder.prProgressBar = (ProgressBar)view.findViewById(R.id.pbProduct);
viewHolder.PrVariants1 = (Spinner) view.findViewById(R.id.spOptions1);
viewHolder.PrVariants1.setFocusable(false);
viewHolder.PrVariants2 = (Spinner) view.findViewById(R.id.spOptions2);
viewHolder.PrVariants2.setFocusable(false);
view.setTag(viewHolder);
}else
viewHolder = (ViewHolder) view.getTag();
MainActivity.imageLoaderProducts.displayImage(info.getPrUrl(), viewHolder.prImage, options, new SimpleImageLoadingListener(){
#Override
public void onLoadingStarted(String imageUri, View view) {
viewHolder.prProgressBar.setProgress(0);
viewHolder.prProgressBar.setVisibility(View.VISIBLE);
}
#Override
public void onLoadingFailed(String imageUri, View view,
FailReason failReason) {
viewHolder.prProgressBar.setVisibility(View.GONE);
}
#Override
public void onLoadingComplete(String imageUri, View view, Bitmap loadedImage) {
viewHolder.prProgressBar.setVisibility(View.GONE);
viewHolder.prName.setText(info.getPrName());
//SHOW WEBVIEW PRODUCT VALUE
String header = "<?xml version=\"1.0\" encoding=\"UTF-8\" ?>";
viewHolder.prDescription.setWebViewClient(new WebViewClient());
viewHolder.prDescription.getSettings().setJavaScriptEnabled(true);
//ENCODING UTF-8
viewHolder.prDescription.getSettings().setDefaultTextEncodingName("utf-8");
/**HERE IS THE PROBLEM ,I LOAD THE info.PrComments(product description)*/
viewHolder.prDescription.loadData(header +"<div style='background-color:#fff'>"+ info.getPrComments()+"</div>", "text/html; charset=utf-8", null);
/****************AND IF I SCROLL THE WEBVIEW VALUES ARE CONFUSED ***********/
/********START FILL VARIANTS 1 & 2***********/
viewHolder.var1Adapter = new ArrayAdapter<String>(getActivity(),android.R.layout.simple_spinner_item);
viewHolder.var2Adapter = new ArrayAdapter<String>(getActivity(), android.R.layout.simple_spinner_item);
//product id
int tempPrid = info.getPrID();
//new variants1
//LOAD variant1
for(int i = 0; i < info.getVariantsItems().size(); i ++){
viewHolder.var1Adapter.add(info.getVariantsItems().get(i).getVarOptions1());
}
//IF VARIANT2 IS NULL, View.GONE
if(info.getVariantsItems2().get(0).getVarOptions2() != null){
for(int i = 0; i < info.getVariantsItems2().size(); i ++){
viewHolder.var2Adapter.add(info.getVariantsItems2().get(i).getVarOptions2());
}
viewHolder.var2Adapter.setDropDownViewResource(android.R.layout.simple_spinner_dropdown_item);
viewHolder.PrVariants2.setAdapter(viewHolder.var2Adapter);
}//end if
else{
viewHolder.PrVariants2.setVisibility(View.GONE);
}//end else variant2
viewHolder.var1Adapter.setDropDownViewResource(android.R.layout.simple_spinner_dropdown_item);
viewHolder.PrVariants1.setAdapter(viewHolder.var1Adapter);
//add eventListener on variants1 listbox
viewHolder.PrVariants1.setOnItemSelectedListener(new OnItemSelectedListener() {
#Override
public void onItemSelected(AdapterView<?> parent,
View arg1, int pos, long arg3) {
//GET VALUES FROM spinner1
String tempOption1 = parent.getItemAtPosition(pos).toString();
//initialize
String tempOption2=null;
//CHECK IF SPINNER2 IS VISIBLE(IF IT IS VISIBLE ,IT HAS VALUE)
if (viewHolder.PrVariants2.getVisibility() != View.GONE){
if (viewHolder.PrVariants2.getSelectedItem() != null){
tempOption2 = viewHolder.PrVariants2.getSelectedItem().toString();
}
}
if (tempOption2 !=null)
{
VarTitle = tempOption1 + "/" + tempOption2;
}else
VarTitle = tempOption1;
ArrayList<String> res = MainApplication.dbHelper.checkVariation(VarTitle, Integer.toString(info.getPrID()));
//IF VARIATION DOES NOT EXIST , price field = N/A
if (res.isEmpty())
viewHolder.prfprice.setText("N/A");
else{
viewHolder.prfprice.setText(res.get(1) + "€");
VarId = res.get(0);//get the variantId for the cart
VarPrice = Float.valueOf(res.get(1));//get the variant price for the cart
}
}
#Override
public void onNothingSelected(AdapterView<?> arg0) {}
});
//add event listener on variants2 listbox
viewHolder.PrVariants2.setOnItemSelectedListener(new OnItemSelectedListener() {
#Override
public void onItemSelected(AdapterView<?> parent,
View arg1, int pos, long arg3) {
//initialize
String tempOption2 = null;
if(parent.getItemAtPosition(pos) != null){
tempOption2 = parent.getItemAtPosition(pos).toString();
}
//GET SPINNER1 VALUE
String tempOption1 = viewHolder.PrVariants1.getSelectedItem().toString();
if(tempOption2 != null)
{
VarTitle = tempOption1 + "/" + tempOption2;
}else
VarTitle = tempOption1;
ArrayList<String> res = MainApplication.dbHelper.checkVariation(VarTitle, Integer.toString(info.getPrID()));
///IF VARIATION DOES NOT EXIST , price field = N/A
if (res.isEmpty())
viewHolder.prfprice.setText("N/A");
else{
viewHolder.prfprice.setText(res.get(1) + "€");
VarId = res.get(0);//get the variantId for the cart
VarPrice = Float.valueOf(res.get(1));//get the variant price for the cart
}
}
#Override
public void onNothingSelected(AdapterView<?> arg0) {}
});
/********END FILL VARIANTS 1 & 2*************/
}
}, new ImageLoadingProgressListener() {
#Override
public void onProgressUpdate(String imageUri, View view, int current,
int total) {
viewHolder.prProgressBar.setProgress(Math.round(100.0f * current / total));
}
}
);
return view;
}
}
Don't use ViewHolder! => http://blog.xebia.com/2013/07/22/viewholder-considered-harmful/
try this:
...without if(convert == null){ ....
just inflate convertView
#Override
public View getView(int position, View convertView, ViewGroup parent) {
convertView = Inflater.inflate(R.layout.productslistitem_layout, null);
...
...
I am currently modifying an android app that I need to add a listview to an existing fragment. As I am new to android, I am just imitating the code from the apps. I created a new arrayadapter, a new class of data and made some modifies to the existing fragment class. The problem is I cannot see my list in the app. Below are my codes.
Adapter
public class RecordArrayAdapter extends ArrayAdapter<CheckInRecord.CheckInRec> {
private int resourceId;
private Context context;
private List<CheckInRecord.CheckInRec> checkInRec;
public RecordArrayAdapter(Context context, int resourceId, List<CheckInRecord.CheckInRec> checkInRec)
{
super(context, resourceId, checkInRec);
this.resourceId = resourceId;
this.context = context;
this.checkInRec = checkInRec;
}
public View getView(int position, View convertView, ViewGroup parent)
{
if (convertView == null){
LayoutInflater inflater = ((Activity)context).getLayoutInflater();
convertView = inflater.inflate(resourceId, parent, false);
}
TextView textViewName = (TextView) convertView.findViewById(R.id.tv_name);
TextView textViewCheckInDate = (TextView) convertView.findViewById(R.id.tv_checkindate);
TextView textViewPoints = (TextView) convertView.findViewById(R.id.tv_points);
ImageView imageViewIcon = (ImageView) convertView.findViewById(R.id.iv_icon);
CheckInRecord.CheckInRec checkInrec = checkInRec.get(position);
textViewName.setText(checkInrec.providerName);
textViewCheckInDate.setText(checkInrec.checkInDate);
textViewPoints.setText(checkInrec.providerPoints);
ImageLoader.getInstance().displayImage(checkInrec.providerIcon, imageViewIcon, Utility.displayImageOptions);
return convertView;
}
public int getIsPrize(int position) {return (this.checkInRec.get(position).isPrize);}
}
Data type
public class CheckInRecord {
public int userPoints;
public String userName;
public String gender;
public String birthDate;
public String location;
public String userIcon;
public List<CheckInRec> checkInRecList = new ArrayList<CheckInRec>();
public void addCheckInRec(String providerName, String providerLocation, String providerIcon,
String checkInDate, int providerPoints, int isPrize){
CheckInRec checkInRec = new CheckInRec();
checkInRec.providerName = providerName;
checkInRec.providerLocation = providerLocation;
checkInRec.providerIcon = providerIcon;
checkInRec.checkInDate = checkInDate;
checkInRec.providerPoints = providerPoints;
checkInRec.isPrize = isPrize;
checkInRecList.add(checkInRec);
}
public List<String> recImages(){
List<String> resultList = new ArrayList<String>();
if (this.checkInRecList == null){
return resultList;
}
for (CheckInRec rec : this.checkInRecList){
resultList.add(rec.providerIcon);
}
return resultList;
}
public class CheckInRec{
public String providerName;
public String providerLocation;
public String providerIcon;
public String checkInDate;
public int providerPoints;
public int isPrize;
}
}
Fragment
public class MeFragment extends Fragment implements ApiRequestDelegate {
private TextView textViewName;
private TextView textViewPoints;
private ProgressDialog progressDialog;
private RecordArrayAdapter recordArrayAdapter;
private List<CheckInRecord.CheckInRec> checkInRec = new ArrayList<CheckInRecord.CheckInRec>();
public MeFragment() {
}
#Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
AppDataManager.getInstance().setAllowCheckIn(true);
progressDialog = ProgressDialog.show(getActivity(), "", "");
ApiManager.getInstance().checkInHistories(AppDataManager.getInstance().getUserToken(), AppDataManager.getInstance().getUserPhone(),
Utility.getPictureSize(), this);
}
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState) {
View view = inflater.inflate(R.layout.fragment_me, container, false);
textViewName = (TextView) view.findViewById(R.id.tv_name);
textViewPoints = (TextView) view.findViewById(R.id.tv_points);
ListView listViewCheckInRec = (ListView) view.findViewById(R.id.lv_histories);
recordArrayAdapter = new RecordArrayAdapter(this.getActivity().getApplicationContext(), R.layout.row_record, checkInRec);
listViewCheckInRec.setAdapter(recordArrayAdapter);
return view;
}
#Override
public void setMenuVisibility(boolean menuVisible) {
super.setMenuVisibility(menuVisible);
if (menuVisible) {
refreshName();
}
}
public void refreshName() {
progressDialog = ProgressDialog.show(getActivity(), "", "");
AppDataManager dataManager = AppDataManager.getInstance();
ApiManager.getInstance().checkInHistories(dataManager.getUserToken(), dataManager.getUserPhone(), Utility.getPictureSize(), this);
}
#Override
public void apiCompleted(ApiResult apiResult, HttpRequest httpRequest) {
if (progressDialog!=null){
progressDialog.dismiss();
}
if (!apiResult.success){
ApiManager.handleMessageForReason(apiResult.failReason, getActivity());
return;
}
CheckInRecord checkInRecord = (CheckInRecord) apiResult.valueObject;
if (checkInRecord != null){
textViewName.setText(checkInRecord.userName);
textViewPoints.setText(String.format("积分%d分", checkInRecord.userPoints));
// this.checkInRec.clear();
// this.checkInRec.addAll(checkInRecord.checkInRecList);
//
// recordArrayAdapter.notifyDataSetChanged();
}
}
}
The problem is I cannot see my list in the app.
That is because checkInRec does now have any elements inside of it.
I can really tell that it is empty because you commented this out:
// this.checkInRec.clear(); //clear the old data from the list
// this.checkInRec.addAll(checkInRecord.checkInRecList); //add all the data inside the checkInRecord.checkInRecList
//
// recordArrayAdapter.notifyDataSetChanged(); //refreshing the ListView to display the new data
now what are those doing is that clearing the old list array and adding the new set of data from checkInRecord.checkInRecList and refreshing the ListView so those new data are implemented/shown in your ListView.
I'm trying to make a ListFragment. I looked the Api Demo (FragmentLayout). it works on a simple example and now i want to apply it to my existing project.
Here is my code. I create inner classes (RecipeList & RecipeDetail) as in the Api Demo.
public class InfoActivity extends MenuActivity {
#Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.info_fragment_layout);
// ...
}
public static class RecipeList extends ListFragment {
private int mCurrentSelectedItemIndex = -1;
private boolean mIsTablet = false;
#Override
public void onActivityCreated(Bundle savedInstanceState) {
super.onActivityCreated(savedInstanceState);
accountData = new ArrayList<Account>();
new AccountSyncTask() {
#Override
public void onPostExecute(
final ArrayList<ArrayList<String>> result) {
// For each retrieved account
Bd.insert(retrievedAccount);
accountData.add(retrievedAccount);
}
accountListAdapter = new AccountListAdapter(
InfoActivity.this, R.layout.accountlist_detail,
accountData);
accountListAdapter = new AccountListAdapter(
activityContext, R.layout.accountlist_detail,
accountData);
setListAdapter(accountListAdapter);
}
}.execute(sessionName, null, "getAllObjectOnServer",
String.valueOf(nbRow));
if (savedInstanceState != null) {
mCurrentSelectedItemIndex = savedInstanceState.getInt(
"currentListIndex", -1);
}
// This is a tablet if this view exists
View recipeDetails = getActivity()
.findViewById(R.id.recipe_details);
mIsTablet = recipeDetails != null
&& recipeDetails.getVisibility() == View.VISIBLE;
if (mIsTablet) {
getListView().setChoiceMode(ListView.CHOICE_MODE_SINGLE);
}
if (mIsTablet && mCurrentSelectedItemIndex != -1) {
showRecipeDetails();
}
}
#Override
public void onListItemClick(ListView l, View v, int position, long id) {
mCurrentSelectedItemIndex = position;
showRecipeDetails();
}
private void showRecipeDetails() {
if (mIsTablet) {
// Set the list item as checked
getListView().setItemChecked(mCurrentSelectedItemIndex, true);
// Get the fragment instance
RecipeDetail details = (RecipeDetail) getFragmentManager()
.findFragmentById(R.id.recipe_details);
// Is the current visible recipe the same as the clicked? If so,
// there is no need to update
if (details == null
|| details.getRecipeIndex() != mCurrentSelectedItemIndex) {
details = RecipeDetail
.newInstance(mCurrentSelectedItemIndex);
FragmentTransaction ft = getFragmentManager()
.beginTransaction();
ft.replace(R.id.recipe_details, details);
ft.setTransition(FragmentTransaction.TRANSIT_FRAGMENT_FADE);
ft.commit();
}
} else {
}
}
#Override
public void onSaveInstanceState(Bundle outState) {
super.onSaveInstanceState(outState);
outState.putInt("currentListIndex", mCurrentSelectedItemIndex);
}
}
public static class RecipeDetail extends Fragment {
private int mRecipeIndex;
public static RecipeDetail newInstance(int recipeIndex) {
// Create a new fragment instance
RecipeDetail detail = new RecipeDetail();
// Set the recipe index
detail.setRecipeIndex(recipeIndex);
return detail;
}
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState) {
if (container == null) {
return null;
}
View v = inflater
.inflate(R.layout.recipe_details, container, false);
//..
return v;
}
public int getRecipeIndex() {
return mRecipeIndex;
}
public void setRecipeIndex(int index) {
mRecipeIndex = index;
}
}
I have a custom ArrayAdapter (my items in the ListFragment contain 4 textViews and a clickable imageButton).
AccountListAdapter :
public class AccountListAdapter extends ArrayAdapter<Account> {
private final Context context;
private final int layoutResourceId;
private final ArrayList<Account> data;
public AccountListAdapter(Context context, int layoutResourceId,
ArrayList<Account> data) {
super(context, layoutResourceId, data);
this.layoutResourceId = layoutResourceId;
this.context = context;
this.data = data;
}
#Override
public View getView(final int position, View convertView, ViewGroup parent) {
AccountHolder holder = null;
if (convertView == null) {
LayoutInflater inflater = ((Activity) context).getLayoutInflater();
convertView = inflater.inflate(layoutResourceId, parent, false);
holder = new AccountHolder();
convertView.setClickable(true);
convertView.setFocusable(true);
holder.txtName = (TextView) convertView.findViewById(R.id.nom);
holder.txtId = (TextView) convertView.findViewById(R.id.id);
convertView.setTag(holder);
} else {
holder = (AccountHolder) convertView.getTag();
}
convertView.setOnClickListener(new OnClickListener() {
#Override
public void onClick(View v) {
Log.i("click", "index = " + position);
}
});
holder.txtName.setText(data.get(position).getName());
holder.txtId.setText(data.get(position).getId());
convertView.setBackgroundResource(R.drawable.list_selector);
ImageButton img = (ImageButton) convertView.findViewById(R.id.check);
img.setTag(position);
return convertView;
}
static class AccountHolder {
TextView txtName;
TextView txtId;
}
}
Problem :
When i click on an Item of the listFragment,
public void onListItemClick(ListView l, View v, int position, long id) {
mCurrentSelectedItemIndex = position;
Log.i("click", "here";
showRecipeDetails();
}
is not called but the listener on an item defined in AccountListAdapter works
convertView.setOnClickListener(new OnClickListener() {
#Override
public void onClick(View v) {
Log.i("click", "index = " + position);
}
});
Why is onListitemClick never called ?
Another question : is it a proper way to consume a web service in another thread in the onActivityCreated function of my ListFragment (in order to populate the list) ?
Thx in advance
EDIT = For the moment i made "showRecipeDetails" static and call it in the listener in my custom ArrayAdapter.
convertView.setOnClickListener(new OnClickListener() {
#Override
public void onClick(View v) {
RecipeList.showRecipeDetails(position);
}}
I'm not satisfied with my solution, i'm interessed to any other solution
OnItemClickListeners must first be associated with the ListView you want to record clicks for. In your onActivityCreated(..) method, place getListView().setOnItemClickListener(this) somewhere and put implements OnItemClickListener after public static class RecipeList extends ListFragment.