Android:ViewPager详细解释(异步网络负载图片,有图片缓存,)并与导航点
android 应用。准则欢迎页面。 和图像旋转木马特征, 或者没有很多其他的内容显示在一个页面。以被划分成多个页面,在这一刻viewpager这是非常容易使用。
首先看下效果:
以下是一个样例。带异步网络载入图片,并带导航小圆点
package com.example.viewpagertest; import java.io.IOException;
import java.lang.ref.SoftReference;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List; import org.apache.http.HttpEntity;
import org.apache.http.HttpResponse;
import org.apache.http.HttpStatus;
import org.apache.http.client.ClientProtocolException;
import org.apache.http.client.HttpClient;
import org.apache.http.client.methods.HttpGet;
import org.apache.http.impl.client.DefaultHttpClient;
import org.apache.http.params.CoreConnectionPNames; import android.annotation.SuppressLint;
import android.app.Activity;
import android.graphics.drawable.Drawable;
import android.os.Bundle;
import android.os.Handler;
import android.os.Message;
import android.support.v4.view.PagerAdapter;
import android.support.v4.view.ViewPager;
import android.support.v4.view.ViewPager.OnPageChangeListener;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.ImageView;
import android.widget.LinearLayout;
import android.widget.TextView; import com.example.viewpagertest.MainActivity.AsyncImageLoader.ImageCallback; /***
*
* 说明:ViewPager ,带小圆点导航。适配器採用PagerAdapter,基本能够满足需求
* 也能够採用FragmentPagerAdapter。有人说,Fragment能够更好的适应平板和手机。
* 而且能够更好的代码重用。详细这些优点大家试一下就知道了。
*
* @author andylaw
*
* 很多其它内容请查看博客:http://blog.csdn.net/lyc66666666666
*
*/ @SuppressLint("NewApi")
public class MainActivity extends Activity { private ViewPager view_pager; private LayoutInflater inflater; // 图片的地址,这里能够从server获取
String[] urls = new String[]{ "http://a.hiphotos.baidu.com/image/pic/item/3bf33a87e950352ad6465dad5143fbf2b2118b6b.jpg",
"http://a.hiphotos.baidu.com/image/pic/item/c8177f3e6709c93d002077529d3df8dcd0005440.jpg",
"http://f.hiphotos.baidu.com/image/pic/item/7aec54e736d12f2ecc3d90f84dc2d56285356869.jpg",
"http://e.hiphotos.baidu.com/image/pic/item/9c16fdfaaf51f3de308a87fc96eef01f3a297969.jpg",
"http://d.hiphotos.baidu.com/image/pic/item/f31fbe096b63f624b88f7e8e8544ebf81b4ca369.jpg",
"http://h.hiphotos.baidu.com/image/pic/item/11385343fbf2b2117c2dc3c3c88065380cd78e38.jpg",
"http://c.hiphotos.baidu.com/image/pic/item/3801213fb80e7bec5ed8456c2d2eb9389b506b38.jpg" }; private ImageView image;
private View item ;
private MyAdapter adapter ;
private ImageView[] indicator_imgs = new ImageView[7];//存放引到图片数组 @Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main); view_pager = (ViewPager) findViewById(R.id.view_pager);
List<View> list = new ArrayList<View>();
inflater = LayoutInflater.from(this); /**
* 创建多个item (每一条viewPager都是一个item)
* 从server获取完数据(如文章标题、url地址) 后,再设置适配器
*/
for (int i = 0; i < 7; i++) {
item = inflater.inflate(R.layout.item, null);
((TextView) item.findViewById(R.id.text_view)).setText("第 " + i+ " 个 viewPager");
list.add(item);
} //创建适配器。 把组装完的组件传递进去
adapter = new MyAdapter(list);
view_pager.setAdapter(adapter); //绑定动作监听器:如翻页的动画
view_pager.setOnPageChangeListener(new MyListener()); initIndicator();
} /**
* 初始化引导图标
* 动态创建多个小圆点,然后组装到线性布局里
*/
private void initIndicator(){ ImageView imgView;
View v = findViewById(R.id.indicator);// 线性水平布局,负责动态调整导航图标 for (int i = 0; i < 7; i++) {
imgView = new ImageView(this);
LinearLayout.LayoutParams params_linear = new LinearLayout.LayoutParams(10,10);
params_linear.setMargins(7, 10, 7, 10);
imgView.setLayoutParams(params_linear);
indicator_imgs[i] = imgView; if (i == 0) { // 初始化第一个为选中状态 indicator_imgs[i].setBackgroundResource(R.drawable.indicator_focused);
} else {
indicator_imgs[i].setBackgroundResource(R.drawable.indicator);
}
((ViewGroup)v).addView(indicator_imgs[i]);
} } /**
* 适配器。负责装配 、销毁 数据 和 组件 。
*/
private class MyAdapter extends PagerAdapter { private List<View> mList; private AsyncImageLoader asyncImageLoader; public MyAdapter(List<View> list) {
mList = list;
asyncImageLoader = new AsyncImageLoader();
} /**
* Return the number of views available.
*/
@Override
public int getCount() {
// TODO Auto-generated method stub
return mList.size();
} /**
* Remove a page for the given position.
* 滑动过后就销毁 ,销毁当前页的前一个的前一个的页! * instantiateItem(View container, int position)
* This method was deprecated in API level . Use instantiateItem(ViewGroup, int)
*/
@Override
public void destroyItem(ViewGroup container, int position, Object object) {
// TODO Auto-generated method stub
container.removeView(mList.get(position)); } @Override
public boolean isViewFromObject(View arg0, Object arg1) {
// TODO Auto-generated method stub
return arg0==arg1;
} /**
* Create the page for the given position.
*/
@Override
public Object instantiateItem(final ViewGroup container, final int position) { Drawable cachedImage = asyncImageLoader.loadDrawable(
urls[position], new ImageCallback() { public void imageLoaded(Drawable imageDrawable,
String imageUrl) { View view = mList.get(position);
image = ((ImageView) view.findViewById(R.id.image));
image.setBackground(imageDrawable);
container.removeView(mList.get(position));
container.addView(mList.get(position));
// adapter.notifyDataSetChanged(); }
}); View view = mList.get(position);
image = ((ImageView) view.findViewById(R.id.image));
image.setBackground(cachedImage); container.removeView(mList.get(position));
container.addView(mList.get(position));
// adapter.notifyDataSetChanged(); return mList.get(position); } } /**
* 动作监听器,可异步载入图片
*
*/
private class MyListener implements OnPageChangeListener{ @Override
public void onPageScrollStateChanged(int state) {
// TODO Auto-generated method stub
if (state == 0) {
//new MyAdapter(null).notifyDataSetChanged();
}
} @Override
public void onPageScrolled(int arg0, float arg1, int arg2) {
// TODO Auto-generated method stub } @Override
public void onPageSelected(int position) { // 改变全部导航的背景图片为:未选中
for (int i = 0; i < indicator_imgs.length; i++) { indicator_imgs[i].setBackgroundResource(R.drawable.indicator); } // 改变当前背景图片为:选中
indicator_imgs[position].setBackgroundResource(R.drawable.indicator_focused);
} } /**
* 异步载入图片
*/
static class AsyncImageLoader { // 软引用。使用内存做暂时缓存 (程序退出。或内存不够则清除软引用)
private HashMap<String, SoftReference<Drawable>> imageCache; public AsyncImageLoader() {
imageCache = new HashMap<String, SoftReference<Drawable>>();
} /**
* 定义回调接口
*/
public interface ImageCallback {
public void imageLoaded(Drawable imageDrawable, String imageUrl);
} /**
* 创建子线程载入图片
* 子线程载入完图片交给handler处理(子线程不能更新ui。而handler处在主线程,能够更新ui)
* handler又交给imageCallback。imageCallback需要自己来实现,在这里能够对回调參数进行处理
*
* @param imageUrl :需要载入的图片url
* @param imageCallback:
* @return
*/
public Drawable loadDrawable(final String imageUrl,
final ImageCallback imageCallback) { //假设缓存中存在图片 ,则首先使用缓存
if (imageCache.containsKey(imageUrl)) {
SoftReference<Drawable> softReference = imageCache.get(imageUrl);
Drawable drawable = softReference.get();
if (drawable != null) {
imageCallback.imageLoaded(drawable, imageUrl);//运行回调
return drawable;
}
} /**
* 在主线程里运行回调,更新视图
*/
final Handler handler = new Handler() {
public void handleMessage(Message message) {
imageCallback.imageLoaded((Drawable) message.obj, imageUrl);
}
}; /**
* 创建子线程訪问网络并载入图片 ,把结果交给handler处理
*/
new Thread() {
@Override
public void run() {
Drawable drawable = loadImageFromUrl(imageUrl);
// 下载完的图片放到缓存里
imageCache.put(imageUrl, new SoftReference<Drawable>(drawable));
Message message = handler.obtainMessage(0, drawable);
handler.sendMessage(message);
}
}.start(); return null;
} /**
* 下载图片 (注意HttpClient 和httpUrlConnection的差别)
*/
public Drawable loadImageFromUrl(String url) { try {
HttpClient client = new DefaultHttpClient();
client.getParams().setParameter(CoreConnectionPNames.CONNECTION_TIMEOUT, 1000*15);
HttpGet get = new HttpGet(url);
HttpResponse response; response = client.execute(get);
if (response.getStatusLine().getStatusCode() == HttpStatus.SC_OK) {
HttpEntity entity = response.getEntity(); Drawable d = Drawable.createFromStream(entity.getContent(),
"src"); return d;
} else {
return null;
}
} catch (ClientProtocolException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
} return null;
} //清除缓存
public void clearCache() { if (this.imageCache.size() > 0) { this.imageCache.clear();
} } } }
以下是layout主文件:
<span style="font-size:14px;"><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"
android:paddingBottom="@dimen/activity_vertical_margin"
android:paddingLeft="@dimen/activity_horizontal_margin"
android:paddingRight="@dimen/activity_horizontal_margin"
android:paddingTop="@dimen/activity_vertical_margin" > <RelativeLayout
android:layout_width="fill_parent"
android:layout_height="fill_parent" > <android.support.v4.view.ViewPager
android:id="@+id/view_pager"
android:layout_width="wrap_content"
android:layout_height="wrap_content" >
</android.support.v4.view.ViewPager> <LinearLayout
android:id="@+id/indicator"
android:layout_width="fill_parent"
android:layout_height="100px"
android:layout_marginTop="500px"
android:gravity="center_horizontal"
android:orientation="horizontal" >
</LinearLayout> </RelativeLayout> </LinearLayout>
</span>
以下是每一条item文件:
<span style="font-size:14px;"><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"
android:paddingBottom="@dimen/activity_vertical_margin"
android:paddingLeft="@dimen/activity_horizontal_margin"
android:paddingRight="@dimen/activity_horizontal_margin"
android:paddingTop="@dimen/activity_vertical_margin"
android:orientation="vertical" > <TextView
android:id="@+id/text_view"
android:layout_width="fill_parent"
android:layout_height="wrap_content"/> <ImageView
android:id="@+id/image"
android:layout_width="fill_parent"
android:layout_height="wrap_content"
/> </LinearLayout></span>
版权声明:本文博客原创文章。博客,未经同意,不得转载。
Android:ViewPager详细解释(异步网络负载图片,有图片缓存,)并与导航点的更多相关文章
- Android slidingmenu详细解释 滑动的优化
Android slidingmenu 详细解释 性能优化 转载请注明: http://blog.csdn.net/aaawqqq 简单介绍 SlidingMenu 是github 上Androi ...
- Android批量图片加载经典系列——使用二级缓存、异步网络负载形象
一.问题描写叙述 Android应用中常常涉及从网络中载入大量图片,为提升载入速度和效率,降低网络流量都会採用二级缓存和异步载入机制.所谓二级缓存就是通过先从内存中获取.再从文件里获取,最后才会訪问网 ...
- Android Asynchronous Http Client-Android异步网络请求客户端接口
1.简介 Android中网络请求一般使用Apache HTTP Client或者采用HttpURLConnect,但是直接使用这两个类库需要写大量的代码才能完成网络post和get请求,而使用and ...
- android ViewPager具体解释
Viewpager 在android界面布局中属于经常使用类型 ,它能够做导航,页面菜单,进入软件是的欢迎界面 等等.比方今最流行的几款手机软件 ,QQ,微信,微博 等 ,其主界面 都用到了View ...
- Android Fragment——详细解释
1.Fragment概述 在一个Activity中. Fragment代表UI的一个部分或者一个行为.一个Activity能够结合多个Fragment对象,也能够在多个activity中使用同样Fra ...
- 详细解释如何通过Android自带的方式来实现图片的裁剪——原理分析+解决方案
我们很多时候需要进行图片的裁剪,其实这个功能在android系统中已经有一套解决方案了,虽然界面和效果并不是很优秀但功能毫无疑问是完美实现了.至于,不用自带的方案怎么做自定义,这个就是后话了.本篇主要 ...
- android优化从网络中加载图片速度。。
从网络中加载图片主要要注意两个方面的问题: 1.内存管理:图片占的内存很大,假如图片数量多,很容易让系统抛出out of memory的异常. 同时我们也要注意不同android版本中内存管理的区别. ...
- Android之使用Android-AQuery异步加载图片(一)
第一节:转载地址(http://www.cnblogs.com/lee0oo0/archive/2012/10/25/2738299.html) // 必须实现AQuery这个类 AQuery aq ...
- Android中的异步网络请求
本篇文章我们来一起写一个最基本的Android异步网络请求框架,借此来了解下Android中网络请求的相关姿势.由于个人水平有限,文中难免存在疏忽和谬误,希望大家可以指出,谢谢大家:) 1. 同步网络 ...
随机推荐
- sql语句中单引号嵌套问题
在sql语句中,我们难免会用到单引号嵌套的时候,但是直接嵌套肯定是不行的,java中用反斜杠做转义符也是不行的,在sql中是用单引号来做转义符的. 比如下面例子是存储过程里查询时的语句示例 exec ...
- HTML与XML总结
阅览<孙欣HTML>和<刘炜XML>过了一段时间,在这里学到的内容用思维导图来概括. HTML与XML都是标记语言. 同样点: HTML文档与XML文档有类似的结构. 前者是( ...
- 【原创】纯OO:从设计到编码写一个FlappyBird (二)
第一部分请点这里. 续结前文,本文将实现Game类. 首先是实例变量.由上次的类图可以看出,Game类首先得具有如下实例变量: 0.Judge judge;1.SimpleDraw draw; // ...
- Leetcode:minimum_depth_of_binary_tree解决问题的方法
一. 称号 并寻求最深的二元相似.给定的二进制树.求其最小深度. 最小深度是沿从根节点,到叶节点最短的路径. 二. 分析 当我看到这个题目时.我直接将最深二叉树的代码略微改了下,把ma ...
- String类疑虑
Java String类疑虑: 创 拼接 String是java的经常使用类之中的一个,本质是字符数组char[].String类是final类,不可被继承. 关于String的创建,能够通过new来 ...
- 常用Android开源框架
1.volley 项目地址 https://github.com/smanikandan14/Volley-demo (1) JSON,异步下载图片: (2) 网络请求的排序(scheduli ...
- NET开发者部署React-Native
NET开发者部署React-Native 前情摘要 众所周知,有人说.net可以用Xamrian,呵呵,不习惯收费的好么?搞.Net的人设置一次java的环境变量,可能都觉得实在太麻烦了,可能是因为这 ...
- 几款开源ESB总线的比较(转)
现有的开源ESB总线中,自从2003年第一个开源总线Mule出现后,现在已经是百花争鸣的景象了.现在我就对现有的各种开源ESB总线依据性能.可扩展性.资料文档完整程度以及整合难易程度等方面展开. CX ...
- Singleton模式线程相关的(C\C++)
这种需求的最新发展. 我需要一个静态类,无论地方,我可以在线程中调用它public功能对应的功能已经完成. 这个静态类会调用我初始化给它的一个指针,这个指针是与线程一一相应的: 准确来说这样的模式应该 ...
- Myeclipse 10/2014 配置插件(svn、maven、properties、velocity)方法
一.构造SVN具体说明 什么是SVN? 管理软件开发过程中的版本控制工具. 以下会以两种方式来介绍怎么安装svn,myeclipse安装SVN插件步骤.以myeclipse 2014为例,第一种是最常 ...