楼主: 熊猫儿

[转载] 【Android开发网上的一些重要知识点[经验分享]。。】

[复制链接]
论坛徽章:
1682
九尾狐狸
日期:2012-09-19 11:12:55九尾狐狸
日期:2012-09-19 11:12:55九尾狐狸
日期:2012-09-27 15:37:10九尾狐狸
日期:2012-09-19 11:12:55九尾狐狸
日期:2012-09-19 11:12:55九尾狐狸
日期:2012-09-19 11:12:55九尾狐狸
日期:2012-09-19 11:12:55九尾狐狸
日期:2012-09-19 11:12:55玉石琵琶
日期:2014-06-26 16:52:29玉石琵琶
日期:2014-06-26 16:52:29
971#
 楼主| 发表于 2013-8-14 21:42 | 只看该作者
  @Override  
    public void onScroll(AbsListView view, int firstVisibleItem, int visibleItemCount,  
            int totalItemCount) {  
        mFirstVisibleItem = firstVisibleItem;  
        mVisibleItemCount = visibleItemCount;  
        // 下载的任务应该由onScrollStateChanged里调用,但首次进入程序时onScrollStateChanged并不会调用,  
        // 因此在这里为首次进入程序开启下载任务。  
        if (isFirstEnter && visibleItemCount > 0) {  
            loadBitmaps(firstVisibleItem, visibleItemCount);  
            isFirstEnter = false;  
        }  
    }  
  
    /**
     * 加载Bitmap对象。此方法会在LruCache中检查所有屏幕中可见的ImageView的Bitmap对象,
     * 如果发现任何一个ImageView的Bitmap对象不在缓存中,就会开启异步线程去下载图片。
     *  
     * @param firstVisibleItem
     *            第一个可见的ImageView的下标
     * @param visibleItemCount
     *            屏幕中总共可见的元素数
     */  
    private void loadBitmaps(int firstVisibleItem, int visibleItemCount) {  
        try {  
            for (int i = firstVisibleItem; i < firstVisibleItem + visibleItemCount; i++) {  
                String imageUrl = Images.imageThumbUrls[i];  
                Bitmap bitmap = getBitmapFromMemoryCache(imageUrl);  
                if (bitmap == null) {  
                    BitmapWorkerTask task = new BitmapWorkerTask();  
                    taskCollection.add(task);  
                    task.execute(imageUrl);  
                } else {  
                    ImageView imageView = (ImageView) mPhotoWall.findViewWithTag(imageUrl);  
                    if (imageView != null && bitmap != null) {  
                        imageView.setImageBitmap(bitmap);  
                    }  
                }  
            }  
        } catch (Exception e) {  
            e.printStackTrace();  
        }  
    }  
  

使用道具 举报

回复
论坛徽章:
1682
九尾狐狸
日期:2012-09-19 11:12:55九尾狐狸
日期:2012-09-19 11:12:55九尾狐狸
日期:2012-09-27 15:37:10九尾狐狸
日期:2012-09-19 11:12:55九尾狐狸
日期:2012-09-19 11:12:55九尾狐狸
日期:2012-09-19 11:12:55九尾狐狸
日期:2012-09-19 11:12:55九尾狐狸
日期:2012-09-19 11:12:55玉石琵琶
日期:2014-06-26 16:52:29玉石琵琶
日期:2014-06-26 16:52:29
972#
 楼主| 发表于 2013-8-14 21:42 | 只看该作者
   /**
     * 取消所有正在下载或等待下载的任务。
     */  
    public void cancelAllTasks() {  
        if (taskCollection != null) {  
            for (BitmapWorkerTask task : taskCollection) {  
                task.cancel(false);  
            }  
        }  
    }  
  
    /**
     * 异步下载图片的任务。
     *  
     * @author guolin
     */  
    class BitmapWorkerTask extends AsyncTask<String, Void, Bitmap> {  
  
        /**
         * 图片的URL地址
         */  
        private String imageUrl;  
  
        @Override  
        protected Bitmap doInBackground(String... params) {  
            imageUrl = params[0];  
            // 在后台开始下载图片  
            Bitmap bitmap = downloadBitmap(params[0]);  
            if (bitmap != null) {  
                // 图片下载完成后缓存到LrcCache中  
                addBitmapToMemoryCache(params[0], bitmap);  
            }  
            return bitmap;  
        }  
  
        @Override  
        protected void onPostExecute(Bitmap bitmap) {  
            super.onPostExecute(bitmap);  
            // 根据Tag找到相应的ImageView控件,将下载好的图片显示出来。  
            ImageView imageView = (ImageView) mPhotoWall.findViewWithTag(imageUrl);  
            if (imageView != null && bitmap != null) {  
                imageView.setImageBitmap(bitmap);  
            }  
            taskCollection.remove(this);  
        }  
  

使用道具 举报

回复
论坛徽章:
1682
九尾狐狸
日期:2012-09-19 11:12:55九尾狐狸
日期:2012-09-19 11:12:55九尾狐狸
日期:2012-09-27 15:37:10九尾狐狸
日期:2012-09-19 11:12:55九尾狐狸
日期:2012-09-19 11:12:55九尾狐狸
日期:2012-09-19 11:12:55九尾狐狸
日期:2012-09-19 11:12:55九尾狐狸
日期:2012-09-19 11:12:55玉石琵琶
日期:2014-06-26 16:52:29玉石琵琶
日期:2014-06-26 16:52:29
973#
 楼主| 发表于 2013-8-15 16:37 | 只看该作者
/**
         * 建立HTTP请求,并获取Bitmap对象。
         *  
         * @param imageUrl
         *            图片的URL地址
         * @return 解析后的Bitmap对象
         */  
        private Bitmap downloadBitmap(String imageUrl) {  
            Bitmap bitmap = null;  
            HttpURLConnection con = null;  
            try {  
                URL url = new URL(imageUrl);  
                con = (HttpURLConnection) url.openConnection();  
                con.setConnectTimeout(5 * 1000);  
                con.setReadTimeout(10 * 1000);  
                con.setDoInput(true);  
                con.setDoOutput(true);  
                bitmap = BitmapFactory.decodeStream(con.getInputStream());  
            } catch (Exception e) {  
                e.printStackTrace();  
            } finally {  
                if (con != null) {  
                    con.disconnect();  
                }  
            }  
            return bitmap;  
        }  
  
    }  
  
}  
PhotoWallAdapter是整个照片墙程序中最关键的一个类了,这里我来重点给大家讲解一下。首先在PhotoWallAdapter的构造函数中,我们初始化了LruCache类,并设置了最大缓存容量为程序最大可用内存的1/8,接下来又为GridView注册了一个滚动监听器。然后在getView()方法中,我们为每个ImageView设置了一个唯一的Tag,这个Tag的作用是为了后面能够准确地找回这个ImageView,不然异步加载图片会出现乱序的情况。之后调用了setImageView()方法为ImageView设置一张图片,这个方法首先会从LruCache缓存中查找是否已经缓存了这张图片,如果成功找到则将缓存中的图片显示在ImageView上,否则就显示一张默认的空图片。

使用道具 举报

回复
论坛徽章:
1682
九尾狐狸
日期:2012-09-19 11:12:55九尾狐狸
日期:2012-09-19 11:12:55九尾狐狸
日期:2012-09-27 15:37:10九尾狐狸
日期:2012-09-19 11:12:55九尾狐狸
日期:2012-09-19 11:12:55九尾狐狸
日期:2012-09-19 11:12:55九尾狐狸
日期:2012-09-19 11:12:55九尾狐狸
日期:2012-09-19 11:12:55玉石琵琶
日期:2014-06-26 16:52:29玉石琵琶
日期:2014-06-26 16:52:29
974#
 楼主| 发表于 2013-8-15 16:37 | 只看该作者
看了半天,那到底是在哪里下载图片的呢?这是在GridView的滚动监听器中进行的,在onScrollStateChanged()方法中,我们对GridView的滚动状态进行了判断,如果当前GridView是静止的,则调用loadBitmaps()方法去下载图片,如果GridView正在滚动,则取消掉所有下载任务,这样可以保证GridView滚动的流畅性。在loadBitmaps()方法中,我们为屏幕上所有可见的GridView子元素开启了一个线程去执行下载任务,下载成功后将图片存储到LruCache当中,然后通过Tag找到相应的ImageView控件,把下载好的图片显示出来。
由于我们使用了LruCache来缓存图片,所以不需要担心内存溢出的情况,当LruCache中存储图片的总大小达到容量上限的时候,会自动把最近最少使用的图片从缓存中移除。
最后新建或打开MainActivity作为程序的主Activity,代码如下所示:

[java] view plaincopy
public class MainActivity extends Activity {  
  
    /**
     * 用于展示照片墙的GridView
     */  
    private GridView mPhotoWall;  
  
    /**
     * GridView的适配器
     */  
    private PhotoWallAdapter adapter;  
  
    @Override  
    protected void onCreate(Bundle savedInstanceState) {  
        super.onCreate(savedInstanceState);  
        setContentView(R.layout.activity_main);  
        mPhotoWall = (GridView) findViewById(R.id.photo_wall);  
        adapter = new PhotoWallAdapter(this, 0, Images.imageThumbUrls, mPhotoWall);  
        mPhotoWall.setAdapter(adapter);  
    }  
  
    @Override  
    protected void onDestroy() {  
        super.onDestroy();  
        // 退出程序时结束所有的下载任务  
        adapter.cancelAllTasks();  
    }  
  
}  

使用道具 举报

回复
论坛徽章:
1682
九尾狐狸
日期:2012-09-19 11:12:55九尾狐狸
日期:2012-09-19 11:12:55九尾狐狸
日期:2012-09-27 15:37:10九尾狐狸
日期:2012-09-19 11:12:55九尾狐狸
日期:2012-09-19 11:12:55九尾狐狸
日期:2012-09-19 11:12:55九尾狐狸
日期:2012-09-19 11:12:55九尾狐狸
日期:2012-09-19 11:12:55玉石琵琶
日期:2014-06-26 16:52:29玉石琵琶
日期:2014-06-26 16:52:29
975#
 楼主| 发表于 2013-8-15 16:37 | 只看该作者
MainActivity中的代码非常简单,没什么需要说明的了,在Activity被销毁时取消掉了所有的下载任务,避免程序在后台耗费流量。另外由于我们使用了网络功能,别忘了在AndroidManifest.xml中加入网络权限的声明。

现在可以运行一下程序了,效果如下图所示:

                                          

可以看到,滚动照片墙,会异步加载图片到相应的ImageView上。随着加载图片的增多,会释放掉一些之前加载过的图片,你多滚动几次就可以看得出了。另外为了能让大家明显看出图片的释放情况,我在这个程序中没有使用本地缓存,所有被释放掉的图片再次显示需要从网络上再下载一遍。在实际的项目中配合适当的本地缓存效果会更好。

打开DDMS,我们可以发现,由于有LruCache帮我们管理图片缓存,不管如何滚动照片墙,程序内存始终会保持在一个合理的范围内。


好了,今天的讲解到此结束,有疑问的朋友请在下面留言。


使用道具 举报

回复
论坛徽章:
1682
九尾狐狸
日期:2012-09-19 11:12:55九尾狐狸
日期:2012-09-19 11:12:55九尾狐狸
日期:2012-09-27 15:37:10九尾狐狸
日期:2012-09-19 11:12:55九尾狐狸
日期:2012-09-19 11:12:55九尾狐狸
日期:2012-09-19 11:12:55九尾狐狸
日期:2012-09-19 11:12:55九尾狐狸
日期:2012-09-19 11:12:55玉石琵琶
日期:2014-06-26 16:52:29玉石琵琶
日期:2014-06-26 16:52:29
976#
 楼主| 发表于 2013-8-15 16:38 | 只看该作者
Android二维码功能实现,在程序内嵌入ZXing项目
分类: Android精华教程 2013-08-09 08:34 1316人阅读 评论(11) 收藏 举报
Android二维码ZXing扫描zebra crossing
转载请注明出处:http://blog.csdn.net/guolin_blog/article/details/9526247

最近二维码真是越来越火了,随便电视上、网络上、商场里,到处都是二维码。而内嵌二维码扫描功能的软件也越来越多,QQ、微信、UC浏览器等等应用都可以对着二维码扫一扫,感觉我们自己的应用里不加上二维码扫描功能,都跟不上时代潮流了。所以今天我就将带着大家一起,在我们自己的程序里加入二维码扫描的功能。

不过,二维码功能如果真要做起来还是非常复杂的,从零开始实现不太现实,比较好的做法就是借助现有的开源项目。目前在二维码这一领域名气最大的开源项目就是ZXing了(Zebra Crossing),它提供了多个平台的二维码扫描解决方案,开源项目地址是 https://code.google.com/p/zxing/

虽说网上已经有现成的开源项目了,不过关于ZXing的文档和教程好像还比较少,因此还是有不少朋友并不知道在项目中该如何引入ZXing的,这里我就带着大家一步步地实现,相信每个人在看完本篇文章后都可以在自己的项目中实现二维码扫描功能。

首先,我们需要下载ZXing项目所依赖的Jar包的源码。

下载地址是 http://repo1.maven.org/maven2/co ... ore-2.2-sources.jar

然后我们再来下载ZXing项目,下载地址是 https://zxing.googlecode.com/files/ZXing-2.2.zip

建议使用迅雷下载,因为Google Code和Maven的访问在国内不稳定,经常出现断联的情况,使用迅雷可以保证文件的完整性。

使用道具 举报

回复
论坛徽章:
1682
九尾狐狸
日期:2012-09-19 11:12:55九尾狐狸
日期:2012-09-19 11:12:55九尾狐狸
日期:2012-09-27 15:37:10九尾狐狸
日期:2012-09-19 11:12:55九尾狐狸
日期:2012-09-19 11:12:55九尾狐狸
日期:2012-09-19 11:12:55九尾狐狸
日期:2012-09-19 11:12:55九尾狐狸
日期:2012-09-19 11:12:55玉石琵琶
日期:2014-06-26 16:52:29玉石琵琶
日期:2014-06-26 16:52:29
977#
 楼主| 发表于 2013-8-15 16:39 | 只看该作者

另外,经过我的测试,在ZXing项目中直接导入core-2.2的Jar包是无法正常运行的,所以我们只能通过将core-2.2的源码加入到ZXing项目中来实现。下载好以上两个文件后,先解压core-2.2-sources.jar文件,解压之后的目录结构如下图所示:

                                    

然后解压ZXing-2.2这个压缩包,里面可以看到各种平台下的ZXing项目源码,我们进入到android文件夹的src目录下,将core-2.2-sources中的源码拷贝进来。拷贝之后android文件夹下的目录结构如下图所示:

                           


使用道具 举报

回复
论坛徽章:
1682
九尾狐狸
日期:2012-09-19 11:12:55九尾狐狸
日期:2012-09-19 11:12:55九尾狐狸
日期:2012-09-27 15:37:10九尾狐狸
日期:2012-09-19 11:12:55九尾狐狸
日期:2012-09-19 11:12:55九尾狐狸
日期:2012-09-19 11:12:55九尾狐狸
日期:2012-09-19 11:12:55九尾狐狸
日期:2012-09-19 11:12:55玉石琵琶
日期:2014-06-26 16:52:29玉石琵琶
日期:2014-06-26 16:52:29
978#
 楼主| 发表于 2013-8-16 10:49 | 只看该作者

这样准备工作已经完成了,现在我们新建一个Android项目ScannerTest,项目使用Android 4.0的API。

然后将上图中src目录下的所有文件全部复制,粘贴到我们ScannerTest项目的src目录下,完成后目录结构如下图所示:

                           

拷贝完了代码,现在该拷贝资源了,展开ZXing项目android文件夹下的res目录,将drawable文件夹、layout文件夹、menu文件夹、raw文件夹、values文件夹以及xml文件夹中的内容都拷贝到ScannerTest项目的res目录下,注意有冲突的部分要小心解决,比如两个values文件夹中都有string.xml文件,要将它们的内容进行合并,不能只是简单地覆盖。


使用道具 举报

回复
论坛徽章:
1682
九尾狐狸
日期:2012-09-19 11:12:55九尾狐狸
日期:2012-09-19 11:12:55九尾狐狸
日期:2012-09-27 15:37:10九尾狐狸
日期:2012-09-19 11:12:55九尾狐狸
日期:2012-09-19 11:12:55九尾狐狸
日期:2012-09-19 11:12:55九尾狐狸
日期:2012-09-19 11:12:55九尾狐狸
日期:2012-09-19 11:12:55玉石琵琶
日期:2014-06-26 16:52:29玉石琵琶
日期:2014-06-26 16:52:29
979#
 楼主| 发表于 2013-8-16 10:51 | 只看该作者
然后我们还需要将AndroidManifest中的内容进行合并,注意ZXing Android项目下的AndroidManifest在声明Activity时用的都是简写,而现在由于项目包名变了,再使用简写会出现找不到活动的情况,因此所有的简写都要改成完整类名,例如.CaptureActivity要改成com.google.zxing.client.android.CaptureActivity。另外ZXing Android项目下的主活动是CaptureActivity,这里我们需要将主活动的声明删除掉,因为ScannerTest项目中主活动是MainActivity。合并后的AndroidManifest中的代码如下所示:

[html] view plaincopy
<?xml version="1.0" encoding="utf-8"?>  
<manifest xmlns:android="http://schemas.android.com/apk/res/android"  
    package="com.example.scannertest"  
    android:versionCode="1"  
    android:versionName="1.0" >  
  
    <uses-permission android:name="android.permission.CAMERA" />  
    <uses-permission android:name="android.permission.INTERNET" />  
    <uses-permission android:name="android.permission.VIBRATE" />  
    <uses-permission android:name="android.permission.FLASHLIGHT" />  
    <uses-permission android:name="android.permission.READ_CONTACTS" />  
    <uses-permission android:name="com.android.browser.permission.READ_HISTORY_BOOKMARKS" />  
    <uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE" />  
    <uses-permission android:name="android.permission.CHANGE_WIFI_STATE" />  
    <uses-permission android:name="android.permission.ACCESS_WIFI_STATE" />  
  
    <uses-sdk  
        android:minSdkVersion="14"  
        android:targetSdkVersion="17" />  
  
    <uses-feature  
        android:name="android.hardware.camera"  
        android:required="false" />  
    <uses-feature  
        android:name="android.hardware.camera.front"  
        android:required="false" />  
    <uses-feature  
        android:name="android.hardware.camera.autofocus"  
        android:required="false" />  
    <uses-feature  
        android:name="android.hardware.camera.flash"  
        android:required="false" />  
    <uses-feature android:name="android.hardware.screen.landscape" />  
    <uses-feature  
        android:name="android.hardware.wifi"  
        android:required="false" />  
    <uses-feature android:name="android.hardware.touchscreen" />  
  

使用道具 举报

回复
论坛徽章:
1682
九尾狐狸
日期:2012-09-19 11:12:55九尾狐狸
日期:2012-09-19 11:12:55九尾狐狸
日期:2012-09-27 15:37:10九尾狐狸
日期:2012-09-19 11:12:55九尾狐狸
日期:2012-09-19 11:12:55九尾狐狸
日期:2012-09-19 11:12:55九尾狐狸
日期:2012-09-19 11:12:55九尾狐狸
日期:2012-09-19 11:12:55玉石琵琶
日期:2014-06-26 16:52:29玉石琵琶
日期:2014-06-26 16:52:29
980#
 楼主| 发表于 2013-8-16 10:52 | 只看该作者
<supports-screens  
        android:anyDensity="true"  
        android:largeScreens="true"  
        android:normalScreens="true"  
        android:smallScreens="true"  
        android:xlargeScreens="true" />  
  
    <application  
        android:allowBackup="true"  
        android:icon="@drawable/ic_launcher"  
        android:label="@string/app_name"  
        android:theme="@style/AppTheme" >  
        <activity  
            android:name="com.example.scannertest.MainActivity"  
            android:label="@string/app_name" >  
            <intent-filter>  
                <action android:name="android.intent.action.MAIN" />  
  
                <category android:name="android.intent.category.LAUNCHER" />  
            </intent-filter>  
        </activity>  
        <activity  
            android:name="com.google.zxing.client.android.CaptureActivity"  
            android:clearTaskOnLaunch="true"  
            android:configChanges="orientation|keyboardHidden"  
            android:screenOrientation="landscape"  
            android:stateNotNeeded="true"  
            android:theme="@android:style/Theme.NoTitleBar.Fullscreen"  
            android:windowSoftInputMode="stateAlwaysHidden" >  
            <intent-filter>  
                <action android:name="com.google.zxing.client.android.SCAN" />  
                <category android:name="android.intent.category.DEFAULT" />  
            </intent-filter>  
            <intent-filter>  
                <action android:name="android.intent.action.VIEW" />  
                <category android:name="android.intent.category.DEFAULT" />  
                <category android:name="android.intent.category.BROWSABLE" />  
                <data  
                    android:host="zxing.appspot.com"  
                    androidath="/scan"  
                    android:scheme="http" />  
            </intent-filter>  
            <intent-filter>  
                <action android:name="android.intent.action.VIEW" />  
                <category android:name="android.intent.category.DEFAULT" />  
                <category android:name="android.intent.category.BROWSABLE" />  
                <data  
                    android:host="www.google.com"  
                    androidath="/m/products/scan"  
                    android:scheme="http" />  
            </intent-filter>  

使用道具 举报

回复

您需要登录后才可以回帖 登录 | 注册

本版积分规则 发表回复

TOP技术积分榜 社区积分榜 徽章 团队 统计 知识索引树 积分竞拍 文本模式 帮助
  ITPUB首页 | ITPUB论坛 | 数据库技术 | 企业信息化 | 开发技术 | 微软技术 | 软件工程与项目管理 | IBM技术园地 | 行业纵向讨论 | IT招聘 | IT文档
  ChinaUnix | ChinaUnix博客 | ChinaUnix论坛
CopyRight 1999-2011 itpub.net All Right Reserved. 北京盛拓优讯信息技术有限公司版权所有 联系我们 未成年人举报专区 
京ICP备16024965号-8  北京市公安局海淀分局网监中心备案编号:11010802021510 广播电视节目制作经营许可证:编号(京)字第1149号
  
快速回复 返回顶部 返回列表