這個許可權動態申請庫,值得嘗試一下

arvinljw發表於2018-09-19

最近又看到有人是分享使用空Fragment,來避免重寫onActivityResult進行Activity之間資訊的互動,這讓我想起了之前看到的RxPermissions這個庫也是使用這個原理去申請許可權,當時覺得居然還有這種操作,想象力真是太好了。

但是即使它這個再好,我還是想說我這個可能更好一點。

專案地址

優點

  • 沒有使用多餘的第三方庫
  • Google許可權申請的最佳實踐
  • 使用簡單,低耦合,可自定義提示框樣式
  • 整合6.0、7.0、8.0許可權(後兩個待完善
  • 申請Manifest中沒有的許可權時,增加提示(待完成

用法

引用

1、在根目錄的build.gradle中加入如下配置

allprojects {
    repositories {
        ...
        maven { url 'https://jitpack.io' }
    }
}
複製程式碼

2、在要是用的module中增加如下引用

dependencies {
    ...
    implementation 'com.android.support:appcompat-v7:27.1.1'
    implementation 'com.github.arvinljw:PermissionHelper:v1.0.0'
}
複製程式碼

使用

1、初始化PermissionUtil

permissionUtil = new PermissionUtil.Builder()
        .with(this)//必傳:可使用FragmentActivity或v4.app.Fragment例項
        .setTitleText("提示")//彈框標題
        .setEnsureBtnText("確定")//許可權說明彈框授權按鈕文字
        .setCancelBtnText("取消")//許可權說明彈框取消授權按鈕文字
        .setSettingEnsureText("設定")//開啟設定說明彈框開啟按鈕文字
        .setSettingCancelText("取消")//開啟設定說明彈框關閉按鈕文字
        .setSettingMsg("當前應用缺少必要許可權。\n請點選\"設定\"-\"許可權\"-開啟所需許可權。")//開啟設定說明彈框內容文字
        .setShowSetting(true)//是否開啟設定說明彈框
        .setTitleColor(Color.BLACK)//彈框標題文字顏色
        .setMsgColor(Color.GRAY)//彈框內容文字顏色
        .setEnsureBtnColor(Color.BLACK)//彈框確定文字顏色
        .setCancelBtnColor(Color.BLACK)//彈框取消文字顏色
        .build();
複製程式碼

需要說明一下這裡可能有兩個彈框:

  • 第一個彈框:第一次申請許可權被拒絕後,彈出的彈框,解釋為什麼需要這個許可權。
  • 第二個彈框:開啟設定說明的彈框,只有當isShowSetting為true的時候,被拒絕一次之後,再次申請時再次拒絕且還點了不再提示,則通過開啟設定去讓使用者手動修改許可權。

其中彈框使用的是AlertDialog,通過反射去修改文字顏色,不設定則不會呼叫反射方法,會有預設顏色:

  • 標題使用:textAppearanceLarge樣式
  • 內容實用:textAppearanceMedium樣式
  • 按鈕顏色:預設使用colorAccent的顏色

2、申請許可權並回撥

permissionUtil.request("需要讀取聯絡人許可權",
        Manifest.permission.READ_PHONE_STATE,
        new PermissionUtil.RequestPermissionListener() {
            @Override
            public void callback(boolean granted, boolean isAlwaysDenied) {
                if (granted) {
                    //do your jobs..
                } else {
                    //show some tips..
                }
            }
        });
複製程式碼
  • 第一個引數:是申請許可權說明,會在上文說的第一個彈框中作為內容顯示

  • 第二個引數:是一個所要申請的許可權字串,也可以使用字串陣列,例如申請多個許可權可使用:

    PermissionUtil.asArray(Manifest.permission.READ_PHONE_STATE,Manifest.permission.READ_CONTACTS)

  • 第三個引數:申請許可權的回撥,granted表示是否通過,如果有多個許可權的話表示是否全部通過;isAlwaysDenied false表示會重複提示,true表示拒絕且不再提示

通過這兩步,就能完全許可權的申請了,當然這裡申請的許可權需要在配置檔案中定義。

3、清除permissionUtil持有的回撥

這一步清除回撥,避免匿名內部類引起的記憶體洩露。

if (permissionUtil != null) {
    permissionUtil.removeListener();
    permissionUtil = null;
}
複製程式碼

混淆

-keep class net.arvin.permissionhelper.**{*;}
複製程式碼

注意

這裡想說,有的手機只要使用者永久拒絕了許可權,那麼開啟設定去手動開啟許可權也是無效的,索然會回撥已獲取許可權,但是實際的使用中是獲取不到那些資訊的,例如聯絡人或者手機裝置資訊,我測試到的例如小米。當然如果能獲取到的自然就不用管了。

這個問題目前測試的其他庫也存在,所以這個問題尚未找到最好的解決方案

我參考了支付寶發現,在申請許可權之前就先彈一個框告訴使用者我需要這個許可權,你要給我,如果你不給,就不去申請許可權。但是如果點了給許可權,但是在真正的許可權彈框時又不給,依然無法解決,這個是系統的原因,改不了。

目前有兩個辦法能讓處於拒絕且不再提示的應用重新獲取許可權:

  • 開啟應用設定詳情介面(參照lib中開啟方式),然後使用者手動關閉相應許可權,如果已關閉則開啟再關閉,這時候這個系統會傳送一個廣播重啟該應用,所以需要做好資料儲存和恢復工作。
  • 第二種方式就是手動清除應用所有資料,之前所有許可權以及快取都會消失,這種顯然不是很友好,要是能找到許可權的快取資料存在哪個地方去手動清除也是一種辦法,知道的朋友請不吝賜教。

這是我發現的這個問題,要是有更好的解決方案,從而不會有這個問題的也請不吝賜教,那就非常感謝了。

如果覺得好,可以star支援一下。

專案地址

參考

參考文章:

參考專案:

相關文章