1. 程式人生 > >android 第三方app截圖

android 第三方app截圖

將View生成相應的圖片是很容易的,所以app內截圖可以採用此種方式。

view.setDrawingCacheEnabled(true);
view.buildDrawingCache();
Bitmap screenshot = view.getDrawingCache();
//使用完圖片之後再執行destroyDrawingCache,因為destroyDrawingCache內部會呼叫bitmap.recycle()
view.destroyDrawingCache();
view.setDrawingCacheEnabled(false);

拿到了bitmap之後,還需要對其進行處理,分為下面幾個部分/幾種情況:

1.狀態列

2.導航欄

3.魅族flyme的smartbar

對於狀態列,app是無法截圖的,截出來只是狀態列底色,上面的通知和時間電量等資訊是沒有的,所以一般會去掉狀態列這一塊

對於導航欄,這個是可以截到的,但是內容和app無關,只是3個按鈕,可能也不好看,所以一般也會去掉

另外,魅族還有smartbar,一般也需要幹掉

對於上面3條,我們只需要得知其高度即可,然後去除這幾部分(這裡沒有考慮橫屏)

//width為截圖寬度,height為最終的圖片高度,即處理過狀態列/導航欄/smartbar之後的高度
//top為狀態列的高度
Bitmap bg = Bitmap.createBitmap(width, height, Bitmap.Config.ARGB_8888);
Canvas canvas = new Canvas(bg);
canvas.drawBitmap(screenshot, width, top, null);
screenshot.recycle();

下面是對於魅族的flyme特殊處理的部分

判斷flyme系統

/**
 * 判斷是否是魅族系統
 * @return
 */
public static boolean isFlyme() {
    try {
        // Invoke Build.hasSmartBar()
        final Method method = Build.class.getMethod("hasSmartBar");
        return method != null;
    } catch (final Exception e) {
        return false;
    }
}

獲取smartbar高度

//獲取魅族smartbar高度
public static int getSmartBarHeight(Context context) {
    try {
        Class clazz = Class.forName("com.android.internal.R$dimen");
        Object obj = clazz.newInstance();
        Field field = clazz.getField("mz_action_button_min_height");
        int height = Integer.parseInt(field.get(obj).toString());
        return context.getResources().getDimensionPixelSize(height);
    } catch (ClassNotFoundException e) {
        Log.w(TAG, e);
    } catch (InstantiationException e) {
        Log.w(TAG, e);
    } catch (IllegalAccessException e) {
        Log.w(TAG, e);
    } catch (NoSuchFieldException e) {
        Log.w(TAG, e);
    }
    return 0;
}

如何獲取狀態列/導航欄高度這裡不再贅述

上面說的是一般情況,下面我們來說說幾種特殊情況

1.如何擷取dialog

如果直接在activity獲取window中的DecorView,擷取的圖片實際是沒有dialog部分的,只有dialog下面的頁面。想要獲取dialog截圖,我們可以先獲取dialog引用,然後獲取

dialog.getWindow().getDecorView()

2.當頁面沒有佔滿螢幕時

舉個例子,有的時候我們會把頁面做成半窗形式,螢幕上方還能看到上一個頁面的內容。這時activity只有螢幕下方那部分,所以這時處理截圖時不能再減去狀態列那部分了,因為此時截圖上面根本沒有狀態列

3.webview截圖

在4.3系統上面,使用getDecorView().getDrawingCache()方法有時不能準確的擷取webview上面顯示的內容。當webview裡顯示tab形式的頁面時,有時不管當前處於哪個tab,截圖出來的都是第一個tab的內容。

但是,如果使用webview.getDrawingCache(),那麼是能得到正確的圖片的,所以我在含有webview的頁面中截圖方式是遍歷頁面中的view,然後將圖片拼到一起