android瀑布流简单实现原理
- - ITeye博客网上关于android瀑布流的例子一大堆,但是很多都是很复杂,对于新手来说有一定的难度. 原理很简单,就是异步下载图片,把图片addView到ScrollView(因为可以上下一直拖动)中,你需要屏幕显示几列就在ScrollView中放置几个LinearLayout,. 下面我就一个简单的例子来讲解android瀑布流的用法,样子很丑就不上图了.
网上关于android瀑布流的例子一大堆,但是很多都是很复杂,对于新手来说有一定的难度。
原理很简单,就是异步下载图片,把图片addView到ScrollView(因为可以上下一直拖动)中,你需要屏幕显示几列就在ScrollView中放置几个LinearLayout,
下面我就一个简单的例子来讲解android瀑布流的用法,样子很丑就不上图了。。
1、在xml布局文件:很简单就是
<ScrollView xmlns:android="http://schemas.android.com/apk/res/android" android:layout_width="fill_parent" android:layout_height="wrap_content" android:id="@+id/scrollview"> <LinearLayout android:orientation="horizontal" android:layout_width="fill_parent" android:layout_height="wrap_content"> <LinearLayout android:id="@+id/left" android:orientation="vertical" android:layout_width="fill_parent" android:layout_height="wrap_content" > </LinearLayout> <LinearLayout android:id="@+id/right" android:orientation="vertical" android:layout_width="fill_parent" android:layout_height="wrap_content"> </LinearLayout> </LinearLayout> </ScrollView>
2、在java代码中:
先声明几个变量,其中imagePathStr数组用来存图片的链接
private LinearLayout leftLayout; private LinearLayout rightLayout; private String[] imagePathStr = { "http://www.cf69.com/Upfiles/BeyondPic/2010-08/20108175740983313.jpg", "http://www.syfff.com/UploadFile/pic/2008122163204.jpg", "http://pic.newssc.org/0/10/34/32/10343297_564251.jpg", "http://ent.hangzhou.com.cn/images/20090311/zym2009031323.jpg", "http://a4.att.hudong.com/86/60/01300000013093119087608457965.jpg", "http://file.sdteacher.gov.cn/upload/gz0901/images/0907/22/110437191.jpg", "http://www.fun9.cn/uploadfile/starpic/uploadpics/200910/20091008090155126.jpg", "http://img3.yxlady.com/yl/UploadFiles_5361/20110820/20110820120609469.jpg", "http://news.sznews.com/content/images/site3/20070827/001558d90baa083c6da20d.jpg", "http://henan.sinaimg.cn/cr/2010/0824/2297073692.jpg", "http://www.cf69.com/Upfiles/BeyondPic/2010-08/20108175740983313.jpg", "http://www.syfff.com/UploadFile/pic/2008122163204.jpg", "http://pic.newssc.org/0/10/34/32/10343297_564251.jpg", "http://ent.hangzhou.com.cn/images/20090311/zym2009031323.jpg", "http://a4.att.hudong.com/86/60/01300000013093119087608457965.jpg", "http://file.sdteacher.gov.cn/upload/gz0901/images/0907/22/110437191.jpg", "http://www.fun9.cn/uploadfile/starpic/uploadpics/200910/20091008090155126.jpg", "http://img3.yxlady.com/yl/UploadFiles_5361/20110820/20110820120609469.jpg", "http://news.sznews.com/content/images/site3/20070827/001558d90baa083c6da20d.jpg", "http://henan.sinaimg.cn/cr/2010/0824/2297073692.jpg" };
其次,在oncreate()中采用异步加载图片的方法把获取到的Drawable添加到左右两栏的LinearLayout中:
@Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_main); leftLayout=(LinearLayout) findViewById(R.id.left); rightLayout=(LinearLayout) findViewById(R.id.right); int j=0; for (int i = 0; i < imagePathStr.length; i++) { addToAsynLoadImage(imagePathStr[i],j,i); j++; if(j<=2){ j=0; } } }
addToAsynLoadImage() 方法如下,每次加载一个图片就创建一个ImageView,然后把ImageView加到LinearLayout中:
private void addToAsynLoadImage(String imageUrl, int j, int i) { ImageView imageView=new ImageView(this); imageView.setLayoutParams(new LayoutParams(LayoutParams.FILL_PARENT,LayoutParams.WRAP_CONTENT)); imageView.setTag(i); new ImageDownloadAsynTask(MainActivity.this,imageUrl,imageView).execute(null); if(j==0){ leftLayout.addView(imageView); }else if(j==1){ rightLayout.addView(imageView); } }
ImageDownloadAsynTask()方法继承自AsyncTask<Params, Progress, Result>,
这个类有三个参数,4个步骤(begin,doinbackground,processProgress,end)
最后一个参数是在doinbackground()中返回的结果,另外还有onPreExecute()、onPostExecute()
public class ImageDownloadAsynTask extends AsyncTask<Void, Void, Drawable>{ private Context context; private String imageUrl; private ImageView imageView; private String sdPath="/sdcard/netImages"; ProgressDialog progressDialog; public ImageDownloadAsynTask(Context context, String imageUrl,ImageView imageView) { this.context=context; this.imageUrl=imageUrl; this.imageView=imageView; } /* 后台执行,比较耗时的操作都可以放在这里。注意这里不能直接操作UI * 不需要传入什么参数,返回一个Drawable */ @Override protected Drawable doInBackground(Void... params) { String filename=sdPath+imageUrl.substring(imageUrl.lastIndexOf("/")); File file=new File(filename); if(file.exists()==true){ Bitmap bitmap=BitmapFactory.decodeFile(filename); BitmapDrawable bitmapDrawable=new BitmapDrawable(bitmap); return bitmapDrawable; }else{ try { URL url=new URL(imageUrl); URLConnection connection=url.openConnection(); connection.setDoInput(true);// 使用 URL 连接进行输入 connection.connect(); InputStream is = connection.getInputStream(); Bitmap b=BitmapFactory.decodeStream(is); BitmapDrawable bd=new BitmapDrawable(b); saveFile(bd,filename); // connection.getContent(); return bd; } catch (MalformedURLException e) { e.printStackTrace(); } catch (IOException e) { e.printStackTrace(); } } return null; } /**通过outPutStream、bitmap.compress(),flush()把图片保存到指定路径 * @param bd * @param filename */ private void saveFile(BitmapDrawable bd, String filename) { File file = new File(sdPath); if(!file.exists()){ file.mkdir(); } File f=new File(filename); try { BufferedOutputStream bos = new BufferedOutputStream(new FileOutputStream(f)); Bitmap b=bd.getBitmap(); b.compress(Bitmap.CompressFormat.JPEG, 80, bos); bos.flush(); bos.close(); } catch (FileNotFoundException e) { e.printStackTrace(); } catch (IOException e) { e.printStackTrace(); } } @Override protected void onPreExecute() { super.onPreExecute(); progressDialog.show(context, "","正在下载图片。。。"); } /** * 相当于Handler 处理UI的方式,在这里面可以使用在doInBackground 得到的结果处理操作UI。 * 此方法在主线程执行,任务执行的结果作为此方法的参数返回 */ @Override protected void onPostExecute(Drawable result) { super.onPostExecute(result); if(result!=null){//如果doInBackground()获取的结果不为空 imageView.setBackgroundDrawable(result);//那么就在这一步更新UI } progressDialog.dismiss(); } }