网络资源
慕课网提供了获取课程信息的地址:http://www.imooc.com/api/teacher?type=4&num=30,可以获取json格式表述的30门课程的图标、标题、描述、学员数等信息。
{
"status": 1,
"data": [
{
"id": 1,
"name": "Tony老师聊shell——环境变量配置文件",
"picSmall": "http://img.mukewang.com/55237dcc0001128c06000338-300-170.jpg",
"picBig": "http://img.mukewang.com/55237dcc0001128c06000338.jpg",
"description": "为你带来shell中的环境变量配置文件",
"learner": 12312
},
{
"id": 2,
"name": "数学知识在CSS动画中的应用",
"picSmall": "http://img.mukewang.com/55249cf30001ae8a06000338-300-170.jpg",
"picBig": "http://img.mukewang.com/55249cf30001ae8a06000338.jpg",
"description": "数学知识与CSS结合实现酷炫效果",
"learner": 45625
},
......
],
"msg": "成功"
}
实现效果
异步获取课程信息,并用ListView列表展示。
实现代码
activity_load_news.xml
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:orientation="vertical" android:layout_width="match_parent"
android:layout_height="match_parent"
android:padding="5dp">
<ListView
android:id="@+id/lv_news"
android:layout_width="match_parent"
android:layout_height="match_parent"></ListView>
</LinearLayout>
news_item.xml
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:orientation="horizontal"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:padding="5dp">
<ImageView
android:id="@+id/iv_news"
android:layout_width="64dp"
android:layout_height="64dp"
android:src="@mipmap/ic_launcher"/>
<LinearLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:orientation="vertical"
android:paddingLeft="10dp"
android:layout_gravity="center">
<TextView
android:id="@+id/tv_news_title"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text="Title"
android:maxLines="1"
android:textSize="16sp"
android:textColor="@color/black"/>
<TextView
android:id="@+id/tv_news_content"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text="Content"
android:maxLines="3"
android:textSize="12sp"
android:textColor="@color/steelblue"/>
</LinearLayout>
</LinearLayout>
LoadNewsActivity.java
public class LoadNewsActivity extends Activity {
private static final String URL = "http://www.imooc.com/api/teacher?type=4&num=30";
private ListView lv_news;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_load_news);
lv_news = (ListView) findViewById(R.id.lv_news);
new LoadNewsAsyncTask(this, lv_news).execute(URL);
}
}
LoadNewsAsyncTask.java
/**
* 异步加载网络资源
*/
public class LoadNewsAsyncTask extends AsyncTask<String, Void, List<NewsBean>> {
private Context ctx;
private ListView lv_news;
public LoadNewsAsyncTask(Context context, ListView lv) {
ctx = context;
lv_news = lv;
}
@Override
protected List<NewsBean> doInBackground(String... strings) {
return getJsonData(strings[0]);
}
@Override
protected void onPostExecute(List<NewsBean> newsBeans) {
super.onPostExecute(newsBeans);
NewsAdapter adapter = new NewsAdapter(ctx, newsBeans);
lv_news.setAdapter(adapter);
}
/**
* 通过url读取json
* @param url
* @return
*/
private List<NewsBean> getJsonData(String url) {
List<NewsBean> newsBeanList = new ArrayList<>();
try {
String jsonString = readStream(new URL(url).openStream());
JSONObject jsonObject = new JSONObject(jsonString);
if (jsonObject != null) {
JSONArray jsonArray = jsonObject.getJSONArray("data");
if (jsonArray != null) {
int count = jsonArray.length();
for (int i = 0; i < count; i++) {
JSONObject obj = jsonArray.getJSONObject(i);
if (obj != null) {
NewsBean bean = new NewsBean();
bean.IconUrl = obj.getString("picSmall");
bean.Title = obj.getString("name");
bean.Content = obj.getString("description");
newsBeanList.add(bean);
}
}
}
}
} catch (IOException e) {
e.printStackTrace();
} catch (JSONException e) {
e.printStackTrace();
}
return newsBeanList;
}
/**
* 读取inputstream中的文本
* @param is
* @return
*/
private String readStream(InputStream is) {
InputStreamReader isr;
String result = "";
try {
String line = "";
isr = new InputStreamReader(is, "utf-8");
BufferedReader br = new BufferedReader(isr);
while ((line = br.readLine()) != null) {
result += line;
}
} catch (UnsupportedEncodingException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}
return result;
}
}
NewsBean.java
/**
* 封装json数据
*/
public class NewsBean {
/**
* 图标地址
*/
public String IconUrl = "";
/**
* 标题
*/
public String Title = "";
/**
* 内容
*/
public String Content = "";
}
NewsAdapter.java
public class NewsAdapter extends BaseAdapter {
private LayoutInflater inflater;
private List<NewsBean> list;
public NewsAdapter(Context context, List<NewsBean> newsBeanList) {
inflater = LayoutInflater.from(context);
list = newsBeanList;
}
@Override
public int getCount() {
return list.size();
}
@Override
public Object getItem(int i) {
return list.get(i);
}
@Override
public long getItemId(int i) {
return i;
}
@Override
public View getView(int i, View view, ViewGroup viewGroup) {
if (view == null) {
view = inflater.inflate(R.layout.news_item, null);
NewsBean bean = list.get(i);
ImageView imageView = (ImageView) view.findViewById(R.id.iv_news);
ImageLoader imageLoader = new ImageLoader(imageView, bean.IconUrl);
// imageLoader.showImageByThread();//异步加载图片
imageLoader.showImageByAsyncTask();
TextView txtTitle = (TextView) view.findViewById(R.id.tv_news_title);
txtTitle.setText(bean.Title);
TextView txtContent = (TextView) view.findViewById(R.id.tv_news_content);
txtContent.setText(bean.Content);
}
return view;
}
}
ImageLoader.java
/**
* 异步加载网络图片
*/
public class ImageLoader {
private ImageView iv;
private String urlAddress;
public ImageLoader(ImageView imageView, String url) {
iv = imageView;
urlAddress = url;
}
//region 多线程
/**
* 接收异步线程的消息,更新主线程的ui
*/
private Handler handler = new Handler() {
@Override
public void handleMessage(Message msg) {
super.handleMessage(msg);
iv.setImageBitmap((Bitmap) msg.obj);
}
};
/**
* 使用多线程异步加载图片
* 异步线程不能直接更新ui,需要利用Message
*/
public void showImageByThread() {
new Thread(){
@Override
public void run() {
super.run();
//获取网络图片
Bitmap bitmap = getBitmapFromURL(urlAddress);
//通知主线程更新图片
Message message = Message.obtain();//获取现有的以及回收的message,提高message的使用效率
message.obj = bitmap;
handler.sendMessage(message);
}
}.start();
}
//endregion
//region AsyncTask方式
/**
* AsyncTask是在多线程的基础上进行了封装,可利用onPostExecute方法直接更新ui
*/
public void showImageByAsyncTask() {
new LoadImageAsyncTask().execute(urlAddress);
}
class LoadImageAsyncTask extends AsyncTask<String, Void, Bitmap> {
@Override
protected Bitmap doInBackground(String... strings) {
return getBitmapFromURL(strings[0]);
}
@Override
protected void onPostExecute(Bitmap bitmap) {
super.onPostExecute(bitmap);
iv.setImageBitmap(bitmap);
}
}
//endregion
/**
* 加载网络图片
* @param urlString
* @return
*/
private Bitmap getBitmapFromURL(String urlString) {
Bitmap bitmap = null;
InputStream is = null;
try {
URL url = new URL(urlString);
HttpURLConnection connection = (HttpURLConnection) url.openConnection();
is = new BufferedInputStream(connection.getInputStream());
bitmap = BitmapFactory.decodeStream(is);
connection.disconnect();
} catch (MalformedURLException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
} finally {
try {
is.close();
} catch (IOException e) {
e.printStackTrace();
}
}
return bitmap;
}
}