最简单的listView
用的是ArrayAdapter ,把上下文对象 this item布局,数据源放入adapter中,然后listView布局setAdapter(adapter)就可以展现一个列表了
import android.support.v7.app.ActionBarActivity;
import android.app.Activity;
import android.os.Bundle;
import android.view.Menu;
import android.view.MenuItem;
import android.view.View;
import android.widget.AdapterView;
import android.widget.AdapterView.OnItemClickListener;
import android.widget.ArrayAdapter;
import android.widget.ListView;
public class MainActivity extends Activity {
private String[] data = {"Apple","Banana","Pineapple","Tomato","Pear","Patato",
"Strawberry","Orange","Mango","Cherry","liqi","Yoghourt"};
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
//适配器adapter,数据源data
ArrayAdapter<String> adapter = new ArrayAdapter<String>(MainActivity.this,
android.R.layout.simple_list_item_1,data);
ListView listView = (ListView) findViewById(R.id.list_view2);
//列表listView
listView.setAdapter(adapter);
}
接下来是增加一个难度的listView 不过也是用的ArrayAdapter
MainActivity
package com.example.listviewtest;
import java.util.ArrayList;
import java.util.List;
import com.example.listviewtest.Fruit;
import android.app.Activity;
import android.os.Bundle;
import android.view.Menu;
import android.view.MenuItem;
import android.view.View;
import android.widget.AdapterView;
import android.widget.ArrayAdapter;
import android.widget.ListView;
import android.widget.Toast;
import android.widget.AdapterView.OnItemClickListener;
public class MainActivity extends Activity {
/*
* private String [] data
* ={"apple","Banana","Orange","Watermelon","pear","Grape","Pineapple",
* "Strawbery","Cherry","Mango"};
*/
private List<Fruit> fruitList = new ArrayList<Fruit>();
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
initFruit();//初始化水果数据
FruitAdapter adapter = new FruitAdapter(MainActivity.this, R.layout.fruit_item,
fruitList);
//在list中填充adapter
ListView listView = (ListView) findViewById(R.id.list_view);
listView.setAdapter(adapter);
//点击事件
listView.setOnItemClickListener(new OnItemClickListener(){
@Override
public void onItemClick(AdapterView<?> parent, View view, int position, long id) {
// TODO Auto-generated method stub
//获取当前项fruit实例
Fruit fruit = fruitList.get(position);
Toast.makeText(MainActivity.this, fruit.getName(),Toast.LENGTH_LONG).show();
}
});
}
public void initFruit(){
//给bean文件赋值,然后添加都数据源中(FruitAdapter就可以直接从bean中取值了)
Fruit apple = new Fruit ("Apple",R.drawable.apple_pic);
fruitList.add(apple);
Fruit orange = new Fruit ("Orange",R.drawable.orange_pic);
fruitList.add(orange);
Fruit banana = new Fruit ("Banana",R.drawable.banana_pic);
fruitList.add(banana);
Fruit watermelon = new Fruit ("Watermelon",R.drawable.watermelon_pic);
fruitList.add(watermelon);
Fruit pear = new Fruit ("Pear",R.drawable.pear_pic);
fruitList.add(pear);
Fruit grape = new Fruit ("Grape",R.drawable.grape_pic);
fruitList.add(grape);
Fruit pineapple = new Fruit ("Pineapple",R.drawable.pineapple_pic);
fruitList.add(pineapple);
Fruit strawberry = new Fruit ("Strawberry",R.drawable.strawberry_pic);
fruitList.add(strawberry);
Fruit cherry = new Fruit ("Cherry",R.drawable.cherry_pic);
fruitList.add(cherry);
Fruit mango = new Fruit ("Mango",R.drawable.mango_pic);
fruitList.add(mango);
Fruit strawberr = new Fruit ("Strawberry",R.drawable.strawberry_pic);
fruitList.add(strawberry);
Fruit cherr = new Fruit ("Cherry",R.drawable.cherry_pic);
fruitList.add(cherry);
Fruit mang = new Fruit ("Mango",R.drawable.mango_pic);
fruitList.add(mango);
}
}
Adapter
package com.example.listviewtest;
import java.util.List;
import android.content.Context;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.ArrayAdapter;
import android.widget.ImageView;
import android.widget.TextView;
public class FruitAdapter extends ArrayAdapter<Fruit> {
private int resourceId;
//上下文 item布局 数据源
public FruitAdapter(Context context, int textViewResourceId, List<Fruit> objects) {
super(context, textViewResourceId, objects);
resourceId = textViewResourceId;
}
@Override
public View getView(int position, View convertView, ViewGroup parent) {
Fruit fruit = getItem(position);//获取当前项的fruit实例
View view;
ViewHolder viewHolder;
if(convertView==null){
//填充列表每行的资源
convertView = LayoutInflater.from(getContext()).inflate(resourceId,null);
//viewHolder的作用就是少产生对象 即少findViewById ,就是这个作用
viewHolder = new ViewHolder();
viewHolder.fruitImage = (ImageView) convertView.findViewById(R.id.fruit_image);
viewHolder.fruitName = (TextView) convertView.findViewById(R.id.fruit_name);
convertView.setTag(viewHolder);//将ViewHolder存储在view中
}else{
//convertView就是减少创建view对象的产生,
//此时convertView已经获取最顶层的item滑出的View对象
// 然后convertView获取listView曾经最下面一行布局的item的标签(即新的视图要放在这个标签里)
viewHolder = (ViewHolder)convertView.getTag();//重新获取viewHolder
}
viewHolder.fruitImage.setImageResource(fruit.getImageId());
viewHolder.fruitName.setText(fruit.getName());
return convertView;
}
class ViewHolder{
ImageView fruitImage;
TextView fruitName;
}
}
bean 文件
package com.example.listviewtest;
public class Fruit {
private String name;
private int imageId;
public Fruit (String name,int imageId){
this.name= name;
this.imageId=imageId;
}
public String getName(){
return name;
}
public int getImageId(){
return imageId;
}
}
xml
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
tools:context="com.example.listviewtest.MainActivity" >
<ListView
android:id="@+id/list_view"
android:layout_width="match_parent"
android:layout_height="match_parent">
</ListView>
</LinearLayout>
注意:这些代码如果设置为0 或者null,会影响显示数据
@Override
public int getCount() {
// TODO Auto-generated method stub
return listTip.size(); //要显示出来,不能写0
}
@Override
public Object getItem(int arg0) {
return listTip!=null?listTip.get(arg0):null;
}
@Override
public long getItemId(int arg0) {
return arg0;
}
实战开发级别
MainActivity
import java.util.ArrayList;
import java.util.List;
import org.json.JSONArray;
import org.json.JSONException;
import org.json.JSONObject;
import android.app.Activity;
import android.content.Intent;
import android.os.Bundle;
import android.os.Handler;
import android.view.View;
import android.widget.AdapterView;
import android.widget.AdapterView.OnItemClickListener;
import android.widget.ListView;
import com.jikexueyuan.news.adapter.NewsAdapter;
import com.jikexueyuan.news.model.News;
import com.jikexueyuan.news.utils.HttpUtils;
public class MainActivity extends Activity implements OnItemClickListener{
private ListView lvNews;
private NewsAdapter adapter;
private List<News> newsList;
//此处需要修改为自己的服务器地址
public static final String GET_NEWS_URL = "http://172.31.28.208/NewsDemo/getNewsJSON.php";
private Handler getNewsHandler = new Handler(){
public void handleMessage(android.os.Message msg) {
String jsonData = (String) msg.obj;
System.out.println(jsonData);
try {
JSONArray jsonArray = new JSONArray(jsonData);
for (int i=0;i<jsonArray.length();i++){
JSONObject object = jsonArray.getJSONObject(i);
String title = object.getString("title");
String desc = object.getString("desc");
String time = object.getString("time");
String content_url = object.getString("content_url");
String pic_url = object.getString("pic_url");
newsList.add(new News(title, desc, time, content_url, pic_url));
}
adapter.notifyDataSetChanged();
} catch (Exception e) {
e.printStackTrace();
}
};
};
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
lvNews = (ListView) findViewById(R.id.lvNews);
newsList = new ArrayList<News>();
adapter = new NewsAdapter(this, newsList);
lvNews.setAdapter(adapter);
lvNews.setOnItemClickListener(this);
//传入一个handler对象过去 getNewsHandler
HttpUtils.getNewsJSON(GET_NEWS_URL, getNewsHandler);
}
@Override
public void onItemClick(AdapterView<?> arg0, View arg1, int position, long arg3) {
News news = newsList.get(position);
Intent intent = new Intent(this, BrowseNewsActivity.class);
intent.putExtra("content_url", news.getContent_url());
startActivity(intent);
}
}
点击后跳转的Activity
import android.app.Activity;
import android.os.Bundle;
import android.webkit.WebSettings;
import android.webkit.WebView;
public class BrowseNewsActivity extends Activity {
private WebView webView;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.acitivy_browse_news);
webView = (WebView) findViewById(R.id.webView);
String pic_url = getIntent().getStringExtra("content_url");
webView.loadUrl(pic_url);
webView.getSettings().setJavaScriptEnabled(true);
webView.getSettings().setCacheMode(WebSettings.LOAD_CACHE_ELSE_NETWORK);
}
}
工具类
import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.net.HttpURLConnection;
import java.net.MalformedURLException;
import java.net.URL;
import android.graphics.Bitmap;
import android.graphics.BitmapFactory;
import android.os.Handler;
import android.os.Message;
import android.widget.ImageView;
public class HttpUtils {
public static void getNewsJSON(final String url, final Handler handler){
new Thread(new Runnable() {
@Override
public void run() {
HttpURLConnection conn;
InputStream is;
try {
conn = (HttpURLConnection) new URL(url).openConnection();
conn.setRequestMethod("GET");
is = conn.getInputStream();
BufferedReader reader = new BufferedReader(new InputStreamReader(is));
String line = "";
StringBuilder result = new StringBuilder();
while ( (line = reader.readLine()) != null ){
result.append(line);
}
Message msg = Message.obtain();
msg.obj = result.toString();
handler.sendMessage(msg);
} catch (Exception e) {
e.printStackTrace();
}
}
}).start();
}
public static void setPicBitmap(final ImageView ivPic, final String pic_url){
new Thread(new Runnable() {
@Override
public void run() {
//pic_url是传过来的图片资源地址
try {
HttpURLConnection conn = (HttpURLConnection) new URL(pic_url).openConnection();
conn.connect();
InputStream is = conn.getInputStream();
Bitmap bitmap = BitmapFactory.decodeStream(is);
ivPic.setImageBitmap(bitmap);
is.close();
} catch (Exception e) {
e.printStackTrace();
}
}
}).start();
}
}
Adapter
import java.util.List;
import android.content.Context;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.BaseAdapter;
import android.widget.ImageView;
import android.widget.TextView;
import com.jikexueyuan.news.R;
import com.jikexueyuan.news.model.News;
import com.jikexueyuan.news.utils.HttpUtils;
public class NewsAdapter extends BaseAdapter {
private Context context;
private List<News> newsList;
public NewsAdapter(Context context, List<News> newsList){
this.context = context;
this.newsList = newsList;
}
@Override
public int getCount() {
return newsList.size();
}
@Override
public News getItem(int position) {
return newsList.get(position);
}
@Override
public long getItemId(int position) {
return position;
}
@Override
public View getView(int position, View convertView, ViewGroup parent) {
ViewHolder viewHolder;
if (convertView == null){
convertView = LayoutInflater.from(context).inflate(R.layout.news_item, null);
viewHolder = new ViewHolder();
viewHolder.tvTitle = (TextView) convertView.findViewById(R.id.tvTitle);
viewHolder.tvDesc = (TextView) convertView.findViewById(R.id.tvDesc);
viewHolder.tvTime = (TextView) convertView.findViewById(R.id.tvTime);
viewHolder.ivPic = (ImageView) convertView.findViewById(R.id.ivPic);
convertView.setTag(viewHolder);
}
else{
//向下转型
viewHolder = (ViewHolder) convertView.getTag();
}
News news = newsList.get(position);
viewHolder.tvTitle.setText(news.getTitle());
viewHolder.tvDesc.setText(news.getDesc());
viewHolder.tvTime.setText(news.getTime());
//把string类型的图片转换为bitmap图片
String pic_url = news.getPic_url();
HttpUtils.setPicBitmap(viewHolder.ivPic, pic_url);
return convertView;
}
class ViewHolder{
ImageView ivPic;
TextView tvTitle;
TextView tvDesc;
TextView tvTime;
}
}
bean
public class News {
private String title;
private String desc;
private String time;
private String content_url;
private String pic_url;
public News(String title, String desc, String time, String content_url, String pic_url){
setTitle(title);
setDesc(desc);
setTime(time);
setContent_url(content_url);
setPic_url(pic_url);
}
public String getTitle() {
return title;
}
public void setTitle(String title) {
this.title = title;
}
public String getDesc() {
return desc;
}
public void setDesc(String desc) {
this.desc = desc;
}
public String getTime() {
return time;
}
public void setTime(String time) {
this.time = time;
}
public String getContent_url() {
return content_url;
}
public void setContent_url(String content_url) {
this.content_url = content_url;
}
public String getPic_url() {
return pic_url;
}
public void setPic_url(String pic_url) {
this.pic_url = pic_url;
}
}
从代码中抽取一段代码(listView的优化或者说getView方法中应该怎样去写):
@Override
public View getView(int position, View convertView, ViewGroup parent) {
ViewHolder holder;
if (convertView == null) {
convertView = LayoutInflater.from(context).inflate(R.layout.call, null);
holder = new ViewHolder();
holder.nametv = (TextView) convertView.findViewById(R.id.name);
holder.numbertv = (TextView) convertView.findViewById(R.id.number);
convertView.setTag(holder);
}else{
holder = (ViewHolder) convertView.getTag();
}
holder.nametv.setText(lists.get(position).getName());
holder.numbertv.setText(lists.get(position).getNumber());
return convertView;
}
private static class ViewHolder{
TextView nametv;
TextView numbertv;
}
为什么要这样优化:
<span style="font-size:18px;">// 但当listview有大量的数据需要加载的时候,会占据大量内存,影响性能,这时候就需要按需填充并重新使用view来减少对象的创建。convertView就是减少创建view对象,convertView 对于所有的可见项是空值(如下)</span>
ViewHolder holder;
if (convertView == null) {
convertView = LayoutInflater.from(context).inflate(R.layout.call, null);
holder = new ViewHolder();
holder.nametv = (TextView) convertView.findViewById(R.id.name);
holder.numbertv = (TextView) convertView.findViewById(R.id.number);
convertView.setTag(holder);
}else{
holder = (ViewHolder) convertView.getTag();
}
holder.nametv.setText(lists.get(position).getName());
holder.numbertv.setText(lists.get(position).getNumber());
return convertView;
}
private static class ViewHolder{
TextView nametv;
TextView numbertv;
}
关于tag: 首先我们要知道setTag方法是干什么的,SDK解释为Tags Unlike IDs, tags are not used to identify views. Tags are essentially an extra piece of information that can be associated with a view. They are most often used as a convenience to store data related to views in the views themselves rather than by putting them in a separate structure. 这段官方的解释告诉我们 : tag标签就是用来关联view视图的,设置标签到某对象中,则view就在这个对象中,设置标签在String类型的数据,则view就在String类型的数据中。 //convertVIew把holder对象放入tag中,然后通过getTag()获取,因为这个holder对象中有像TextView nametv; TextView numbertv; 属性,所以不需要在findViewById()减少了性能的损坏。
listView基础学习demo1 https://yunpan.cn/cPCgEbs4fuNQX 访问密码 8790
listViwe基础学习 demo2 https://yunpan.cn/cPCsftxVuibUK 访问密码 cf29
参考链接 http://www.cnblogs.com/devinzhang/archive/2012/01/20/2328334.html