1. 程式人生 > >安卓識別身份證,自動提取身份證資訊功能實現(附原始碼)

安卓識別身份證,自動提取身份證資訊功能實現(附原始碼)

原始碼下載地址:注:原始碼裡沒有騰訊優圖的賬號需要填寫自己的 下載地址

先講幾下.首先我們需要去騰訊優圖申請一個賬號,因為身份證識別需要用到第三方介面如圖所示

我申請的是掃描身份證,當然還有其他的功能,比如掃描銀行卡,營業執照,車牌等等  ,大家可以去研究一下

1.記得配許可權,需要讀寫SD卡 ,還需要網路的許可權   記得引入第三方庫,本人很懶,反正能少些程式碼的,絕對不手打,能用第三庫解決的,絕不自己動手,哈哈

    //網路請求庫
    compile 'org.xutils:xutils:3.3.36'
    //圖片選擇器庫
    compile 'com.github.LuckSiege.PictureSelector:picture_library:v2.2.3'
    //解析庫
    compile 'com.google.code.gson:gson:2.7'

還有,記得在allprojects新增下程式碼

allprojects {
    repositories {
        maven { url 'https://jitpack.io' }
        maven { url 'https://maven.google.com' }
        //圖片選擇器庫
        maven {
            url "http://dl.bintray.com/nuptboyzhb/maven"
        }
        google()
        jcenter()
    }
}

下面配置好許可權

    <!-- 讀寫 -->
    <uses-permission android:name="android.permission.MOUNT_UNMOUNT_FILESYSTEMS" />
    <!-- 用於申請呼叫照相機 -->
    <uses-permission android:name="android.permission.CAMERA" />

然後新建一個Application配置下網路請求吧

public class MyApplication extends Application {
    @Override
    public void onCreate() {
        super.onCreate();
//網路請求
        x.Ext.init(this);
    }
}

記得在Manifests中設定一下name=.MyApplication

 <application
        android:name=".MyApplication"
        android:allowBackup="true"
        android:icon="@mipmap/ic_launcher"
        android:label="@string/app_name"
        android:roundIcon="@mipmap/ic_launcher_round"
        android:supportsRtl="true"
        android:theme="@style/AppTheme">

接下來是佈局檔案來,等會上程式碼了

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:background="@color/white"
    android:orientation="vertical">

    <ScrollView
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        android:fillViewport="true"
        android:scrollbars="vertical">

        <LinearLayout
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            android:orientation="vertical">

            <ImageView
                android:id="@+id/activity_autonym_certification_iv_positive"
                android:layout_width="match_parent"
                android:layout_height="180dp"
                android:layout_marginRight="30dp"
                android:layout_marginLeft="30dp"
                android:layout_marginTop="20dp"
                android:background="@drawable/autonym_certification_iv_line"
                android:padding="20dp"
                android:src="@mipmap/idcard_positive" />

            <ImageView
                android:id="@+id/activity_autonym_certification_iv_reverse"
                android:layout_width="match_parent"
                android:layout_height="180dp"
                android:layout_marginTop="25dp"
                android:layout_marginRight="30dp"
                android:layout_marginLeft="30dp"
                android:background="@drawable/autonym_certification_iv_line"
                android:padding="20dp"
                android:src="@mipmap/idcard_reverse" />

            <LinearLayout
                android:layout_marginRight="30dp"
                android:layout_marginLeft="30dp"
                android:layout_marginTop="20dp"
                android:layout_width="match_parent"
                android:layout_height="wrap_content"
                android:orientation="horizontal">
                <TextView
                    android:layout_width="90dp"
                    android:layout_height="wrap_content"
                    android:text="姓名:"
                    android:textColor="@color/black"/>
                <EditText
                    android:enabled="false"
                    android:id="@+id/activity_autonym_certification_et_name"
                    android:layout_width="match_parent"
                    android:layout_height="wrap_content"
                    android:textColor="@color/black"
                    android:gravity="center"
                    android:background="@drawable/autonym_certification_iv_line"
                    android:text=""/>
            </LinearLayout>

            <LinearLayout
                android:layout_marginTop="10dp"
                android:layout_marginLeft="30dp"
                android:layout_marginRight="30dp"
                android:layout_width="match_parent"
                android:layout_height="wrap_content"
                android:orientation="horizontal">
                <TextView
                    android:layout_width="90dp"
                    android:layout_height="wrap_content"
                    android:text="有效日期:"
                    android:textColor="@color/black"/>
                <EditText
                    android:enabled="false"
                    android:id="@+id/activity_autonym_certification_et_effective_date"
                    android:layout_width="match_parent"
                    android:layout_height="wrap_content"
                    android:textColor="@color/black"
                    android:gravity="center"
                    android:background="@drawable/autonym_certification_iv_line"
                    android:text=""/>
            </LinearLayout>

            <LinearLayout
                android:layout_marginLeft="30dp"
                android:layout_marginRight="30dp"
                android:layout_marginTop="10dp"
                android:layout_width="match_parent"
                android:layout_height="wrap_content"
                android:orientation="horizontal">
                <TextView
                    android:layout_width="90dp"
                    android:layout_height="wrap_content"
                    android:text="身份證號碼:"
                    android:textColor="@color/black"/>
                <EditText
                    android:id="@+id/activity_autonym_certification_et_id_card"
                    android:layout_width="match_parent"
                    android:layout_height="wrap_content"
                    android:textColor="@color/black"
                    android:gravity="center"
                    android:enabled="false"
                    android:background="@drawable/autonym_certification_iv_line"
                    android:text=""/>
            </LinearLayout>
        </LinearLayout>


    </ScrollView>

</LinearLayout>

然後是兩個實體類用來存放身份證 正反兩面的資料,先是正面

package com.example.aa.demo.entity;

import java.io.Serializable;
import java.util.List;

/**
 * 識別結果實體
 */
public class IdentifyResult implements Serializable {

    /**
     * errorcode : 0
     * errormsg : OK
     * name : xxx
     * name_confidence_all : [50,60,53]
     * sex : xx
     * sex_confidence_all : [41]
     * nation : xx
     * nation_confidence_all : [38]
     * birth : xxxx/xx/xx
     * birth_confidence_all : [69,43,46,46,44,53,50]
     * address : xxxxxxxxx
     * address_confidence_all : [43,36,34,17,25,24,21,31,45,36,23,62,12,30,9,1,39,34,24,19,16,30,30,4]
     * id : xxxxxxxxxxxxxxxxxx
     * id_confidence_all : [52,58,59,73,54,56,61,63,50,63,60,49,72,50,62,57,63,53]
     * frontimage : xxx
     * frontimage_confidence_all : []
     * watermask_confidence_all : []
     * valid_date_confidence_all : []
     * authority_confidence_all : []
     * backimage_confidence_all : []
     * detail_errorcode : []
     * detail_errormsg : []
     */

    private int errorcode;
    private String errormsg;
    private String name;
    private String sex;
    private String nation;
    private String birth;
    private String address;
    private String id;
    private String frontimage;
    private List<Integer> name_confidence_all;
    private List<Integer> sex_confidence_all;
    private List<Integer> nation_confidence_all;
    private List<Integer> birth_confidence_all;
    private List<Integer> address_confidence_all;
    private List<Integer> id_confidence_all;
    private List<?> frontimage_confidence_all;
    private List<?> watermask_confidence_all;
    private List<?> valid_date_confidence_all;
    private List<?> authority_confidence_all;
    private List<?> backimage_confidence_all;
    private List<Integer> detail_errorcode;
    private List<String> detail_errormsg;

    public int getErrorcode() {
        return errorcode;
    }

    public void setErrorcode(int errorcode) {
        this.errorcode = errorcode;
    }

    public String getErrormsg() {
        return errormsg;
    }

    public void setErrormsg(String errormsg) {
        this.errormsg = errormsg;
    }

    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }

    public String getSex() {
        return sex;
    }

    public void setSex(String sex) {
        this.sex = sex;
    }

    public String getNation() {
        return nation;
    }

    public void setNation(String nation) {
        this.nation = nation;
    }

    public String getBirth() {
        return birth;
    }

    public void setBirth(String birth) {
        this.birth = birth;
    }

    public String getAddress() {
        return address;
    }

    public void setAddress(String address) {
        this.address = address;
    }

    public String getId() {
        return id;
    }

    public void setId(String id) {
        this.id = id;
    }

    public String getFrontimage() {
        return frontimage;
    }

    public void setFrontimage(String frontimage) {
        this.frontimage = frontimage;
    }

    public List<Integer> getName_confidence_all() {
        return name_confidence_all;
    }

    public void setName_confidence_all(List<Integer> name_confidence_all) {
        this.name_confidence_all = name_confidence_all;
    }

    public List<Integer> getSex_confidence_all() {
        return sex_confidence_all;
    }

    public void setSex_confidence_all(List<Integer> sex_confidence_all) {
        this.sex_confidence_all = sex_confidence_all;
    }

    public List<Integer> getNation_confidence_all() {
        return nation_confidence_all;
    }

    public void setNation_confidence_all(List<Integer> nation_confidence_all) {
        this.nation_confidence_all = nation_confidence_all;
    }

    public List<Integer> getBirth_confidence_all() {
        return birth_confidence_all;
    }

    public void setBirth_confidence_all(List<Integer> birth_confidence_all) {
        this.birth_confidence_all = birth_confidence_all;
    }

    public List<Integer> getAddress_confidence_all() {
        return address_confidence_all;
    }

    public void setAddress_confidence_all(List<Integer> address_confidence_all) {
        this.address_confidence_all = address_confidence_all;
    }

    public List<Integer> getId_confidence_all() {
        return id_confidence_all;
    }

    public void setId_confidence_all(List<Integer> id_confidence_all) {
        this.id_confidence_all = id_confidence_all;
    }

    public List<?> getFrontimage_confidence_all() {
        return frontimage_confidence_all;
    }

    public void setFrontimage_confidence_all(List<?> frontimage_confidence_all) {
        this.frontimage_confidence_all = frontimage_confidence_all;
    }

    public List<?> getWatermask_confidence_all() {
        return watermask_confidence_all;
    }

    public void setWatermask_confidence_all(List<?> watermask_confidence_all) {
        this.watermask_confidence_all = watermask_confidence_all;
    }

    public List<?> getValid_date_confidence_all() {
        return valid_date_confidence_all;
    }

    public void setValid_date_confidence_all(List<?> valid_date_confidence_all) {
        this.valid_date_confidence_all = valid_date_confidence_all;
    }

    public List<?> getAuthority_confidence_all() {
        return authority_confidence_all;
    }

    public void setAuthority_confidence_all(List<?> authority_confidence_all) {
        this.authority_confidence_all = authority_confidence_all;
    }

    public List<?> getBackimage_confidence_all() {
        return backimage_confidence_all;
    }

    public void setBackimage_confidence_all(List<?> backimage_confidence_all) {
        this.backimage_confidence_all = backimage_confidence_all;
    }

    public List<Integer> getDetail_errorcode() {
        return detail_errorcode;
    }

    public void setDetail_errorcode(List<Integer> detail_errorcode) {
        this.detail_errorcode = detail_errorcode;
    }

    public List<String> getDetail_errormsg() {
        return detail_errormsg;
    }

    public void setDetail_errormsg(List<String> detail_errormsg) {
        this.detail_errormsg = detail_errormsg;
    }
}

再是反面

package com.example.aa.demo.entity;

import java.io.Serializable;
import java.util.List;

/**
 * Created by aa on 2018/10/30.
 */

public class cardReverseRusult implements Serializable {

    /**
     * errorcode : 0
     * errormsg : OK
     * session_id :
     * name_confidence_all : []
     * sex_confidence_all : []
     * nation_confidence_all : []
     * birth_confidence_all : []
     * address_confidence_all : []
     * id_confidence_all : []
     * frontimage_confidence_all : []
     * watermask_confidence_all : []
     * valid_date : 2010.07.21-2020.07.21
     * valid_date_confidence_all : [99,99,99,99,99,99,99,99,99,99,99,99,99,99,99,99,95,99,99,99,99]
     * authority : 趙縣公安局
     * authority_confidence_all : [100]
     * backimage : .....
     * backimage_confidence_all : []
     * detail_errorcode : []
     * detail_errormsg : []
     * card_type : 1
     * recognize_warn_code : []
     * recognize_warn_msg : []
     */

    private int errorcode;
    private String errormsg;
    private String session_id;
    private String valid_date;
    private String authority;
    private String backimage;
    private int card_type;
    private List<?> name_confidence_all;
    private List<?> sex_confidence_all;
    private List<?> nation_confidence_all;
    private List<?> birth_confidence_all;
    private List<?> address_confidence_all;
    private List<?> id_confidence_all;
    private List<?> frontimage_confidence_all;
    private List<?> watermask_confidence_all;
    private List<Integer> valid_date_confidence_all;
    private List<Integer> authority_confidence_all;
    private List<?> backimage_confidence_all;
    private List<?> detail_errorcode;
    private List<?> detail_errormsg;
    private List<?> recognize_warn_code;
    private List<?> recognize_warn_msg;

    public int getErrorcode() {
        return errorcode;
    }

    public void setErrorcode(int errorcode) {
        this.errorcode = errorcode;
    }

    public String getErrormsg() {
        return errormsg;
    }

    public void setErrormsg(String errormsg) {
        this.errormsg = errormsg;
    }

    public String getSession_id() {
        return session_id;
    }

    public void setSession_id(String session_id) {
        this.session_id = session_id;
    }

    public String getValid_date() {
        return valid_date;
    }

    public void setValid_date(String valid_date) {
        this.valid_date = valid_date;
    }

    public String getAuthority() {
        return authority;
    }

    public void setAuthority(String authority) {
        this.authority = authority;
    }

    public String getBackimage() {
        return backimage;
    }

    public void setBackimage(String backimage) {
        this.backimage = backimage;
    }

    public int getCard_type() {
        return card_type;
    }

    public void setCard_type(int card_type) {
        this.card_type = card_type;
    }

    public List<?> getName_confidence_all() {
        return name_confidence_all;
    }

    public void setName_confidence_all(List<?> name_confidence_all) {
        this.name_confidence_all = name_confidence_all;
    }

    public List<?> getSex_confidence_all() {
        return sex_confidence_all;
    }

    public void setSex_confidence_all(List<?> sex_confidence_all) {
        this.sex_confidence_all = sex_confidence_all;
    }

    public List<?> getNation_confidence_all() {
        return nation_confidence_all;
    }

    public void setNation_confidence_all(List<?> nation_confidence_all) {
        this.nation_confidence_all = nation_confidence_all;
    }

    public List<?> getBirth_confidence_all() {
        return birth_confidence_all;
    }

    public void setBirth_confidence_all(List<?> birth_confidence_all) {
        this.birth_confidence_all = birth_confidence_all;
    }

    public List<?> getAddress_confidence_all() {
        return address_confidence_all;
    }

    public void setAddress_confidence_all(List<?> address_confidence_all) {
        this.address_confidence_all = address_confidence_all;
    }

    public List<?> getId_confidence_all() {
        return id_confidence_all;
    }

    public void setId_confidence_all(List<?> id_confidence_all) {
        this.id_confidence_all = id_confidence_all;
    }

    public List<?> getFrontimage_confidence_all() {
        return frontimage_confidence_all;
    }

    public void setFrontimage_confidence_all(List<?> frontimage_confidence_all) {
        this.frontimage_confidence_all = frontimage_confidence_all;
    }

    public List<?> getWatermask_confidence_all() {
        return watermask_confidence_all;
    }

    public void setWatermask_confidence_all(List<?> watermask_confidence_all) {
        this.watermask_confidence_all = watermask_confidence_all;
    }

    public List<Integer> getValid_date_confidence_all() {
        return valid_date_confidence_all;
    }

    public void setValid_date_confidence_all(List<Integer> valid_date_confidence_all) {
        this.valid_date_confidence_all = valid_date_confidence_all;
    }

    public List<Integer> getAuthority_confidence_all() {
        return authority_confidence_all;
    }

    public void setAuthority_confidence_all(List<Integer> authority_confidence_all) {
        this.authority_confidence_all = authority_confidence_all;
    }

    public List<?> getBackimage_confidence_all() {
        return backimage_confidence_all;
    }

    public void setBackimage_confidence_all(List<?> backimage_confidence_all) {
        this.backimage_confidence_all = backimage_confidence_all;
    }

    public List<?> getDetail_errorcode() {
        return detail_errorcode;
    }

    public void setDetail_errorcode(List<?> detail_errorcode) {
        this.detail_errorcode = detail_errorcode;
    }

    public List<?> getDetail_errormsg() {
        return detail_errormsg;
    }

    public void setDetail_errormsg(List<?> detail_errormsg) {
        this.detail_errormsg = detail_errormsg;
    }

    public List<?> getRecognize_warn_code() {
        return recognize_warn_code;
    }

    public void setRecognize_warn_code(List<?> recognize_warn_code) {
        this.recognize_warn_code = recognize_warn_code;
    }

    public List<?> getRecognize_warn_msg() {
        return recognize_warn_msg;
    }

    public void setRecognize_warn_msg(List<?> recognize_warn_msg) {
        this.recognize_warn_msg = recognize_warn_msg;
    }
}

然後需要幾個工具類

第一個bitmap編解碼工具類

package cn.vonce.doer.utils;

import android.content.Context;
import android.content.Intent;
import android.graphics.Bitmap;
import android.graphics.BitmapFactory;
import android.graphics.Color;
import android.graphics.Matrix;
import android.net.Uri;
import android.os.Environment;
import android.provider.MediaStore;
import android.util.Base64;
import android.widget.Toast;

import java.io.ByteArrayInputStream;
import java.io.ByteArrayOutputStream;
import java.io.File;
import java.io.FileInputStream;
import java.io.FileNotFoundException;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.InputStream;

/**
 * bitmap編解碼工具類
 */
public class BitMapUtils {


    /**
     * bitmap轉為base64
     *
     * @param bitmap
     * @return
     */
    public static String bitmapToBase64(Bitmap bitmap) {
        String result = null;
        ByteArrayOutputStream baos = null;
        try {
            if (bitmap != null) {
                baos = new ByteArrayOutputStream();
                bitmap.compress(Bitmap.CompressFormat.JPEG, 100, baos);
                baos.flush();
                baos.close();
                byte[] bitmapBytes = baos.toByteArray();
                result = Base64.encodeToString(bitmapBytes, Base64.DEFAULT);
            }
        } catch (IOException e) {
            return "";
        } finally {
            try {
                if (baos != null) {
                    baos.flush();
                    baos.close();
                }
            } catch (IOException e) {
                return "";
            }
        }
        return result;
    }


    /**
     * 從SD卡上獲取圖片。如果不存在則返回null</br>
     * @return 代表圖片的Bitmap物件
     */
    public static Bitmap getBitmapFromSDCard(String url) {
        InputStream inputStream = null;
        try {
            inputStream = new FileInputStream(new File(url));
            if (inputStream != null && inputStream.available() > 0) {
                Bitmap bitmap = BitmapFactory.decodeStream(inputStream);
                return bitmap;
            }
        } catch (Exception e) {
            e.printStackTrace();
        }
        return null;
    }

    // 分享單張圖片
    public static void shareSingleImage(Context context, Bitmap copy) {
        if(copy != null){
            File appDir = new File(Environment.getExternalStorageDirectory(), "demo");
            if (!appDir.exists()) {
                appDir.mkdir();
            }
            String fileName = System.currentTimeMillis() + ".jpg";
            File file = new File(appDir, fileName);
            try {
                FileOutputStream fos = new FileOutputStream(file);
                copy.compress(Bitmap.CompressFormat.JPEG, 100, fos);
                fos.flush();
                fos.close();
            } catch (FileNotFoundException e) {
                e.printStackTrace();
            } catch (IOException e) {
                e.printStackTrace();
            }

            String path = file.getAbsolutePath();

            // 由檔案得到uri
            Uri imageUri = Uri.fromFile(new File(path));
            Intent shareIntent = new Intent();
            shareIntent.setAction(Intent.ACTION_SEND);
            shareIntent.putExtra(Intent.EXTRA_STREAM, imageUri);
            shareIntent.setType("image/*");
            context.startActivity(Intent.createChooser(shareIntent, "分享到"));
        }else {
            Toast.makeText(context, "請先從相簿選擇一張圖片", Toast.LENGTH_SHORT).show();
        }
    }

    /**
     * 儲存圖片到本地相簿
     *
     * @param context       上下文
     * @param bmp           要儲存的bitmap
     */
    public static void saveImageToGallery(Context context, Bitmap bmp) {
        // 首先儲存圖片
        File appDir = new File(Environment.getExternalStorageDirectory(), "demo");
        if (!appDir.exists()) {
            appDir.mkdir();
        }
        String fileName = System.currentTimeMillis() + ".jpg";
        File file = new File(appDir, fileName);
        try {
            FileOutputStream fos = new FileOutputStream(file);
            bmp.compress(Bitmap.CompressFormat.JPEG, 100, fos);
            fos.flush();
            fos.close();
        } catch (FileNotFoundException e) {
            e.printStackTrace();
        } catch (IOException e) {
            e.printStackTrace();
        }

        String path = file.getAbsolutePath();

        // 其次把檔案插入到系統圖庫
        try {
            MediaStore.Images.Media.insertImage(context.getContentResolver(),
                    file.getAbsolutePath(), fileName, null);
        } catch (FileNotFoundException e) {
            e.printStackTrace();
        }
        Toast.makeText(context, "圖片已儲存至" + path, Toast.LENGTH_SHORT).show();
        // 最後通知相簿更新
        context.sendBroadcast(new Intent(Intent.ACTION_MEDIA_SCANNER_SCAN_FILE, Uri.parse("file://" + path)));
    }

    /**
     * 選擇圖片後壓縮展示
     */
    public static Bitmap onSelected(String local_path) {
        Bitmap bitmap = BitmapFactory.decodeFile(local_path);
        ByteArrayOutputStream out = new ByteArrayOutputStream();
        bitmap.compress(Bitmap.CompressFormat.JPEG, 85, out);
        int size = bitmap.getWidth() * bitmap.getHeight();
        float zoom = (float) Math.sqrt(size * 1024 / (float)out.toByteArray().length);

        Matrix matrix = new Matrix();
        matrix.setScale(zoom, zoom);

        Bitmap result = Bitmap.createBitmap(bitmap, 0, 0, bitmap.getWidth(), bitmap.getHeight(), matrix, true);
        out.reset();
        result.compress(Bitmap.CompressFormat.JPEG, 85, out);
        while(out.toByteArray().length > size * 1024){
            System.out.println(out.toByteArray().length);
            matrix.setScale(0.9f, 0.9f);
            result = Bitmap.createBitmap(result, 0, 0, result.getWidth(), result.getHeight(), matrix, true);
            out.reset();
            result.compress(Bitmap.CompressFormat.JPEG, 85, out);
        }
        bitmap = result;
        return bitmap;
    }

    /**
     * 獲取壓縮後的圖片
     *
     * @param srcPath       要壓縮的圖片路徑
     * @return              壓縮後的bitmap
     */
    public static Bitmap getImage(String srcPath) {
        BitmapFactory.Options newOpts = new BitmapFactory.Options();
        // 開始讀入圖片,此時把options.inJustDecodeBounds 設回true了
        newOpts.inJustDecodeBounds = true;
        Bitmap bitmap = BitmapFactory.decodeFile(srcPath,newOpts);// 此時返回bm為空

        newOpts.inJustDecodeBounds = false;
        int w = newOpts.outWidth;
        int h = newOpts.outHeight;
        // 現在主流手機比較多是800*480解析度,所以高和寬我們設定為
        float hh = 800f;// 這裡設定高度為800f
        float ww = 480f;// 這裡設定寬度為480f
        // 縮放比。由於是固定比例縮放,只用高或者寬其中一個數據進行計算即可
        int be = 1;// be=1表示不縮放
        if (w > h && w > ww) {// 如果寬度大的話根據寬度固定大小縮放
            be = (int) (newOpts.outWidth / ww);
        } else if (w < h && h > hh) {// 如果高度高的話根據寬度固定大小縮放
            be = (int) (newOpts.outHeight / hh);
        }
        if (be <= 0)
            be = 1;
        newOpts.inSampleSize = be;// 設定縮放比例
        // 重新讀入圖片,注意此時已經把options.inJustDecodeBounds 設回false了
        bitmap = BitmapFactory.decodeFile(srcPath, newOpts);
        return compressImage(bitmap);// 壓縮好比例大小後再進行質量壓縮
    }

    public static Bitmap compressImage(Bitmap image) {
        ByteArrayOutputStream baos = new ByteArrayOutputStream();
        image.compress(Bitmap.CompressFormat.JPEG, 100, baos);// 質量壓縮方法,這裡100表示不壓縮,把壓縮後的資料存放到baos中
        int options = 100;
        while (baos.toByteArray().length / 1024 > 100) {  // 迴圈判斷如果壓縮後圖片是否大於100kb,大於繼續壓縮
            baos.reset();// 重置baos即清空baos
            image.compress(Bitmap.CompressFormat.JPEG, options, baos);// 這裡壓縮options%,把壓縮後的資料存放到baos中
            options -= 10;// 每次都減少10
        }
        ByteArrayInputStream isBm = new ByteArrayInputStream(baos.toByteArray());// 把壓縮後的資料baos存放到ByteArrayInputStream中
        Bitmap bitmap = BitmapFactory.decodeStream(isBm, null, null);// 把ByteArrayInputStream資料生成圖片
        return bitmap;
    }

    /**
     * 處理指定的圖片
     */
    public static Bitmap handlePicture(Bitmap bitmap){
        int width = bitmap.getWidth();
        int height = bitmap.getHeight();
        Bitmap copy = Bitmap.createBitmap(width, height, Bitmap.Config.ARGB_8888);
        int[] before = new int[width * height];
        int[] after = new int[width * height];
        bitmap.getPixels(before, 0, width, 0, 0, width, height);
        int pixelsA, pixelsR, pixelsG, pixelsB;
        for(int i = 0;i < width * height;i++){
            int color = before[i];
            // ∂獲取RGB分量
            pixelsA = Color.alpha(color);
            pixelsR = Color.red(color);
            pixelsG = Color.green(color);
            pixelsB = Color.blue(color);

            if(pixelsA >= 1) {
                // 轉換
                pixelsR = (255 - pixelsR);
                pixelsG = (255 - pixelsG);
                pixelsB = (255 - pixelsB);
                // 均小於等於255大於等於0
                if (pixelsR > 255) {
                    pixelsR = 255;
                } else if (pixelsR < 0) {
                    pixelsR = 0;
                }
                if (pixelsG > 255) {
                    pixelsG = 255;
                } else if (pixelsG < 0) {
                    pixelsG = 0;
                }
                if (pixelsB > 255) {
                    pixelsB = 255;
                } else if (pixelsB < 0) {
                    pixelsB = 0;
                }
            }
            // 根據新的RGB生成新畫素
            after[i] = Color.argb(pixelsA, pixelsR, pixelsG, pixelsB);
        }
        copy.setPixels(after, 0, width, 0, 0, width, height);
        return copy;
    }


    /**
     * 處理指定的圖片為黑白照片
     */
    public static Bitmap colored(Bitmap bitmap){
        int width = bitmap.getWidth();
        int height = bitmap.getHeight();
        Bitmap copy = Bitmap.createBitmap(width, height, Bitmap.Config.ARGB_8888);
        int[] before = new int[width * height];
        int[] after = new int[width * height];
        bitmap.getPixels(before, 0, width, 0, 0, width, height);
        int pixelsA, pixelsR, pixelsG, pixelsB;
        for(int i = 0;i < width * height;i++){
            int color = before[i];
            // 獲取RGB分量
            pixelsA = Color.alpha(color);
            pixelsR = Color.red(color);
            pixelsG = Color.green(color);
            pixelsB = Color.blue(color);

            if(pixelsA >= 1) {
                pixelsR = pixelsG = pixelsB = (pixelsR + pixelsG + pixelsB) / 3;
            }

            // 根據新的RGB生成新畫素
            after[i] = Color.argb(pixelsA, pixelsR, pixelsG, pixelsB);
        }
        copy.setPixels(after, 0, width, 0, 0, width, height);
        return copy;
    }

    /**
     * 處理指定的圖片為半透明照片
     */
    public static Bitmap halfTrans(Bitmap bitmap){
        int width = bitmap.getWidth();
        int height = bitmap.getHeight();
        Bitmap copy = Bitmap.createBitmap(width, height, Bitmap.Config.ARGB_8888);
        int[] before = new int[width * height];
        int[] after = new int[width * height];
        bitmap.getPixels(before, 0, width, 0, 0, width, height);
        int pixelsA, pixelsR, pixelsG, pixelsB;
        for(int i = 0;i < width * height;i++){
            int color = before[i];
            // 獲取RGB分量
            pixelsA = Color.alpha(color);
            pixelsR = Color.red(color);
            pixelsG = Color.green(color);
            pixelsB = Color.blue(color);

            // 根據新的RGB生成新畫素
            after[i] = Color.argb(pixelsA / 2, pixelsR, pixelsG, pixelsB);
        }
        copy.setPixels(after, 0, width, 0, 0, width, height);
        return copy;
    }

}

第二個網路請求工具類  請求騰訊的介面

package cn.vonce.doer.utils;

import android.util.Log;

import org.xutils.common.Callback;
import org.xutils.http.RequestParams;
import org.xutils.x;

import java.io.File;

import cn.vonce.doer.sign.Constant;
import cn.vonce.doer.sign.YoutuSign;

/**
 * 網路請求工具類
 */
public class TecentHttpUtil {

    public static void uploadIdCard(String bitmap, String card_type, final SimpleCallBack callback) {
        StringBuffer mySign = new StringBuffer("");
        YoutuSign.appSign(Constant.AppID, Constant.SecretID, Constant.SecretKey,
                System.currentTimeMillis() / 1000 + Constant.EXPIRED_SECONDS,
                Constant.QQNumber, mySign);
        RequestParams params = new RequestParams("http://api.youtu.qq.com/youtu/ocrapi/idcardocr");
        params.setAsJsonContent(true);
        params.addHeader("accept", "*/*");
        params.addHeader("Host", "api.youtu.qq.com");
        params.addHeader("user-agent", "youtu-java-sdk");
        params.addHeader("Authorization", mySign.toString());
        params.addHeader("Content-Type", "text/json");
        params.addParameter("card_type", Integer.valueOf(card_type));
        params.addBodyParameter("image", bitmap);
        params.addBodyParameter("app_id", Constant.AppID);
        x.http().post(params, new Callback.CommonCallback<String>() {
            @Override
            public void onSuccess(String result) {
                Log.d("onSuccess",result);
                callback.Succ(result);
            }

            @Override
            public void onError(Throwable ex, boolean isOnCallback) {
                Log.d("onError",ex.getMessage());
            }

            @Override
            public void onCancelled(CancelledException cex) {
                Log.d("onCancelled", cex.getMessage());
            }

            @Override
            public void onFinished() {

            }
        });

    }

    public interface SimpleCallBack {
        void Succ(String result);

        void error();
    }


}

 在網路請求工具類裡面會用到你申請的id了   需要幾個類

package com.example.aa.demo.sign;

import java.util.Random;

public class YoutuSign {

	/**
	 *app_sign    時效性簽名
	 *@param  appId       http://open.youtu.qq.com/上申請的業務ID
	 *@param  secret_id   http://open.youtu.qq.com/上申請的金鑰id
	 *@param  secret_key  http://open.youtu.qq.com/上申請的金鑰key
	 *@param  expired     簽名過期時間
	 *@param  userid      業務賬號系統,沒有可以不填
	 *@param  mySign      生成的簽名
	 *@return 0表示成功
	 */
	public static int appSign(String appId, String secret_id, String secret_key,
                              long expired, String userid, StringBuffer mySign) {
		return appSignBase(appId, secret_id, secret_key, expired, userid, null, mySign);
	}

    
	private static int appSignBase(String appId, String secret_id,
                                   String secret_key, long expired, String userid, String url,
                                   StringBuffer mySign) {
		

		if (empty(secret_id) || empty(secret_key))
    	{
            return -1;
    	}
    	
    	String puserid = "";
    	if (!empty(userid))
    	{
			if (userid.length() > 64)
			{
                return -2;
			}
			puserid = userid;
    	}
    	

        long now = System.currentTimeMillis() / 1000;
        int rdm = Math.abs(new Random().nextInt());
        String plain_text = "a=" + appId + "&k=" + secret_id + "&e=" + expired + "&t=" + now + "&r=" + rdm + "&u=" + puserid ;//+ "&f=" + fileid.toString();

        byte[] bin = hashHmac(plain_text, secret_key);

        byte[] all = new byte[bin.length + plain_text.getBytes().length];
        System.arraycopy(bin, 0, all, 0, bin.length);
        System.arraycopy(plain_text.getBytes(), 0, all, bin.length, plain_text.getBytes().length);
        
        mySign.append(Base64Util.encode(all));
        
        return 0;
	}

	private static byte[] hashHmac(String plain_text, String accessKey) {
		
		try {
			return HMACSHA1.getSignature(plain_text, accessKey);
		} catch (Exception e) {
			e.printStackTrace();
			return null;
		}
	}

    
	public static boolean empty(String s){
		return s == null || s.trim().equals("") || s.trim().equals("null");
	}
		
}
package com.example.aa.demo.sign;

public class Base64Util {
	private static final char last2byte = (char) Integer
			.parseInt("00000011", 2);
	private static final char last4byte = (char) Integer
			.parseInt("00001111", 2);
	private static final char last6byte = (char) Integer
			.parseInt("00111111", 2);
	private static final char lead6byte = (char) Integer
			.parseInt("11111100", 2);
	private static final char lead4byte = (char) Integer
			.parseInt("11110000", 2);
	private static final char lead2byte = (char) Integer
			.parseInt("11000000", 2);
	private static final char[] encodeTable = new char[] { 'A', 'B', 'C', 'D',
			'E', 'F', 'G', 'H', 'I', 'J', 'K', 'L', 'M', 'N', 'O', 'P', 'Q',
			'R', 'S', 'T', 'U', 'V', 'W', 'X', 'Y', 'Z', 'a', 'b', 'c', 'd',
			'e', 'f', 'g', 'h', 'i', 'j', 'k', 'l', 'm', 'n', 'o', 'p', 'q',
			'r', 's', 't', 'u', 'v', 'w', 'x', 'y', 'z', '0', '1', '2', '3',
			'4', '5', '6', '7', '8', '9', '+', '/' };

	/**
	 * Base64 encoding.
	 * 
	 * @param from
	 *            The src data.
	 * @return cryto_str
	 */
	public static String encode(byte[] from) {
		StringBuilder to = new StringBuilder((int) (from.length * 1.34) + 3);
		int num = 0;
		char currentByte = 0;
		for (int i = 0; i < from.length; i++) {
			num = num % 8;
			while (num < 8) {
				switch (num) {
				case 0:
					currentByte = (char) (from[i] & lead6byte);
					currentByte = (char) (currentByte >>> 2);
					break;
				case 2:
					currentByte = (char) (from[i] & last6byte);
					break;
				case 4:
					currentByte = (char) (from[i] & last4byte);
					currentByte = (char) (currentByte << 2);
					if ((i + 1) < from.length) {
						currentByte |= (from[i + 1] & lead2byte) >>> 6;
					}
					break;
				case 6:
					currentByte = (char) (from[i] & last2byte);
					currentByte = (char) (currentByte << 4);
					if ((i + 1) < from.length) {
						currentByte |= (from[i + 1] & lead4byte) >>> 4;
					}
					break;
				}
				to.append(encodeTable[currentByte]);
				num += 6;
			}
		}
		if (to.length() % 4 != 0) {
			for (int i = 4 - to.length() % 4; i > 0; i--) {
				to.append("=");
			}
		}
		return to.toString();
	}
}
package com.example.aa.demo.sign;

import javax.crypto.Mac;
import javax.crypto.spec.SecretKeySpec;

public class HMACSHA1 {

	private static final String HMAC_SHA1 = "HmacSHA1";

	public static byte[] getSignature(String data, String key) throws Exception {
		Mac mac = Mac.getInstance(HMAC_SHA1);
		SecretKeySpec signingKey = new SecretKeySpec(key.getBytes(),
				mac.getAlgorithm());
		mac.init(signingKey);

		return mac.doFinal(data.getBytes());
	}
}
package com.example.aa.demo.sign;

/**
 * 優圖賬號
 *這裡填大家自己申請的
 */
public class Constant {

    public static String QQNumber = "";// 騰訊優圖開發者賬號(QQ號)
    public static String AppID = "";
    public static String SecretID = "";
    public static String SecretKey = "";
    public static int EXPIRED_SECONDS = ;// 過期時間戳
}

然後就是主類了

package com.example.aa.demo;

import android.Manifest;
import android.content.Intent;
import android.content.pm.PackageManager;
import android.graphics.Bitmap;
import android.support.v4.app.ActivityCompat;
import android.support.v4.content.ContextCompat;
import android.support.v7.app.AppCompatActivity;
import android.os.Bundle;
import android.util.Log;
import android.view.View;
import android.widget.EditText;
import android.widget.ImageView;
import android.widget.Toast;

import com.example.aa.demo.entity.IdentifyResult;
import com.example.aa.demo.entity.cardReverseRusult;
import com.example.aa.demo.utils.BitMapUtils;
import com.example.aa.demo.utils.TecentHttpUtil;
import com.google.gson.Gson;
import com.luck.picture.lib.PictureSelector;
import com.luck.picture.lib.config.PictureConfig;
import com.luck.picture.lib.config.PictureMimeType;
import com.luck.picture.lib.entity.LocalMedia;

import java.util.ArrayList;
import java.util.List;

public class AutonymCertificationActivity extends AppCompatActivity implements View.OnClickListener {

    /**
     * 身份證正面
     */
    private ImageView activity_autonym_certification_iv_positive;

    /**
     * 身份證反面
     */
    private ImageView activity_autonym_certification_iv_reverse;

    /**
     * 選擇身份證正面
     */
    private List<LocalMedia> cardPositive = new ArrayList<>();

    /**
     * 選擇身份證反面
     */
    private List<LocalMedia> cardReverse = new ArrayList<>();

    /**
     * 選擇模式:全部.PictureMimeType.ofAll()、圖片.ofImage()、視訊.ofVideo()、音訊.ofAudio()
     */
    private int chooseMode = PictureMimeType.ofImage();

    /**
     * 主題id:R.style.picture_default_style、R.style.picture_white_style、R.style.picture_QQ_style、R.style.picture_Sina_style
     */
    private int themeId = R.style.picture_default_style;

    /**
     * 最多可選擇1張圖片
     */
    private int maxSelectNum = 1;

    /**
     * 正反圖片路徑
     */
    private String cardPositivePath = null, cardReversePath = null;

    /**
     * 儲存圖片,正反
     */
    private Bitmap cardPositiveBitMap, cardReverseBitMap;

    /**
     * 自動識別姓名  有效日期   身份證號碼
     */
    private EditText activity_autonym_certification_et_name;

    private EditText activity_autonym_certification_et_effective_date;

    private EditText activity_autonym_certification_et_id_card;

    /**
     * 存放正面識別資料的類
     */
    IdentifyResult result;

    /**
     * 存放反面識別資料的類
     */
      cardReverseRusult cardReverseRusult;


    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_autonym_certification);
        //初始化找id
        initViews();
    }

    private void initViews() {
        activity_autonym_certification_iv_positive=findViewById(R.id.activity_autonym_certification_iv_positive);
        activity_autonym_certification_iv_reverse=findViewById(R.id.activity_autonym_certification_iv_reverse);
        activity_autonym_certification_et_name=findViewById(R.id.activity_autonym_certification_et_name);
        activity_autonym_certification_et_effective_date=findViewById(R.id.activity_autonym_certification_et_effective_date);
        activity_autonym_certification_et_id_card=findViewById(R.id.activity_autonym_certification_et_id_card);
        activity_autonym_certification_iv_positive.setOnClickListener(this);
        activity_autonym_certification_iv_reverse.setOnClickListener(this);
        //簡單的申請兩個許可權
        
        if (ContextCompat.checkSelfPermission(AutonymCertificationActivity.this, Manifest.permission.WRITE_EXTERNAL_STORAGE) != PackageManager.PERMISSION_GRANTED) {
            ActivityCompat.requestPermissions(this,
                    new String[]{Manifest.permission.WRITE_EXTERNAL_STORAGE},
                    1);
        }
    }


    @Override
    public void onClick(View v) {
        switch (v.getId()) {
            //身份證正面點選事件
            case R.id.activity_autonym_certification_iv_positive:
                //0表示正面
                OpenPhotoAlbum(cardPositive, 0);
                break;

            //身份證反面的點選事件  1表示反面
            case R.id.activity_autonym_certification_iv_reverse:
                OpenPhotoAlbum(cardReverse, 1);
                break;
        }
    }

    /**
     * @param list 相片返回的地方
     * @param i    判斷返回的是正反    0是正面  1是反面
     */
    private void OpenPhotoAlbum(List list, int i) {
        // 進入相簿 以下是例子:不需要的api可以不寫
        PictureSelector.create(this)
                .openGallery(chooseMode)// 全部.PictureMimeType.ofAll()、圖片.ofImage()、視訊.ofVideo()、音訊.ofAudio()
                .theme(themeId)// 主題樣式設定 具體參考 values/styles   用法:R.style.picture.white.style
                .maxSelectNum(maxSelectNum)// 最大圖片選擇數量
                .minSelectNum(1)// 最小選擇數量
                .imageSpanCount(4)// 每行顯示個數
                .selectionMode(PictureConfig.MULTIPLE)// PictureConfig.MULTIPLE多選 or 單選PictureConfig.SINGLE
                .previewImage(true)// 是否可預覽圖片
                //.previewVideo(true)// 是否可預覽視訊
                //.enablePreviewAudio(ture) // 是否可播放音訊
                //.compressGrade(Luban.THIRD_GEAR)// luban壓縮檔次,預設3檔 Luban.FIRST_GEAR、Luban.CUSTOM_GEAR
                .isCamera(true)// 是否顯示拍照按鈕
                .isZoomAnim(true)// 圖片列表點選 縮放效果 預設true
                //.setOutputCameraPath("/CustomPath")// 自定義拍照儲存路徑
                //.enableCrop(false)// 是否裁剪
                .compress(true)// 是否壓縮
                // .compressMode(PictureConfig.SYSTEM_COMPRESS_MODE)//系統自帶 or 魯班壓縮 PictureConfig.SYSTEM_COMPRESS_MODE or LUBAN_COMPRESS_MODE
                //.sizeMultiplier(0.5f)// glide 載入圖片大小 0~1之間 如設定 .glideOverride()無效
                .glideOverride(160, 160)// glide 載入寬高,越小圖片列表越流暢,但會影響列表圖片瀏覽的清晰度
                //.withAspectRatio(0, 0)// 裁剪比例 如16:9 3:2 3:4 1:1 可自定義
                //.hideBottomControls(false)// 是否顯示uCrop工具欄,預設不顯示
                //.isGif(false)// 是否顯示gif圖片
                //.freeStyleCropEnabled(false)// 裁剪框是否可拖拽
                //.circleDimmedLayer(false)// 是否圓形裁剪
                //.showCropFrame(false)// 是否顯示裁剪矩形邊框 圓形裁剪時建議設為false
                //.showCropGrid(false)// 是否顯示裁剪矩形網格 圓形裁剪時建議設為false
                .openClickSound(false)// 是否開啟點選聲音
                .selectionMedia(list)// 是否傳入已選圖片
//                        .videoMaxSecond(15)
//                        .videoMinSecond(10)
                //.previewEggs(false)// 預覽圖片時 是否增強左右滑動圖片體驗(圖片滑動一半即可看到上一張是否選中)
                //.cropCompressQuality(90)// 裁剪壓縮質量 預設100
                //.compressMaxKB()//壓縮最大值kb compressGrade()為Luban.CUSTOM_GEAR有效
                //.compressWH() // 壓縮寬高比 compressGrade()為Luban.CUSTOM_GEAR有效
                //.cropWH()// 裁剪寬高比,設定如果大於圖片本身寬高則無效
                //.rotateEnabled() // 裁剪是否可旋轉圖片
                //.scaleEnabled()// 裁剪是否可放大縮小圖片
                //.videoQuality()// 視訊錄製質量 0 or 1
                //.videoSecond()//顯示多少秒以內的視訊or音訊也可適用
                //.recordVideoSecond()//錄製視訊秒數 預設60s
                .forResult(i);//結果回撥onActivityResult code(這裡自己設定了0.1 目的區分是正反)
    }

    //選擇完照片的回撥
    @Override
    protected void onActivityResult(int requestCode, int resultCode, Intent data) {
        super.onActivityResult(requestCode, resultCode, data);
        //選擇圖片回撥
        if (resultCode == RESULT_OK) {
            switch (requestCode) {
                case 0:
                    /**
                     * 正面識別
                     */
                    // 圖片選擇結果回撥
                    cardPositive = PictureSelector.obtainMultipleResult(data);
                    // 例如 LocalMedia 裡面返回三種path
                    // 1.media.getPath(); 為原圖path
                    // 2.media.getCutPath();為裁剪後path,需判斷media.isCut();是否為true
                    // 3.media.getCompressPath();為壓縮後path,需判斷media.isCompressed();是否為true
                    // 如果裁剪並壓縮了,以取壓縮路徑為準,因為是先裁剪後壓縮的

                    //首先獲取圖片地址
                    if (cardPositive.size() > 0) {
                        //首先確保大於0
                        LocalMedia localMedia = cardPositive.get(0);
                        cardPositivePath = localMedia.getPath();//正常的地址,看具體的業務,如果需要壓縮,則獲取壓縮地址
                        //拿到了地址,那麼就載入圖片
                        cardPositiveBitMap = BitMapUtils.getImage(cardPositivePath);
//                        //設定圖片
                        activity_autonym_certification_iv_positive.setImageBitmap(cardPositiveBitMap);
                        //設定完成自動識別
                        TecentHttpUtil.uploadIdCard(BitMapUtils.bitmapToBase64(cardPositiveBitMap), "0", new TecentHttpUtil.SimpleCallBack() {
                            @Override
                            public void Succ(String res) {
                                result = new Gson().fromJson(res, IdentifyResult.class);
                                if (result != null) {
                                    if (result.getErrorcode() == 0) {
                                        // 識別成功設定姓名
                                        activity_autonym_certification_et_name.setText(result.getName());
                                        //設定身份證號碼
                                        activity_autonym_certification_et_id_card.setText(result.getId());
                                    } else {
                                        Toast.makeText(AutonymCertificationActivity.this, "識別錯誤", Toast.LENGTH_SHORT).show();
                                /*switch (result.getErrorcode()){
                                    case -7001:
                                        Toast.makeText(MainActivity.this, "未檢測到身份證,請對準邊框(請避免拍攝時傾角和旋轉角過大、攝像頭)", Toast.LENGTH_SHORT).show();
                                        break;
                                    case -7002:
                                        Toast.makeText(MainActivity.this, "請使用第二代身份證件進行掃描", Toast.LENGTH_SHORT).show();
                                        break;
                                    case -7003:
                                        Toast.makeText(MainActivity.this, "不是身份證正面照片(請使用帶證件照的一面進行掃描)", Toast.LENGTH_SHORT).show();
                                        break;
                                    case -7004:
                                        Toast.makeText(MainActivity.this, "不是身份證反面照片(請使用身份證反面進行掃描)", Toast.LENGTH_SHORT).show();
                                        break;
                                    case -7005:
                                        Toast.makeText(MainActivity.this, "確保掃描證件影象清晰", Toast.LENGTH_SHORT).show();
                                        break;
                                    case -7006:
                                        Toast.makeText(MainActivity.this, "請避開燈光直射在證件表面", Toast.LENGTH_SHORT).show();
                                        break;
                                    default:
                                        Toast.makeText(MainActivity.this, "識別失敗,請稍後重試", Toast.LENGTH_SHORT).show();
                                        break;
                                }*/
                                    }
                                }
                            }

                            @Override
                            public void error() {
                                Log.i("識別錯誤", "error: ");
                            }
                        });
                    }
                    break;

                case 1:
                    /**
                     * 反面識別
                     */
                    cardReverse = PictureSelector.obtainMultipleResult(data);
                    if (cardReverse.size() > 0) {
                        //首先確保大於0
                        LocalMedia localMedia = cardReverse.get(0);
                        cardReversePath = localMedia.getPath();//正常的地址,看具體的業務,如果需要壓縮,則獲取壓縮地址
                        //拿到了地址,那麼就載入圖片
                        cardReverseBitMap = BitMapUtils.getImage(cardReversePath);
//                        //設定圖片
                        activity_autonym_certification_iv_reverse.setImageBitmap(cardReverseBitMap);

                        TecentHttpUtil.uploadIdCard(BitMapUtils.bitmapToBase64(cardReverseBitMap), "1", new TecentHttpUtil.SimpleCallBack() {
                            @Override
                            public void Succ(String res) {
                                Log.e("===========success", res);
                                cardReverseRusult = new Gson().fromJson(res, cardReverseRusult.class);

                                if (cardReverseRusult != null) {
                                    if (cardReverseRusult.getErrorcode() == 0) {
                                        //反面識別成功設定有效日期
                                        activity_autonym_certification_et_effective_date.setText(cardReverseRusult.getValid_date());
                                    } else {
                                        Toast.makeText(AutonymCertificationActivity.this, "識別錯誤", Toast.LENGTH_SHORT).show();

                                    }
                                }
                            }

                            @Override
                            public void error() {
                                Log.i("識別錯誤", "error: ");
                            }
                        });
                    }
                    break;
            }
        }

    }
    @Override
    public void onPointerCaptureChanged(boolean hasCapture) {

    }
}

到這來專案基本就跑起來了,程式碼不好,僅供參考,宣告,裡面有一些程式碼是參考了網路上的。