I was just asking myself if there was a way of making a ListView without any texts. I've only found ListViews with images + texts, and that exactly what i dont want. I just want to add a lot of images like in a list and don't want to make it with ImageView because that makes my app crash. Also, i dont want my app to lag. Thanks!
this is what i got in my activity_main.xml
<ListView
android:id="#+id/listview"
android:layout_width="fill_parent"
android:layout_height="wrap_content"
/>
and i found this from another post that actually helped me, but it doesnt display all images
public class MainActivity extends Activity {
// Array of integers points to images stored in /res/drawable-hdpi/
int[] vehs = new int[]{
R.drawable.veh1,
R.drawable.veh2,
R.drawable.veh3,
R.drawable.veh4,
R.drawable.veh5,
R.drawable.veh6,
R.drawable.veh7,
R.drawable.veh8,
R.drawable.veh9,
R.drawable.veh10,
R.drawable.veh11,
R.drawable.veh12,
R.drawable.veh13,
R.drawable.veh14,
R.drawable.veh15,
R.drawable.veh16,
R.drawable.veh17,
R.drawable.veh18,
R.drawable.veh19,
R.drawable.veh20,
R.drawable.veh21,
R.drawable.veh22,
R.drawable.veh23,
R.drawable.veh24,
R.drawable.veh25,
R.drawable.veh26,
R.drawable.veh27,
R.drawable.veh28,
R.drawable.veh29,
R.drawable.veh30,
R.drawable.veh31,
R.drawable.veh32,
R.drawable.veh33,
R.drawable.veh34,
R.drawable.veh35,
R.drawable.veh36,
};
/** Called when the activity is first created. */
#Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
// Each row in the list stores country name, currency and flag
List<HashMap<String,String>> aList = new ArrayList<HashMap<String,String>>();
for(int i=0;i<10;i++){
HashMap<String, String> hm = new HashMap<String,String>();
hm.put("vehs", Integer.toString(vehs[i]) );
aList.add(hm);
}
// Keys used in Hashmap
String[] from = { "vehs","txt","cur" };
// Ids of views in listview_layout
int[] to = { R.id.vehs,R.id.txt,R.id.cur};
// Instantiating an adapter to store each items
// R.layout.listview_layout defines the layout of each item
SimpleAdapter adapter = new SimpleAdapter(getBaseContext(), aList, R.layout.listview_layout, from, to);
// Getting a reference to listview of main.xml layout file
ListView listView = ( ListView ) findViewById(R.id.listview);
// Setting the adapter to the listView
listView.setAdapter(adapter);
}
}
Didn't edit all the code, so you might find some things confusing xD
The way ListView displays data is by using an adapter. The adapter takes your data, inserts it into a custom view, and then adds it to the list.
To build a fast images ListView, the first thing you'd want to do is to add Picasso to your project. This library will automatically download and cache your images, handle ImageView recycling, and more.
The next thing you'd want to do is to write your item view. If you want an images-only list, the view could be as simple as:
<!-- res/layout/list_item.xml -->
<?xml version="1.0" encoding="utf-8"?>
<ImageView xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="?android:attr/listPreferredItemHeight" />
Next, you want to create your adapter. It accepts a List<String> of image URLs as an input, builds the items and inserts them to the ListView.
public class ImageListAdapter extends ArrayAdapter<String> {
List<String> items;
public ImageListAdapter(Context context, int resource, List<String> items) {
super(context, resource, items);
this.items = items;
}
#Override
public View getView(int position, View convertView, ViewGroup parent) {
if (convertView == null) {
LayoutInflater inflater = LayoutInflater.from(getContext());
convertView = inflater.inflate(R.layout.list_item, null);
}
Picasso.with(getContext())
.load(items.get(position))
.into((ImageView) convertView);
return convertView;
}
}
Read the Picasso library documentation if you want to add more options such as image placeholders, transformations, and more.
Finally, to use the adapter on your ListView, add this to your activity's onCreate method:
List<String> images = new ArrayList<String>();
images.add("http://hometowncolumbia.files.wordpress.com/2007/12/lol-cats-dont-look-behind-cat.jpg");
images.add("http://i232.photobucket.com/albums/ee245/topswing/cat-lol.jpg");
listView = (ListView)findViewById(R.id.myListView);
listView.setAdapter(new ImageListAdapter(this, R.layout.list_item, images))
In a real application though, you'd probably want to load the image list from your server. You'd need to use an AsyncTask for that.
Don't make things difficult, the solution is simple in the classic 3 steps
Step 1:
Make a RelativeLayout in XML. Move the image to desired position (always to center, but you can choose if left or right) and change layout_height to wrap_content
Step 2:
Create a custom adapter for ListView, if you do this, you'll be able to all any layout as an item
public class ImagesAdapter extends ArrayAdapter<String> {
private Activity mContext;
private ArrayList<Bitmap> mImages;
public ImagesAdapter(Activity context, ArrayList<String> listOfValues, ArrayList<Bitmap> images) {
//The listOfValues is used when you make item click to get value
//Each image must to have a text value
super(context, R.layout.yourlayout, listOfValues);
mContext = context;
mImages = images;
}
#Override
public void getView(int position, View convertView, ViewGroup parent) {
LayoutInflater inflater = mContext.getLayoutInflater();
View returnView = inflater.inflate(R.layout.yourlayout, null);
ImageView imageView = (ImageView) returnView.findViewById(R.id.yourimageid);
imageView.setImageBitmap(mImages.get(position));
return returnView;
}
}
Step 3:
Implement in your code
ImagesAdapter adapter = new ImagesAdapter(this, myList, myImages);
mylistView.setAdapter(adapter);
myListView.setOnItemClickListener(new OnItemClickListener() {
#Override
public void onItemClick(AdapterView<?> parent, View view, int position, long id) {
//volov = Values Of ListOfValues
String volov = (String) myListView.getItemPosition(position);
Log.i(TAG, "listOfValues is useful " + volov);
}
});
Related
I have a main activity that has a Recyclerview, It displays a list image and a text as the title.
In the main activity I have three array lists; one for the image, one for its title and the last one "array" for a String array.
I am passing the R.array.id as a string into the next activity On Click of an item in the MainActivity. I send the image, title, and the array.
In the second Activity, where I check for incoming intent, Assign them to strings.
String imageUrl = getIntent().getStringExtra("image_url");
String imageName = getIntent().getStringExtra("image_name");
String array= getIntent().getStringExtra("array_id");
Then I have called setArray(array) and then inside the function, I got stuck.
private void setArray(String array) {
// Stuck here
}
I don't know what to do. I have set a ListView in the second layout
and found this code on this site.
ListView lv = (ListView) findViewById(R.id.extView);
ArrayAdapter<CharSequence> aa = ArrayAdapter.createFromResource(this, R.array.id, android.R.layout.simple_list_item_1);
lv.setAdapter(aa);
Which works, if I have a set the source to a static array id but how do I set it the string I receive?
Tried getString(array), which did not work. I also need to set an onClick listener to the items.
For displaying an array in a ListView, you need to have a custom adapter. The ArrayAdapter that you are currently using, is the native adapter for showing a list provided by Android SDK. However, you need a custom class if you need to show the ListView which populates the items dynamically from your array.
In order to do that, you need to have a custom adapter class like the following.
public class ListAdapter extends ArrayAdapter<String> {
private int resourceLayout;
private Context mContext;
public ListAdapter(Context context, int resource, List<String> items) {
super(context, resource, items);
this.resourceLayout = resource;
this.mContext = context;
}
#Override
public View getView(int position, View convertView, ViewGroup parent) {
View v = convertView;
if (v == null) {
LayoutInflater vi;
vi = LayoutInflater.from(mContext);
v = vi.inflate(resourceLayout, null);
}
String p = getItem(position);
if (p != null) {
TextView tt1 = (TextView) v.findViewById(R.id.id);
tt1.setText(p.getId());
}
return v;
}
}
Now you need a layout which indicates each item of your list. For example, the name of your layout is list_item.xml.
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_height="wrap_content" android:orientation="vertical"
android:layout_width="fill_parent">
<TextView
android:id="#+id/id"
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:gravity="left"
android:height="40sp" />
</LinearLayout>
Now in your second Activity, you need to initialize the adapter and set the adapter in your ListView like the following. Please note that, as the adapter takes a List, you need to convert your array string from a String to a List and then pass it to the adapter.
// I assume, the String is comma separated, which indicates the array.
List<String> arrayList = Arrays.asList(array.split("\\s*,\\s*"));
ListView lv = (ListView) findViewById(R.id.extView);
ListAdapter customAdapter = new ListAdapter(this, R.layout.list_item, arrayList);
lv.setAdapter(customAdapter);
Hope that helps!
I am trying to load images to imageview in my ListAdapter. However while I am passing 10 thumbnail images to listAdapter and set them in imageview, only 1 or none is visible in imageview. As I understand from docs, I dont need to use any asyntask, since picasso library has already working asyntask. Could you please help me how I can handle this issue?
// Calling CustumListAdapter like this;
CustomListAdapter customListAdapter = new CustomListAdapter(this, resultArrayList);
listView = (ListView) findViewById(R.id.listview_score);
listView.setAdapter(customListAdapter)
// And here is my CustomListAdapter class
public class CustomListAdapter extends ArrayAdapter<String> {
private ArrayList<String> resultContent;
//private Integer[] imageid;
private Activity context;
public CustomListAdapter(Activity context, ArrayList<String> resultContent) {
super(context, R.layout.activity_ident_result2, resultContent);
this.context = context;
this.resultContent = resultContent;
}
#Override
public View getView(int position, View convertView, ViewGroup parent) {
LayoutInflater inflater = context.getLayoutInflater();
View listViewItem = inflater.inflate(R.layout.activity_ident_result2, null, true);
if (position % 2 == 0) {
TextView textViewName = (TextView) listViewItem.findViewById(R.id.textView_score);
textViewName.setText(resultContent.get(position));
ImageView imageView = (ImageView) listViewItem.findViewById(R.id.imageView_score);
//imageView.setImageBitmap(IdentResultActivity.splittedBitmaps.get(position + 1));
Picasso.with(this.context).load(resultContent.get(position + 1)).into(imageView);
}
return listViewItem;
}
}
EDIT:
I used .placeholder(R.drawble.progress) and I can see one image placed without problem, rest are progress.png
EDIT2:
Here is my imageView xml file;
<ImageView
android:layout_width="75dp"
android:layout_height="75dp"
android:id="#+id/imageView_score" />
I believe the parameters of inflater.inflate should be (R.layout.activity_ident_result2, parent, false)
U need to create loop for adding every image to [] and then u need to show it. Becouse of ur posted code u adding just one image.
I have made a ListView which is populated with elements of an ArrayList. I do not have an XML file with this ListView, it is only in Java. Given this, how would I change the background color of the ListView as well as change the color of the text of the ListView?
This is the code for the ListView:
setListAdapter(new ArrayAdapter<String>(CollegeList.this, android.R.layout.simple_list_item_1, nameList));
In case you want to customize each line of the listview you have to use a custom adapter with custom listview item. Then you can use the "getView" Method to catch each item and position to change colors.
Here is a sample:
public class ListViewAdapter extends ArrayAdapter<Item> {
private Context context;
private int itemResourceId;
private ArrayList<Item> items;
public ListViewAdapter(Context context, int layoutId, ArrayList<Item> items) {
super(context, layoutId, items);
this.context = context;
this.itemResourceId = layoutId;
this.items = items;
}
#Override
public View getView(int position, View view, ViewGroup parent) {
ViewHolder holder = null;
if (view == null) {
holder = new ViewHolder();
LayoutInflater inflater = (LayoutInflater)getContext().getSystemService(Context.LAYOUT_INFLATER_SERVICE);
view = inflater.inflate(itemResourceId, null);
holder.listItem = (TextView) view.findViewById(R.id.item);
view.setTag(holder);
}
else
holder = (ViewHolder) view.getTag();
if (position % 2 == 0)
view.setBackgroundColor(context.getResources().getColor(R.color.listItemEven));
else
view.setBackgroundColor(context.getResources().getColor(R.color.listItemOdd));
Item item = items.get(position);
holder.listItem.setText((position+1) + ". " + item.sTitle);
return view;
}
static class ViewHolder {
TextView listItem;
}
}
android.R.layout.simple_list_item_1
You have to add an extra parameter to your ArrayAdapter, this will be a CUSTOM XML OF YOUR OWN and the next one will be a textview that is inside that custom layout, that way the array adapter will know which layout to fill and which textview needs to show the data you want to show.
from that xml you can modify background and color. will look something like this:
setListAdapter(new ArrayAdapter<String>(CollegeList.this, R.layout.your_custom_layout, R.id.the-text-view-in-that-layout, nameList));
You can get the xml for simple_list_item_1 here. You can copy it to your project and modify it, just change the code for your listview to setListAdapter(new ArrayAdapter<String>(CollegeList.this, R.layout.simple_list_item_1, nameList)); You can also create one yourself, since simple_list_item_1 is nothing but a textview. Just make sure that the id is android:id="#android:id/text1" otherwise it won't work with the default adapter.
This question already has answers here:
Closed 10 years ago.
Possible Duplicate:
How do I do a lazy load of images in ListView
i have listview with bitmap and text. When i download picture and i want to view it, it not appears in my app. When i used image from R.drawable.imagename then it works...
My code:
List<HashMap<String, Object> > aList = new ArrayList<HashMap<String, Object> >();
for(int i=0;i<ilosctalentow.size();i++){
if (ilosctalentow.get(i).indexOf("0/")==-1)
{
HashMap<String, Object> hm = new HashMap<String,Object>();
hm.put("txt", "xxx");
hm.put("cur","Currency : " + ilosctalentow.get(i));
Bitmap bmp = DownloadImage("http://www.xxx.pl/xxx/xxx/xhxuxj.png");
hm.put("flag",bmp);
aList.add(hm);
Log.i(TAG,Integer.toString(R.drawable.afghanistan) );
}
}
// Keys used in Hashmap
String[] from = { "flag","txt","cur" };
// Ids of views in listview_layout
int[] to = { R.id.flag,R.id.txt,R.id.cur};
// Instantiating an adapter to store each items
// R.layout.listview_layout defines the layout of each item
SimpleAdapter adapter = new SimpleAdapter(getBaseContext(), aList, R.layout.listview_layout, from, to);
// Getting a reference to listview of main.xml layout file
ListView listView = ( ListView ) findViewById(R.id.listview);
// Setting the adapter to the listView Zaraz mnie huj strzeli
listView.setAdapter(adapter);
Please help!
I think I can post a link to another question as an answer and explain how to apply it to your current solution.
Lazy load of images in ListView
When your application starts, display a simple list without images. Then start a background thread which downloads and creates bitmaps. When the thread completes its job - update the list so that it displays loaded images.
To make this work, you should create a custom adapter. Take the DrawableManager class from this answer (because the class from the accepted answer contains some bugs) and write the adapter like this:
// You should create your own class instead of TestItem
public class TestAdapter extends ArrayAdapter<TestItem> {
private final LayoutInflater mInflater;
private final DrawableBackgroundDownloader mDrawableBackgroundDownloader = new DrawableBackgroundDownloader();
public TestAdapter(Context context, List<TestItem> objects) {
super(context, -1, objects);
mInflater = LayoutInflater.from(context);
}
#Override
public View getView(int position, View convertView, ViewGroup parent) {
final TestItem item = this.getItem(position);
View view = convertView == null
? mInflater.inflate(R.layout.listview_layout, null)
: convertView;
TextView txtView = (TextView) view.findViewById(R.id.txt);
TextView curView = (TextView) view.findViewById(R.id.cur);
ImageView flagView = (ImageView) view.findViewById(R.id.flag);
txtView.setText(item.getText());
curView.setText(item.getCurrency());
mDrawableBackgroundDownloader.loadDrawable(item.getFlagUrl(), flagView, null);
return view;
}
}
This adapter can be improved by storing found elements in a view bag or using different class for downloading and caching of images. But I will leave it as it is for the sake of simplicity.
Before making my own SimpleAdapter object because I wanted to change the color of the rows, I was just using new SimpleAdapter(...). Now that I am using my own custom SimpleAdapter, the row color is changing, but my text is not getting updated. I have called adapter.notifyDataSetChanged(), but it is still showing only the sample text- "TextView". As I said, everything was working fine when I didn't create my own adapter. I suspect it might have something to do with the order I am initializing things:
public class AddScreen extends Activity implements OnClickListener,
OnItemClickListener, OnItemLongClickListener {
SimpleAdapter adapter;
List<HashMap<String, String>> painItems = new ArrayList<HashMap<String, String>>();
ListView listthings;
int[] to;
String[] from;
public void onCreate(Bundle savedInstanceState) {
...
listthings = (ListView) findViewById(R.id.listthings);
from = new String[] { "row_1", "row_2" };
to = new int[] { R.id.row1, R.id.row2 };
adapter = new Adapter(this, painItems, R.layout.mylistlayout,
from, to);
listthings.setAdapter(adapter);
...
}
public class Adapter extends SimpleAdapter{
HashMap<String, String> map = new HashMap<String, String>();
public Adapter(Context context, List<? extends Map<String, String>> data,
int resource, String[] from, int[] to) {
super(context, data, resource, from, to);
}
#Override
public View getView(int position, View convertView, ViewGroup parent){
View row = convertView;
if (row == null) {
LayoutInflater mInflater = (LayoutInflater)getSystemService(Context.LAYOUT_INFLATER_SERVICE);
row = mInflater.inflate(R.layout.mylistlayout, parent, false);
}
row.setBackgroundColor(0xFF0000FF);
TextView rw1 = (TextView)findViewById(R.id.row1);
// TextView rw2 = (TextView)findViewById(R.id.row2);
rw1.setText(map.get(position));
return row;
}
}
// to add the item, put it in the map, and add the map into the list
private void addItem() {
HashMap<String, String> map = new HashMap<String, String>();
map.put("row_1", row1);
map.put("row_2", row2);
map.put("row_3", painLevelString);
map.put("row_4", painLocation);
map.put("row_5", timeOfPainString);
map.put("row_6",textTreatmentString);
painItems.add(map);
adapter.notifyDataSetChanged();
}
EDIT:Added Code
This is how I am getting the data from the intent(onActivityResult()), placed before the addItem Code:
protected void onActivityResult(int requestCode, int resultCode, Intent data) {
if (resultCode == 1) {
row1 = data.getStringExtra("com.painLogger.row1");
row2 = data.getStringExtra("com.painLogger.row2");
painLevelString = data.getStringExtra("com.painLogger.painLevel");
painLocation = data.getStringExtra("painLocation");
timeOfPainString = data.getStringExtra("com.painLogger.painTime");
textTreatmentString = data
.getStringExtra("com.painLogger.treatment");
addItem();
}
}
*Also, just in case this is relevant the order of placement is this: onCreate() -> custom Adapter class -> onActivityResult() -> addItem()* **
Here is a screenshot of what it looks like. The two TextView fields in each item should be filled with info(which they were, until I did this).
If it worked previously with just using new SimpleAdapter(...) then in your getView(...) implementation change the first line to this:
View row = super.getView(position, convertView, parent);
And see if that is what you're expecting. Take out the LayoutInflater stuff too.
In getView(), about where you are setting the row background, you should also set the text for the TextView.
Calling notifyDataSetChanged(), doesn't automagically set your texts right, it just causes the ListView to redraw the visible rows with the new data...practically calling getView() for each row that needs a refresh.
I also suggest setting the background color from the mylistlayout.xml file, and if the getView() function starts taking on a few findViewByID's, you should also consider using a "view holder" approach like in this sample: http://developer.android.com/resources/samples/ApiDemos/src/com/example/android/apis/view/List14.html
You need to set the text in getView(). Like this:
public View getView(int position, View convertView, ViewGroup parent){
TextView text;
if (convertView == null) {
LayoutInflater mInflater = (LayoutInflater)getSystemService(Context.LAYOUT_INFLATER_SERVICE);
convertView = mInflater.inflate(R.layout.mylistlayout, parent, false);
text = (TextView) convertView.findViewById(R.id.more_list_text);
}
convertView.setBackgroundColor(0xFF0000FF);
text.setText(map.get(position));
return convertView;
}
Also, and this is VERY important - store you map as a member variable of the SimpleAdapter
ie, put this line at the top of your object definition:
HashMap<String, String> map = new HashMap<String, String>();