Android一些经常使用知识和代码(不断更新)

1.如何调用外部图片选择器,选择图片并返回结果javascript

                //获取照片
                Intent in = new Intent(Intent.ACTION_GET_CONTENT);
                in.setType("image/*");
                startActivityForResult(in, 0);html

而后Activity中还要加上一个结果返回接收java

    @Override
    protected void onActivityResult(int requestCode, int resultCode,
            Intent intent)
    {
        super.onActivityResult(requestCode, resultCode, intent);

        System.out.println(intent.getDataString());
        ImageView view = new ImageView(this);
        view.setImageURI(intent.getData());
        ((LinearLayout)findViewById(R.id.layout)).addView(view);
        
        System.out.println(requestCode);
    }android


2.如何调用Google Web Search?
其实android提供了一个很方便的调用方式,就是用Intent去调用系统的Activity,代码以下:web

                //搜索
                Intent search = new Intent(Intent.ACTION_WEB_SEARCH);
                search.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
                search.putExtra(SearchManager.QUERY, "tigertian");
                final Bundle appData = getIntent().getBundleExtra(SearchManager.APP_DATA);
                if (appData != null) {
                    search.putExtra(SearchManager.APP_DATA, appData);
                }
                
                startActivity(search);数据库

执行这段代码以后,就会跳转到google的网站并自动搜索与tigertian相关的记录

3.为何WebView在进行loadUrl的时候,有时候会弹出Android的自带浏览器进行浏览?
被访问页面若是不带跳转(Redirect)是不会弹出自带浏览器的。但若是带跳转(Redirect)的话WebView是作不到的,因此他会调用相应的浏览器进行跳转访问。

4.有按钮的列表项为能够点击吗?
能够,可是须要将按钮的Focusable属性置为false,Checkbox等控件同理。 

5.android:layout_weight什么时候有效果?
 <AutoCompleteTextView android:layout_height="wrap_content"  android:layout_weight="2"
   android:layout_width="wrap_content" android:completionThreshold="1"
   android:id="@+id/AutoCompleteSearchGame"></AutoCompleteTextView>
当layout_height和layout_width都未wrap_content的时候有效果。 

六、若是调用浏览器?
使用startActivity传递这个intent就能够调用浏览器了new Intent(Intent.ACTION_VIEW, Uri.parse(url)) 浏览器

 

读取全部电话号码:缓存

  1、PhoneLookup.CONTENT_FILTER_URI的通常用法网络

 Uri uri = Uri.withAppendedPath(PhoneLookup.CONTENT_FILTER_URI, Uri.encode(phoneNumber));
 resolver.query(uri, new String[]{PhoneLookup.DISPLAY_NAME,...多线程

    API见这里。若是直接以下使用PhoneLookup.CONTENT_FILTER_URI会报IllegalArgument Exception错

getContentResolver().query(PhoneLookup.CONTENT_FILTER_URI,...

 

  2、 技巧用法

        Cursor c = getContentResolver().query(Uri.withAppendedPath(
                PhoneLookup.CONTENT_FILTER_URI, "*"), new String[] {
                PhoneLookup._ID,
                PhoneLookup.NUMBER,
                PhoneLookup.DISPLAY_NAME,
                PhoneLookup.TYPE, PhoneLookup.LABEL }, null, null, sortOrder);

    关键是这个"*",这样就能取到全部的号码以及相关的联系人的姓名以及其余相关字段,比经过联系人再查找其号码要方便不少。

Android ListView item中有按钮(Button)不能点击或者条目不能点击的问题:

增长了按钮以后,列表条目不能点击的缘由是:须要把Button的相关属性设置成这样

android:focusable="false"

不过在开发过程当中,我有个动态获取图片并刷新列表的机制,发现每次调用完notifyDataSetChanged()方法以后Button都不能点击了,后来发现若是有图片动态加载那么每次都要从新inflate整个列表的条目,因此我干脆重载了notifyDataSetChanged()方法。

    /**
     * Recycle bitmap resources
     */
    public void recycleBitmapRes() {
        if (mConvertViews != null && !mConvertViews.isEmpty()) {
            Collection<View> views = mConvertViews.values();
            mConvertViews.clear();
            for (View view : views) {
                ImageView icon = (ImageView) view.findViewById(R.id.imgIcon);
                if (icon != null) {
                    if (icon.getDrawable() != null && icon.getDrawable() instanceof BitmapDrawable) {
                        Bitmap bitmap = ((BitmapDrawable) icon.getDrawable()).getBitmap();
                        if (bitmap != null && !bitmap.isRecycled()) {
                            bitmap.recycle();
                        }
                    }
                }
            }
        }
    }

    @Override
    public void notifyDataSetChanged(){
        //Avoiding that buttons cannot be pressed
        Utils.LogI("GameListAdapter", "notifyDataSetChanged");
        recycleBitmapRes();
        super.notifyDataSetChanged();
    }

 

 

Android弹出拨号界面和拨打电话实现:

须要使用反射机制将ITelephony反射出来进行操做。

private void dial(String number) {
        Class<TelephonyManager> c = TelephonyManager.class;
        Method getITelephonyMethod = null;
        try {
            getITelephonyMethod = c.getDeclaredMethod("getITelephony",
                    (Class[]) null);
            getITelephonyMethod.setAccessible(true);
        } catch (SecurityException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        } catch (NoSuchMethodException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        }

        try {
            TelephonyManager tManager = (TelephonyManager) getSystemService(Context.TELEPHONY_SERVICE);
            Object iTelephony;
            iTelephony = (Object) getITelephonyMethod.invoke(tManager,(Object[]) null);
            Method dial = iTelephony.getClass().getDeclaredMethod("dial", String.class);
            dial.invoke(iTelephony, number);
        } catch (IllegalArgumentException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        } catch (IllegalAccessException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        } catch (SecurityException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        } catch (NoSuchMethodException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        } catch (InvocationTargetException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        }
    }
    
    private void call(String number) {
        Class<TelephonyManager> c = TelephonyManager.class;
        Method getITelephonyMethod = null;
        try {
            getITelephonyMethod = c.getDeclaredMethod("getITelephony",
                    (Class[]) null);
            getITelephonyMethod.setAccessible(true);
        } catch (SecurityException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        } catch (NoSuchMethodException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        }

        try {
            TelephonyManager tManager = (TelephonyManager) getSystemService(Context.TELEPHONY_SERVICE);
            Object iTelephony;
            iTelephony = (Object) getITelephonyMethod.invoke(tManager,(Object[]) null);
            Method dial = iTelephony.getClass().getDeclaredMethod("call", String.class);
            dial.invoke(iTelephony, number);
        } catch (IllegalArgumentException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        } catch (IllegalAccessException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        } catch (SecurityException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        } catch (NoSuchMethodException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        } catch (InvocationTargetException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        }
    }

 

Android中短信拦截解决方案

通过测试,Android中是能够拦截短信的,解决方案以下:

package com.tigertian.sms;

import android.content.BroadcastReceiver;
import android.content.Context;
import android.content.Intent;
import android.os.Bundle;
import android.telephony.SmsMessage;

public class SMSReceiver extends BroadcastReceiver {

    @Override
    public void onReceive(Context context, Intent intent) {
        // TODO Auto-generated method stub
        System.out.println("SMSReceiver, isOrderedBroadcast()="
                + isOrderedBroadcast());
        
        Bundle bundle = intent.getExtras();
        Object messages[] = (Object[]) bundle.get("pdus");
        SmsMessage smsMessage[] = new SmsMessage[messages.length];
        for (int n = 0; n < messages.length; n++) {
            smsMessage[n] = SmsMessage.createFromPdu((byte[]) messages[n]);
            if(smsMessage[n].getMessageBody().contains("hahaha")){
                this.abortBroadcast();
            }
            System.out.println(smsMessage[n].getOriginatingAddress()+" "+smsMessage[n].getMessageBody()+" "+smsMessage[n].getIndexOnIcc());
        }
    }}

   <receiver android:name=".SMSReceiver">
            <intent-filter android:priority="10000">
                <action android:name="android.provider.Telephony.SMS_RECEIVED"></action>
                <category android:name="android.intent.category.DEFAULT" />
            </intent-filter>
        </receiver>

上面的代码是一个消息监听,监听接收短信的消息。咱们能够从控制台打印信息里面看到,他是一个OrderedBroadcast,根据这一点咱们就能够对短信机制进行拦截。如何拦截呢?首先要声明一个消息监听器,同时根据上面的配置文件须要在AndroidManifest.xml中配置好,注意它的优先级是10000,这一点很关键,由于OrderedBroadcast是根据优先级来传递消息的,优先级越高越先获取到消息,待处理完后才会传递给下一个监听器,若是当前监听器退出广播,那么后面的全部监听器都将没法收到消息。其次咱们须要实现onReceive方法,根据上面的代码,咱们能够从bundle中拿到短信内容并还原成SmsMessage,这样咱们能够根据特定条件来判断哪些是须要咱们拦截而且不要让用户知道的,哪些是咱们能够放行的。须要咱们拦截的短信,咱们能够在收到后直接abortBroadcast()(上面的代码中是判断当短信内容包含hahaha的时候直接拦截),这样系统收件箱将没法接收到该条短信,继而也就不会有notification去通知用户。至此,应用编写好以后,短信拦截功能就完成了,固然基于此还能够作一些其余功能,这方面就看需求了。注意,优先级相同,则根据包名依次传递广播。想删除收件箱中已存在的短信,请参考Android源码SmsProvider类,能够在你的应用中使用ContentProvider机制进行操做。

Application保存全局变量

class MyApp extends Application {

  private String myState;

  public String getState(){
    return myState;
  }
  public void setState(String s){
    myState = s;
  }
}

class Blah extends Activity {

  @Override
  public void onCreate(Bundle b){
    MyApp appState = ((MyApp)getApplicationContext());
    String state = appState.getState();
    
  }
}

 

<application android:name=".MyApp" 
       android:icon="@drawable/icon" 
       android:label="@string/app_name">

 

 

android异步图片加载中的图片缓存:

读取大文件流的问题:缓存
开多线程把图片从网络上荡下来之后,首先缓存至本地文件夹 //android.content.ContextWrapper.getCacheDir() android系统提供的一个存放和获得缓存文件夹的方法
而后对文件全路径截取后缀以前的内容进行MD5加密并与后缀拼成一个文件名,根据这个文件名和传入的路径构建一个文件 写一个缓存方法  判断是否存在缓存文件
若是是则返回加密后文件的Uri,若是不是则从网上下载文件并返回文件的Uri.作缓存的目的是用缓存的文件,而Uri就能够惟一标识一个文件。
public static Uri cacheFile(String path,File saveDir)throws Exception{  

  File file = new File(saveDir, MD5.getMD5(path)+ path.substring(path.lastIndexOf('.')));
    if(file.exists()){
        return Uri.fromFile(file);    
    }else{
        FileOutputStream outStream = new FileOutputStream(file);
        HttpURLConnection conn = (HttpURLConnection)new URL(path).openConnection();
        conn.setConnectTimeout(5 * 1000);
        conn.setRequestMethod("GET");
        if(conn.getResponseCode()==200){
            InputStream inStream = conn.getInputStream();
            byte[] buffer = new byte[1024];
            int len = 0;
            while( (len = inStream.read(buffer)) !=-1 ){
                outStream.write(buffer, 0, len);
            }
            outStream.close();
            inStream.close();
            return Uri.fromFile(file);
        }else{
            throw new Exception("文件下载失败!");
        }
    }
}

视频格式的压缩

l  source=source.avi

l  ffmpeg -t 600 -i $source -acodec libfaac -ab 128k -ac 2 -vcodec libx264 \

l  -vpre hq -crf 22 -threads 0 tmp.mp4 && \

l  /usr/bin/MP4Box -3gp -mtu 1450 -hint tmp.mp4 -out target.mp4

插入删除图片MediaScanner缓存问题

插入图片
当你打算在删掉时 : ContentValues values = new ContentValues();  

 values.put(Images.Media.TITLE, filename);

    values.put(Images.Media.DATE_ADDED, System.currentTimeMillis());

    values.put(Images.Media.MIME_TYPE, "image/jpeg");

    Uri uri = this.getContentResolver().insert(Images.Media.EXTERNAL_CONTENT_URI, values);

File f = new File(imageURI);

    f.delete();

在gallery中就会出现占位符 主要是由于MediaScanner有一个缓存

sendBroadcast(new Intent(Intent.ACTION_MEDIA_MOUNTED, Uri.parse("file://" + Environment.getExternalStorageDirectory())));

 

 

AndroidManifest.xml:

<intent-filter>

  <action android:name="android.intent.action.MEDIA_MOUNTED" />

  <data android:scheme="file" />

</intent-filter>

 

屏幕旋转的设置:

1.   @Override  

2.       public void onConfigurationChanged(Configuration newConfig) {  

3.           super.onConfigurationChanged(newConfig);    

4.           ImageView header = (ImageView) this.findViewById(R.id.header);    

5.           if ( newConfig.orientation == Configuration.ORIENTATION_LANDSCAPE ) {  

6.                header.setImageResource(R.drawable.header480);  

7.           }  

8.           else if ( newConfig.orientation == Configuration.ORIENTATION_PORTRAIT ) {  

9.               header.setImageResource(R.drawable.header320);    

10.         }  

11.     }  

 

ListView适配器getView()优化

public View getView(int position, View convertView, ViewGroup parent) {
ViewHolder holder;
if (convertView == null) {
convertView = mInflater.inflate(R.layout.list_item_icon_text, null);
holder = new ViewHolder();
holder.text = (TextView) convertView.findViewById(R.id.text);
holder.icon = (ImageView) convertView.findViewById(R.id.icon);
convertView.setTag(holder);   //设置标记
} else {
holder = (ViewHolder) convertView.getTag();
}
holder.text.setText(DATA[position]);
holder.icon.setImageBitmap((position & 1) == 1 ? mIcon1 : mIcon2);
return convertView;
}
static class ViewHolder {
TextView text;
ImageView icon;
}
android ListView几个比较特别的属性:

首先是stackFromBottom属性,这只该属性以后你作好的列表就会显示你列表的最下面,值为true和false

android:stackFromBottom="true"            

第二是transciptMode属性,须要用ListView或者其它显示大量Items的控件实时跟踪或者查看信息,而且但愿最新的条目能够自动滚动到可视范围内。经过设置的控件transcriptMode属性能够将Android平台的控件(支持ScrollBar)自动滑动到最底部。

 android:transcriptMode="alwaysScroll"   

第三cacheColorHint属性,不少人但愿可以改变一下它的背景,使他可以符合总体的UI设计,改变背景背很简单只须要准备一张图片而后指定属性 android:background="@drawable/bg",不过不要高兴地太早,当你这么作之后,发现背景是变了,可是当你拖动,或者点击list空白位置的时候发现ListItem都变成黑色的了,破坏了总体效果。

若是你只是换背景的颜色的话,能够直接指定android:cacheColorHint为你所要的颜色,若是你是用图片作背景的话,那也只要将android:cacheColorHint指定为透明(#00000000)就能够了

第四divider属性,该属性做用是每一项之间须要设置一个图片作为间隔,或是去掉item之间的分割线

 android:divider="@drawable/list_driver"  其中  @drawable/list_driver 是一个图片资源,若是不想显示分割线则只要设置为android:divider="@drawable/@null" 就能够了

第五fadingEdge属性,上边和下边有黑色的阴影

android:fadingEdge="none" 设置后没有阴影了~

 第五scrollbars属性,做用是隐藏listView的滚动条,

android:scrollbars="none"与setVerticalScrollBarEnabled(true);的效果是同样的,不活动的时候隐藏,活动的时候也隐藏

第六fadeScrollbars属性,android:fadeScrollbars="true"  配置ListView布局的时候,设置这个属性为true就能够实现滚动条的自动隐藏和显示。

 

 

java和javascript互相调用

 mWebView = (WebView) findViewById(R.id.webview);  

        WebSettings mWebSettings = mWebView.getSettings();  

        //加上这句话才能使用javascript方法  

        mWebSettings.setJavaScriptEnabled(true);  

        //增长接口方法,让html页面调用  

        mWebView.addJavascriptInterface(new Object() {  

            //这里我定义了一个拨打电话应用的方法  

            public void callPhone() {

               Uri uri= Uri.parse("tel:12345");

                Intent mIntent = new Intent(Intent.ACTION_CALL,uri);   

                startActivity(mIntent);  

            }  

        }, "demo");  

        //加载页面  

        mWebView.loadUrl("file:///android_asset/demo.html");  

        mButton = (Button) findViewById(R.id.button);  

        //给button添加事件响应,执行JavaScript的fillContent()方法  

        mButton.setOnClickListener(new Button.OnClickListener() {  

            public void onClick(View v) {  

                mWebView.loadUrl("javascript:fillContent()");  

            }  

});  

<html>  

<head>

<meta http-equiv="Content-Type" content="text/html;charset=utf-8" />

</head>

    <script> 

        function fillContent(){  

            document.getElementById("content").innerHTML =   

                 "java调用javascript哈哈,这些话是javascript搞出来的";  

        }         

</script>    

<body>  

    <p><a onClick="window.demo.callPhone()" href="">打电话</a></p>  

    <p id="content"></p>  

    <p>java和javascript相互调用</p>  

</body>  

</html>

 

 

 

1.每次启动新的Activity的时候,输入法老是弹出来,太烦人了。  

主要缘由就是页面上方有个EditTexit,每次都自动获取焦点。  

注意要求是:每次启动新的Activity的时候,EditTexit不要获取到焦点或者获取到焦点也不让输入法弹出来,并非阻止输入法使用。只要第一次启动的时候别弹出来就好了,若是主动点到EditTexit的时候输入法仍是得正常的弹出来的  

解决:  
在OnCreate方法里面加下面这句代码  
// 隐藏软键盘  
Java代码    收藏代码
  1. getWindow().setSoftInputMode(  
  2.                 WindowManager.LayoutParams.SOFT_INPUT_STATE_ALWAYS_HIDDEN);   


2.在editText中输入完之后,旁边有个send 按钮,当点击send button 关闭软键盘,再次输入的时候再弹出来。  
解决:  
Java代码    收藏代码
  1. // close input method after send  
  2. final InputMethodManager imm = (InputMethodManager)getSystemService(INPUT_METHOD_SERVICE);       
  3. imm.hideSoftInputFromWindow(contentTextEdit.getWindowToken(), 0);   

 

Android应用如何实现换主题功能:   

假设一个简单的场景:有2套主题,一套绿色,一套黑色的。应用界面就一个按钮,每点击一下,按钮和背景都切换为不一样的主题,如当前为黑色主题,下一次就为绿色主题,再下一次为黑色,以此类推。

打开Eclipse,新建三个Android工程项目,名字分别为BlackSkin、GreenSkin和MainSkin。BlackSkin和GreenSkin分别对应黑色、绿色主题资源,MainSkin为主应用。

BlackSkin
该工程下没有任何代码,只是在res\drawable目录下放置2张图片,一张黑色的背景,一张黑色的按钮图片。接着修改AndroidManifest.xml文件。

<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
android:versionCode="1"
android:versionName="1.0"
package="net.toeach.blackskin"
android:sharedUserId="net.toeach.MainSkin">

<uses-sdk android:minSdkVersion="3" />

</manifest>













GreenSkin
与BlackSkin项目同样,该工程下也没有任何代码,只是在res\drawable目录下放置2张图片,一张绿色的背景,一张绿色的按钮图片。接着修改AndroidManifest.xml文件。

<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
android:versionCode="1"
android:versionName="1.0"
package="net.toeach.greenskin"
android:sharedUserId="net.toeach.mainskin">

<uses-sdk android:minSdkVersion="3" />

</manifest>















咱们知道Android给每一个APK进程分配一个单独的用户空间,其manifest中的userid就是对应一个Linux用户的(Android 系统是基于Linux)。因此不一样APK(用户)间互相访问数据默认是禁止的,可是它也提供了2种APK间共享数据的形式:
1. Share Preference. / Content Provider
APK能够指定接口和数据给任何其余APK读取,须要本身实现接口和Share的数据.

2. Shared User id
经过Shared User id,拥有同一个User id的多个APK能够配置成运行在同一个进程中。因此默认就是能够互相访问任意数据。也能够配置成运行成不一样的进程,同时能够访问其余APK的数据目录下的数据库和文件。就像访问本程序的数据同样。本文中的换主题功能就是经过这种方式来实现的。

MainSkin
该工程为主应用,咱们新创建一个Activity类,叫MainActivity.java。代码以下:

public class MainActivity extends Activity {
private LinearLayout showBg;
private Button btn;
private Context greenSkinContext = null;
private Context blackSkinContext = null;
int flag = 0;

@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.main);
try {
greenSkinContext = this.createPackageContext("net.toeach.greenskin", Context.CONTEXT_IGNORE_SECURITY);
blackSkinContext = this.createPackageContext("net.toeach.blackskin", Context.CONTEXT_IGNORE_SECURITY);
} catch (NameNotFoundException e) {
e.printStackTrace();
}

showBg = (LinearLayout) findViewById(R.id.linear_layout_1);
btn = (Button) findViewById(R.id.btn_change_skin);
btn.setOnClickListener(new OnClickListener() {
@Override
public void onClick(View v) {
if (flag == 0) {
//访问GreenSkin下的资源
showBg.setBackgroundDrawable(greenSkinContext.getResources().getDrawable(R.drawable.bg));
btn.setBackgroundDrawable(greenSkinContext.getResources().getDrawable(R.drawable.btn_normal));
flag = 1;
} else if (flag == 1) {
//访问BlackSkin下的资源
showBg.setBackgroundDrawable(blackSkinContext.getResources().getDrawable(R.drawable.bg)); btn.setBackgroundDrawable(blackSkinContext.getResources().getDrawable(R.drawable.btn_normal)); flag = 0; }//end of if }); }//end of method }//end of class

相关文章
相关标签/搜索