Android 6.0 permissions multiples

Je sais que Android 6.0 A de nouvelles permissions et je sais que je peux les appeler avec quelque chose comme ça

if (ContextCompat.checkSelfPermission(this, Manifest.permission.WRITE_EXTERNAL_STORAGE) !=
    PackageManager.PERMISSION_GRANTED) {
    ActivityCompat.requestPermissions(this,
        new String[] { 
            Manifest.permission.WRITE_EXTERNAL_STORAGE
        }, PERMISSION_WRITE_STORAGE);
}

Aujourd'hui, j'ai vu une application Google qui nécessite 3 autorisations: contacts, sms et appareil photo. Il fait une page 1-3 et les appelle tous ensemble en même temps pour activer.

est-ce que quelqu'un peut me dire comment je peux appeler 4 permissions pour activer à la fois sms, appareil photo, contacts et stockage?

exemple (oublié le nom de l'application google :( )

L'application a besoin de sms,de contacts et d'appareils photo

l'application m'a demandé (et a fait un dialogue page1-3) d'activer sms, Activer contacts et puis caméra. Donc, cette application google appelait les 3 permissions requises ensemble et ma question Est Comment puis-je obtenir la même chose ?

119
demandé sur Ahmad Aghazadeh 2015-12-17 22:34:51

19 réponses

il suffit d'inclure les 4 permissions dans l'appel ActivityCompat.requestPermissions(...) et Android les affichera automatiquement ensemble comme vous l'avez mentionné.

j'ai une méthode d'aide pour vérifier les permissions multiples et voir si l'une d'elles n'est pas accordée.

public static boolean hasPermissions(Context context, String... permissions) {
    if (context != null && permissions != null) {
        for (String permission : permissions) {
            if (ActivityCompat.checkSelfPermission(context, permission) != PackageManager.PERMISSION_GRANTED) {
                return false;
            }
        }
    }
    return true;
}

ensuite, il suffit de lui envoyer toutes les permissions. Android ne demandera que ceux dont il a besoin.

// The request code used in ActivityCompat.requestPermissions()
// and returned in the Activity's onRequestPermissionsResult()
int PERMISSION_ALL = 1; 
String[] PERMISSIONS = {
  android.Manifest.permission.READ_CONTACTS, 
  android.Manifest.permission.WRITE_CONTACTS, 
  android.Manifest.permission.WRITE_EXTERNAL_STORAGE, 
  android.Manifest.permission.READ_SMS, 
  android.Manifest.permission.CAMERA
};

if(!hasPermissions(this, PERMISSIONS)){
    ActivityCompat.requestPermissions(this, PERMISSIONS, PERMISSION_ALL);
}
216
répondu James McCracken 2018-07-22 13:53:19

voici un exemple détaillé avec plusieurs demandes de permission:-

l'application a besoin de 2 permissions au démarrage . SEND_SMS et ACCESS_FINE_LOCATION (tous deux sont mentionnés dans le manifeste.XML.)

j'utilise Support Library v4 qui est prêt à gérer Android pre-Marshmallow et donc pas besoin de vérifier les versions de construction.

dès Que l'application démarre, il vous demande de plusieurs les autorisations d'ensemble. Si les deux permissions sont accordées, le flux normal disparaît.

enter image description here

enter image description here

public static final int REQUEST_ID_MULTIPLE_PERMISSIONS = 1;
@Override
protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.activity_main);
    if(checkAndRequestPermissions()) {
        // carry on the normal flow, as the case of  permissions  granted.
    }
}

private  boolean checkAndRequestPermissions() {
    int permissionSendMessage = ContextCompat.checkSelfPermission(this,
            Manifest.permission.SEND_SMS);
    int locationPermission = ContextCompat.checkSelfPermission(this, Manifest.permission.ACCESS_FINE_LOCATION);
    List<String> listPermissionsNeeded = new ArrayList<>();
    if (locationPermission != PackageManager.PERMISSION_GRANTED) {
        listPermissionsNeeded.add(Manifest.permission.ACCESS_FINE_LOCATION);
    }
    if (permissionSendMessage != PackageManager.PERMISSION_GRANTED) {
        listPermissionsNeeded.add(Manifest.permission.SEND_SMS);
    }
    if (!listPermissionsNeeded.isEmpty()) {
        ActivityCompat.requestPermissions(this, listPermissionsNeeded.toArray(new String[listPermissionsNeeded.size()]),REQUEST_ID_MULTIPLE_PERMISSIONS);
        return false;
    }
    return true;
}

ContextCompat.checkSelfPermission (), ActivityCompat.requestPermissions (), ActivityCompat.shouldShowRequestPermissionRationale () font partie de la bibliothèque de soutien.

Si une ou plusieurs permissions ne sont pas accordées, ActivityCompat.requestPermissions() demandera les permissions et le contrôle va à la méthode de callback onRequestPermissionsResult ().

vous devez vérifier la valeur du drapeau shouldShowRequestPermissionRationale() dans la méthode de callback onRequestPermissionsResult ().

il n'y a que deux cas:--

Cas 1: -chaque fois que l'utilisateur clique sur Refuser les autorisations (y compris la première fois), elle retournera true. Ainsi, lorsque l'utilisateur nie, nous pouvons montrer plus d'explications et demander à nouveau

cas 2: - seulement si l'utilisateur sélectionne" ne demande plus jamais " il retournera false. Dans ce cas, nous pouvons continuer avec des fonctionnalités limitées et guide de l'utilisateur pour activer les autorisations de paramètres pour plus de fonctionnalités, ou nous pouvons terminer l'installation, si les autorisations sont triviales pour l'application.

"151930920 CAS" -1

enter image description here

CAS 2

enter image description here

    @Override
    public void onRequestPermissionsResult(int requestCode,
                                           String permissions[], int[] grantResults) {
        Log.d(TAG, "Permission callback called-------");
        switch (requestCode) {
            case REQUEST_ID_MULTIPLE_PERMISSIONS: {

                Map<String, Integer> perms = new HashMap<>();
                // Initialize the map with both permissions
                perms.put(Manifest.permission.SEND_SMS, PackageManager.PERMISSION_GRANTED);
                perms.put(Manifest.permission.ACCESS_FINE_LOCATION, PackageManager.PERMISSION_GRANTED);
                // Fill with actual results from user
                if (grantResults.length > 0) {
                    for (int i = 0; i < permissions.length; i++)
                        perms.put(permissions[i], grantResults[i]);
                    // Check for both permissions
                    if (perms.get(Manifest.permission.SEND_SMS) == PackageManager.PERMISSION_GRANTED
                            && perms.get(Manifest.permission.ACCESS_FINE_LOCATION) == PackageManager.PERMISSION_GRANTED) {
                        Log.d(TAG, "sms & location services permission granted");
                        // process the normal flow
                        //else any one or both the permissions are not granted
                    } else {
                            Log.d(TAG, "Some permissions are not granted ask again ");
                            //permission is denied (this is the first time, when "never ask again" is not checked) so ask again explaining the usage of permission
//                        // shouldShowRequestPermissionRationale will return true
                            //show the dialog or snackbar saying its necessary and try again otherwise proceed with setup.
                            if (ActivityCompat.shouldShowRequestPermissionRationale(this, Manifest.permission.SEND_SMS) || ActivityCompat.shouldShowRequestPermissionRationale(this, Manifest.permission.ACCESS_FINE_LOCATION)) {
                                showDialogOK("SMS and Location Services Permission required for this app",
                                        new DialogInterface.OnClickListener() {
                                            @Override
                                            public void onClick(DialogInterface dialog, int which) {
                                                switch (which) {
                                                    case DialogInterface.BUTTON_POSITIVE:
                                                        checkAndRequestPermissions();
                                                        break;
                                                    case DialogInterface.BUTTON_NEGATIVE:
                                                        // proceed with logic by disabling the related features or quit the app.
                                                        break;
                                                }
                                            }
                                        });
                            }
                            //permission is denied (and never ask again is  checked)
                            //shouldShowRequestPermissionRationale will return false
                            else {
                                Toast.makeText(this, "Go to settings and enable permissions", Toast.LENGTH_LONG)
                                        .show();
    //                            //proceed with logic by disabling the related features or quit the app.
                            }
                    }
                }
            }
        }

    }

    private void showDialogOK(String message, DialogInterface.OnClickListener okListener) {
        new AlertDialog.Builder(this)
                .setMessage(message)
                .setPositiveButton("OK", okListener)
                .setNegativeButton("Cancel", okListener)
                .create()
                .show();
    }
77
répondu Nicks 2016-02-19 01:42:52

petit code:

 public static final int MULTIPLE_PERMISSIONS = 10; // code you want.

 String[] permissions= new String[]{
        Manifest.permission.WRITE_EXTERNAL_STORAGE,
        Manifest.permission.CAMERA,
        Manifest.permission.ACCESS_COARSE_LOCATION,
        Manifest.permission.ACCESS_FINE_LOCATION};


if (checkPermissions())
         //  permissions  granted.    
}

private  boolean checkPermissions() {
        int result;
        List<String> listPermissionsNeeded = new ArrayList<>();
        for (String p:permissions) {
            result = ContextCompat.checkSelfPermission(getActivity(),p);
            if (result != PackageManager.PERMISSION_GRANTED) {
                listPermissionsNeeded.add(p);
            }
        }
        if (!listPermissionsNeeded.isEmpty()) {
            ActivityCompat.requestPermissions(this, listPermissionsNeeded.toArray(new String[listPermissionsNeeded.size()]),MULTIPLE_PERMISSIONS );
            return false;
        }
        return true;
    }


   @Override
    public void onRequestPermissionsResult(int requestCode, String permissionsList[], int[] grantResults) {
        switch (requestCode) {
            case MULTIPLE_PERMISSIONS:{
                if (grantResults.length > 0) {
                String permissionsDenied = "";
                for (String per : permissionsList) {
                    if(grantResults[0] == PackageManager.PERMISSION_DENIED){
                        permissionsDenied += "\n" + per;

                    } 

                }
                // Show permissionsDenied 
                updateViews();
            }
                return;
            }
        }
     }

liste des permissions Android permissions normales et permissions dangereuses dans API 23

27
répondu Ahmad Aghazadeh 2018-07-23 04:58:09

dans un Fragment

public class Homefragment extends Fragment {
    View hfrag;
   Context context;
 public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {

//first we must check the permissions are already granted

        hfrag = inflater.inflate(R.layout.home, container, false);
        context = getActivity();
checkAndRequestPermissions();

}




}


private boolean checkAndRequestPermissions() {
        int permissionSendMessage = ContextCompat.checkSelfPermission(context,
                Manifest.permission.READ_SMS);
        int contactpermission = ContextCompat.checkSelfPermission(context, Manifest.permission.GET_ACCOUNTS);

        int writepermission = ContextCompat.checkSelfPermission(context, Manifest.permission.WRITE_EXTERNAL_STORAGE);

        int callpermission = ContextCompat.checkSelfPermission(context, Manifest.permission.CALL_PHONE);

        int receivepermission = ContextCompat.checkSelfPermission(context, Manifest.permission.RECEIVE_SMS);
        int locationpermission = ContextCompat.checkSelfPermission(context, Manifest.permission.ACCESS_FINE_LOCATION);

        List<String> listPermissionsNeeded = new ArrayList<>();

        if (locationpermission != PackageManager.PERMISSION_GRANTED) {
            listPermissionsNeeded.add(Manifest.permission.ACCESS_FINE_LOCATION);
        }

        if (contactpermission != PackageManager.PERMISSION_GRANTED) {
            listPermissionsNeeded.add(Manifest.permission.GET_ACCOUNTS);
        }
        if (writepermission != PackageManager.PERMISSION_GRANTED) {
            listPermissionsNeeded.add(Manifest.permission.WRITE_EXTERNAL_STORAGE);
        }
        if (permissionSendMessage != PackageManager.PERMISSION_GRANTED) {
            listPermissionsNeeded.add(Manifest.permission.READ_SMS);
        }
        if (receivepermission != PackageManager.PERMISSION_GRANTED) {
            listPermissionsNeeded.add(Manifest.permission.RECEIVE_SMS);
        }

        if (callpermission != PackageManager.PERMISSION_GRANTED) {
            listPermissionsNeeded.add(Manifest.permission.CALL_PHONE);
        }
        if (!listPermissionsNeeded.isEmpty()) {
            requestPermissions(listPermissionsNeeded.toArray(new String[listPermissionsNeeded.size()]), REQUEST_ID_MULTIPLE_PERMISSIONS);
            return false;
        }
        return true;
    }



 @Override
public void onRequestPermissionsResult(int requestCode, @NonNull String[] permissions, @NonNull int[] grantResults) {
    super.onRequestPermissionsResult(requestCode, permissions, grantResults);


    if (requestCode == REQUEST_ID_MULTIPLE_PERMISSIONS) {


        if (grantResults.length > 0) {
            for (int i = 0; i < permissions.length; i++) {


                if (permissions[i].equals(Manifest.permission.GET_ACCOUNTS)) {
                    if (grantResults[i] == PackageManager.PERMISSION_GRANTED) {
                        Log.e("msg", "accounts granted");

                    }
                } else if (permissions[i].equals(Manifest.permission.WRITE_EXTERNAL_STORAGE)) {
                    if (grantResults[i] == PackageManager.PERMISSION_GRANTED) {
                        Log.e("msg", "storage granted");

                    }
                } else if (permissions[i].equals(Manifest.permission.CALL_PHONE)) {
                    if (grantResults[i] == PackageManager.PERMISSION_GRANTED) {
                        Log.e("msg", "call granted");

                    }
                } else if (permissions[i].equals(Manifest.permission.RECEIVE_SMS)) {
                    if (grantResults[i] == PackageManager.PERMISSION_GRANTED) {
                        Log.e("msg", "sms granted");

                    }
                } else if (permissions[i].equals(Manifest.permission.ACCESS_FINE_LOCATION)) {
                    if (grantResults[i] == PackageManager.PERMISSION_GRANTED) {
                        Log.e("msg", "location granted");

                    }
                }


            }

        }


    }
}

}

8
répondu Antony jackson 2016-07-25 09:07:42

C'est facile, le faire de cette façon

private static final int REQUEST_READ_PHONE_STATE = 110 , REQUEST_ACCESS_FINE_LOCATION = 111, REQUEST_WRITE_STORAGE = 112;

Dans votre onCreate

 //request permission
    boolean hasPermissionPhoneState = (ContextCompat.checkSelfPermission(getApplicationContext(),
            Manifest.permission.READ_PHONE_STATE) == PackageManager.PERMISSION_GRANTED);
    if (!hasPermissionPhoneState) {
        ActivityCompat.requestPermissions(LoginActivity.this,
                new String[]{Manifest.permission.READ_PHONE_STATE},
                REQUEST_READ_PHONE_STATE);
    }

    boolean hasPermissionLocation = (ContextCompat.checkSelfPermission(getApplicationContext(),
            Manifest.permission.ACCESS_FINE_LOCATION) == PackageManager.PERMISSION_GRANTED);
    if (!hasPermissionLocation) {
        ActivityCompat.requestPermissions(LoginActivity.this,
                new String[]{Manifest.permission.ACCESS_FINE_LOCATION},
                REQUEST_ACCESS_FINE_LOCATION);
    }

    boolean hasPermissionWrite = (ContextCompat.checkSelfPermission(getApplicationContext(),
            Manifest.permission.WRITE_EXTERNAL_STORAGE) == PackageManager.PERMISSION_GRANTED);
    if (!hasPermissionWrite) {
        ActivityCompat.requestPermissions(LoginActivity.this,
                new String[]{Manifest.permission.WRITE_EXTERNAL_STORAGE},
                REQUEST_WRITE_STORAGE);
    }

puis vérifier le résultat

@Override
public void onRequestPermissionsResult(int requestCode, String[] permissions, int[] grantResults) {
    super.onRequestPermissionsResult(requestCode, permissions, grantResults);
    switch (requestCode)
    {
        case REQUEST_READ_PHONE_STATE: {
            if (grantResults.length > 0 && grantResults[0] == PackageManager.PERMISSION_GRANTED)
            {
                Toast.makeText(LoginActivity.this, "Permission granted.", Toast.LENGTH_SHORT).show();
                //reload my activity with permission granted or use the features what required the permission
                finish();
                startActivity(getIntent());
            } else
            {
                Toast.makeText(LoginActivity.this, "The app was not allowed to get your phone state. Hence, it cannot function properly. Please consider granting it this permission", Toast.LENGTH_LONG).show();
            }
        }
        case REQUEST_ACCESS_FINE_LOCATION: {
            if (grantResults.length > 0 && grantResults[0] == PackageManager.PERMISSION_GRANTED)
            {
                Toast.makeText(LoginActivity.this, "Permission granted.", Toast.LENGTH_SHORT).show();
                //reload my activity with permission granted or use the features what required the permission
                finish();
                startActivity(getIntent());
            } else
            {
                Toast.makeText(LoginActivity.this, "The app was not allowed to get your location. Hence, it cannot function properly. Please consider granting it this permission", Toast.LENGTH_LONG).show();
            }
        }

        case REQUEST_WRITE_STORAGE: {
            if (grantResults.length > 0 && grantResults[0] == PackageManager.PERMISSION_GRANTED)
            {
                Toast.makeText(LoginActivity.this, "Permission granted.", Toast.LENGTH_SHORT).show();
                //reload my activity with permission granted or use the features what required the permission
                finish();
                startActivity(getIntent());
            } else
            {
                Toast.makeText(LoginActivity.this, "The app was not allowed to write to your storage. Hence, it cannot function properly. Please consider granting it this permission", Toast.LENGTH_LONG).show();
            }
        }
    }

}
7
répondu Tharindu Bandara 2016-10-12 11:31:42

ma classe handler pour les permissions multiples de requêtes. Vous pouvez vérifier le au complet en utilisant ici

public class RequestPermissionHandler {
    private Activity mActivity;
    private RequestPermissionListener mRequestPermissionListener;
    private int mRequestCode;

    public void requestPermission(Activity activity, @NonNull String[] permissions, int requestCode,
            RequestPermissionListener listener) {
        mActivity = activity;
        mRequestCode = requestCode;
        mRequestPermissionListener = listener;

        if (!needRequestRuntimePermissions()) {
            mRequestPermissionListener.onSuccess();
            return;
        }
        requestUnGrantedPermissions(permissions, requestCode);
    }

    private boolean needRequestRuntimePermissions() {
        return Build.VERSION.SDK_INT >= Build.VERSION_CODES.M;
    }

    private void requestUnGrantedPermissions(String[] permissions, int requestCode) {
        String[] unGrantedPermissions = findUnGrantedPermissions(permissions);
        if (unGrantedPermissions.length == 0) {
            mRequestPermissionListener.onSuccess();
            return;
        }
        ActivityCompat.requestPermissions(mActivity, unGrantedPermissions, requestCode);
    }

    private boolean isPermissionGranted(String permission) {
        return ActivityCompat.checkSelfPermission(mActivity, permission)
                == PackageManager.PERMISSION_GRANTED;
    }

    private String[] findUnGrantedPermissions(String[] permissions) {
        List<String> unGrantedPermissionList = new ArrayList<>();
        for (String permission : permissions) {
            if (!isPermissionGranted(permission)) {
                unGrantedPermissionList.add(permission);
            }
        }
        return unGrantedPermissionList.toArray(new String[0]);
    }

    public void onRequestPermissionsResult(int requestCode, @NonNull String[] permissions,
            @NonNull int[] grantResults) {
        if (requestCode == mRequestCode) {
            if (grantResults.length > 0) {
                for (int grantResult : grantResults) {
                    if (grantResult != PackageManager.PERMISSION_GRANTED) {
                        mRequestPermissionListener.onFailed();
                        return;
                    }
                }
                mRequestPermissionListener.onSuccess();
            } else {
                mRequestPermissionListener.onFailed();
            }
        }
    }

    public interface RequestPermissionListener {
        void onSuccess();

        void onFailed();
    }
}

enter image description here

4
répondu Phan Van Linh 2017-11-30 09:27:57

la méthodologie suivante est d'environ

  • demande dynamique de permissions;
  • montrant un AlertDialog si l'utilisateur refuse toute permission
  • boucle jusqu'à ce que l'utilisateur accepte la(les) permission (s)

Créer "statique" de la classe pour les autorisations de méthodes

public class PermissionsUtil {
    public static final int PERMISSION_ALL = 1;

    public static boolean doesAppNeedPermissions(){
        return android.os.Build.VERSION.SDK_INT > Build.VERSION_CODES.LOLLIPOP_MR1;
    }

    public static String[] getPermissions(Context context)
            throws PackageManager.NameNotFoundException {
        PackageInfo info = context.getPackageManager().getPackageInfo(
                context.getPackageName(), PackageManager.GET_PERMISSIONS);

        return info.requestedPermissions;
    }

    public static void askPermissions(Activity activity){
        if(doesAppNeedPermissions()) {
            try {
                String[] permissions = getPermissions(activity);

                if(!checkPermissions(activity, permissions)){
                    ActivityCompat.requestPermissions(activity, permissions,
                            PERMISSION_ALL);
                }
            } catch(Exception e) {
                e.printStackTrace();
            }
        }
    }

    public static boolean checkPermissions(Context context, String... permissions){
        if (android.os.Build.VERSION.SDK_INT >= Build.VERSION_CODES.M && context != null &&
                permissions != null) {
            for (String permission : permissions) {
                if (ContextCompat.checkSelfPermission(context, permission) !=
                        PackageManager.PERMISSION_GRANTED) {
                    return false;
                }
            }
        }
        return true;
    }
}

Dans Activité Principale.java

    private void checkPermissions(){
        PermissionsUtil.askPermissions(this);
    }

    @Override
    public void onRequestPermissionsResult(int requestCode,
                                           @NonNull String[] permissions,
                                           @NonNull int[] grantResults) {
        super.onRequestPermissionsResult(requestCode, permissions, grantResults);
        switch (requestCode) {
            case PermissionsUtil.PERMISSION_ALL: {

                if (grantResults.length > 0) {

                    List<Integer> indexesOfPermissionsNeededToShow = new ArrayList<>();

                    for(int i = 0; i < permissions.length; ++i) {
                        if(ActivityCompat.shouldShowRequestPermissionRationale(this, permissions[i])) {
                            indexesOfPermissionsNeededToShow.add(i);
                        }
                    }

                    int size = indexesOfPermissionsNeededToShow.size();
                    if(size != 0) {
                        int i = 0;
                        boolean isPermissionGranted = true;

                        while(i < size && isPermissionGranted) {
                            isPermissionGranted = grantResults[indexesOfPermissionsNeededToShow.get(i)]
                                    == PackageManager.PERMISSION_GRANTED;
                            i++;
                        }

                        if(!isPermissionGranted) {

                            showDialogNotCancelable("Permissions mandatory",
                                    "All the permissions are required for this app",
                                    new DialogInterface.OnClickListener() {
                                        @Override
                                        public void onClick(DialogInterface dialogInterface, int i) {
                                            checkPermissions();
                                        }
                                    });
                        }
                    }
                }
            }
        }
    }

    private void showDialogNotCancelable(String title, String message,
                                         DialogInterface.OnClickListener okListener) {
        new AlertDialog.Builder(this)
                .setTitle(title)
                .setMessage(message)
                .setPositiveButton("OK", okListener)
                .setCancelable(false)
                .create()
                .show();
    }
3
répondu Nicolas Bodin-Ripert 2016-12-16 10:08:14

mon approche est basée sur la réponse de Nicks et je l'espère est un peu plus utilisable pour les permissions multiples (autant que nécessaire, pas seulement deux). Il suggère d'ajouter des Permissionsuniquesresponsabilité par classe:

import android.app.Activity;
import android.app.AlertDialog;
import android.content.pm.PackageManager;
import android.support.v4.app.ActivityCompat;
import android.support.v4.content.ContextCompat;
import android.util.Log;

import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

public class PermissionsHelper {

private static final int REQUEST_ID_MULTIPLE_PERMISSIONS = 100; // any code you want.

public void checkAndRequestPermissions(Activity activity, String... permissions) {
    List<String> listPermissionsNeeded = new ArrayList<>();
    for (String permission : permissions) {
        if (ContextCompat.checkSelfPermission(activity, permission) != PackageManager.PERMISSION_GRANTED) {
            listPermissionsNeeded.add(permission);
        }
    }
    if (!listPermissionsNeeded.isEmpty()) {
        ActivityCompat.requestPermissions(activity, listPermissionsNeeded.toArray(new String[listPermissionsNeeded.size()]), REQUEST_ID_MULTIPLE_PERMISSIONS);
    }
}

public void onRequestPermissionsResult(Activity activity, int requestCode, String permissions[], int[] grantResults) {
    switch (requestCode) {
        case REQUEST_ID_MULTIPLE_PERMISSIONS: {
            Map<String, Integer> perms = new HashMap<>();

            for (String permission : permissions) {
                perms.put(permission, PackageManager.PERMISSION_GRANTED);
            }

            if (grantResults.length > 0) {
                for (int i = 0; i < permissions.length; i++)
                    perms.put(permissions[i], grantResults[i]);

                boolean allPermissionsGranted = true;
                for (String permission1 : permissions) {
                    allPermissionsGranted = allPermissionsGranted && (perms.get(permission1) == PackageManager.PERMISSION_GRANTED);
                }

                if (allPermissionsGranted) {
                    Log.d(PermissionsHelper.class.getSimpleName(), "onRequestPermissionsResult: all permissions granted");
                } else {
                    for (String permission2 : perms.keySet())
                        if (perms.get(permission2) == PackageManager.PERMISSION_GRANTED)
                            perms.remove(permission2);

                    StringBuilder message = new StringBuilder("The app has not been granted permissions:\n\n");
                    for (String permission : perms.keySet()) {
                        message.append(permission);
                        message.append("\n");
                    }
                    message.append("\nHence, it cannot function properly." +
                            "\nPlease consider granting it this permission in phone Settings.");

                    AlertDialog.Builder builder = new AlertDialog.Builder(activity);
                    builder.setTitle(R.string.permission_required)
                            .setMessage(message)
                            .setPositiveButton(android.R.string.ok, (dialog, id) -> dialog.cancel());
                    AlertDialog alert = builder.create();
                    alert.show();
                }
            }
        }
    }
}

}

si une ou plusieurs permissions requises n'ont pas été accordées par l'utilisateur, le message AlertDialog détaillé lui sera montré.

exemple d'utilisation en activité:

private PermissionsHelper permissionsHelper;

@Override
protected void onCreate(@Nullable Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);

    checkPermissions();

    //any other code
}

@Override
public void onRequestPermissionsResult(int requestCode, @NonNull String[] permissions, @NonNull int[] grantResults) {
    permissionsHelper.onRequestPermissionsResult(this, requestCode, permissions, grantResults);
}

private void checkPermissions() {
    permissionsHelper = new PermissionsHelper();
    permissionsHelper.checkAndRequestPermissions(this,
            Manifest.permission.READ_EXTERNAL_STORAGE,
            Manifest.permission.ACCESS_FINE_LOCATION,
            Manifest.permission.ACCESS_COARSE_LOCATION);
}

espère que cela sera utile pour quelqu'un.

3
répondu Andrew Vovk 2017-10-24 09:53:11

vérifier toutes les situations

en cas de refus d' - montrant la boîte de dialogue d'Alerte à l'utilisateur pourquoi nous avons besoin de la permission

public static final int MULTIPLE_PERMISSIONS = 1;
public static final int CAMERA_PERMISSION_REQUEST_CODE = 2;
public static final int STORAGE_PERMISSION_REQUEST_CODE = 3;

    private void askPermissions() {

    int permissionCheckStorage = ContextCompat.checkSelfPermission(this,
            Manifest.permission.WRITE_EXTERNAL_STORAGE);

    int permissionCheckCamera = ContextCompat.checkSelfPermission(this,
            Manifest.permission.CAMERA); 

   // we already asked for permisson & Permission granted, call camera intent
    if (permissionCheckStorage == PackageManager.PERMISSION_GRANTED && permissionCheckCamera == PackageManager.PERMISSION_GRANTED) {

        launchCamera();

    } //asking permission for the first time
     else if (permissionCheckStorage != PackageManager.PERMISSION_GRANTED && permissionCheckCamera != PackageManager.PERMISSION_GRANTED) {

        ActivityCompat.requestPermissions(this,
                new String[]{Manifest.permission.CAMERA, Manifest.permission.WRITE_EXTERNAL_STORAGE},
                MULTIPLE_PERMISSIONS);

    } else {
        // Permission denied, so request permission

        // if camera request is denied
        if (ActivityCompat.shouldShowRequestPermissionRationale(this,
                Manifest.permission.CAMERA)) {
            AlertDialog.Builder builder = new AlertDialog.Builder(this);
            builder.setMessage("You need to give permission to take pictures in order to work this feature.");
            builder.setNegativeButton("CANCEL", new DialogInterface.OnClickListener() {
                @Override
                public void onClick(DialogInterface dialogInterface, int i) {
                    dialogInterface.dismiss();
                }
            });
            builder.setPositiveButton("GIVE PERMISSION", new DialogInterface.OnClickListener() {
                @Override
                public void onClick(DialogInterface dialogInterface, int i) {
                    dialogInterface.dismiss();

                    // Show permission request popup
                    ActivityCompat.requestPermissions(this,
                            new String[]{Manifest.permission.CAMERA},
                            CAMERA_PERMISSION_REQUEST_CODE);
                }
            });
            builder.show();

        }   // if storage request is denied
                else if (ActivityCompat.shouldShowRequestPermissionRationale(this,
                Manifest.permission.WRITE_EXTERNAL_STORAGE)) {
            AlertDialog.Builder builder = new AlertDialog.Builder(this);
            builder.setMessage("You need to give permission to access storage in order to work this feature.");
            builder.setNegativeButton("CANCEL", new DialogInterface.OnClickListener() {
                @Override
                public void onClick(DialogInterface dialogInterface, int i) {
                    dialogInterface.dismiss();
                }
            });
            builder.setPositiveButton("GIVE PERMISSION", new DialogInterface.OnClickListener() {
                @Override
                public void onClick(DialogInterface dialogInterface, int i) {
                    dialogInterface.dismiss();

                    // Show permission request popup
                    ActivityCompat.requestPermissions(this,
                            new String[]{Manifest.permission.WRITE_EXTERNAL_STORAGE},
                            STORAGE_PERMISSION_REQUEST_CODE);
                }
            });
            builder.show();

        } 

    }
}

Résultats Des Autorisations De Vérification

 @Override
public void onRequestPermissionsResult(int requestCode, @NonNull String[] permissions, @NonNull int[] grantResults) {
    super.onRequestPermissionsResult(requestCode, permissions, grantResults);

    switch (requestCode) {
        case CAMERA_PERMISSION_REQUEST_CODE:
            if (grantResults.length > 0 && permissions[0].equals(Manifest.permission.CAMERA)) {
                // check whether camera permission granted or not.
                if (grantResults[0] == PackageManager.PERMISSION_GRANTED) {
                    launchCamera();
                }
            }
            break;
        case STORAGE_PERMISSION_REQUEST_CODE:
            if (grantResults.length > 0 && permissions[0].equals(Manifest.permission.WRITE_EXTERNAL_STORAGE)) {
                // check whether storage permission granted or not.
                if (grantResults[0] == PackageManager.PERMISSION_GRANTED) {
                    launchCamera();
                }
            }
            break;
        case MULTIPLE_PERMISSIONS:
            if (grantResults.length > 0 && permissions[0].equals(Manifest.permission.CAMERA) && permissions[1].equals(Manifest.permission.WRITE_EXTERNAL_STORAGE)) {
                // check whether All permission granted or not.
                if (grantResults[0] == PackageManager.PERMISSION_GRANTED && grantResults[1] == PackageManager.PERMISSION_GRANTED) {
                    launchCamera();

                }
            }
            break;
        default:
            break;
    }
}

vous pouvez simplement copier et coller ce code, il fonctionne très bien. changement de contexte(ce) et des autorisations selon vous.

2
répondu Adarsh Vijayan P 2018-04-20 05:20:01

j'ai implémenté avec succès le code simple pour la permission Multiple à la fois. Suivez les étapes ci-dessous 1:L'Utilitaire Make.classe java comme ci-dessous

public class Utility {
public static final int MY_PERMISSIONS_REQUEST = 123;
@TargetApi(Build.VERSION_CODES.JELLY_BEAN)
public static boolean checkPermissions(Context context, String... permissions) {
    if (android.os.Build.VERSION.SDK_INT >= Build.VERSION_CODES.M && context != null && permissions != null) {
        for (String permission : permissions) {
            if (ActivityCompat.checkSelfPermission(context, permission) != PackageManager.PERMISSION_GRANTED) {
                if (ActivityCompat.shouldShowRequestPermissionRationale((Activity) context, permission)) {
                    ActivityCompat.requestPermissions((Activity) context, new String[]{Manifest.permission.READ_EXTERNAL_STORAGE,Manifest.permission.CALL_PHONE,Manifest.permission.GET_ACCOUNTS}, MY_PERMISSIONS_REQUEST);
                } else {
                    ActivityCompat.requestPermissions((Activity) context, new String[]{Manifest.permission.READ_EXTERNAL_STORAGE,Manifest.permission.CALL_PHONE,Manifest.permission.GET_ACCOUNTS}, MY_PERMISSIONS_REQUEST);
                }
                return false;
            }
        }
    }
    return true;
}
}

2: maintenant appelez

boolean permissionCheck = Utility.checkPermissions(this, Manifest.permission.READ_EXTERNAL_STORAGE, Manifest.permission.CALL_PHONE, Manifest.permission.GET_ACCOUNTS);  

dans votre Activité onCreate (), ou selon votre logique.

3:Vérifiez maintenant l'autorisation avant d'effectuer l'opération pour la tâche particulière

if (permissionCheck) {
 performTaskOperation();//this method what you need to perform
} else {
        Toast.makeText(this, "Need permission ON.", Toast.LENGTH_SHORT).show();
       }

4: Maintenant implémenter la méthode onRequestPermissionsResult() dans votre activité comme ci-dessous

  @Override
public void onRequestPermissionsResult(int requestCode, String[] permissions, int[] grantResults) {
    switch (requestCode) {
        case Utility.MY_PERMISSIONS_REQUEST:
            if (grantResults.length > 0 && grantResults[0] == PackageManager.PERMISSION_GRANTED) {
                if (userChoosenTask.equals("STORAGE"))
                    performTaskOperation();//this method what you need to perform
            }
            break;
    }
}
1
répondu Ness Tyagi 2016-10-11 09:06:31

après avoir vu toutes les réponses longues et complexes. Je veux poster cette réponse.

rxpermission est largement utilisé bibliothèque maintenant pour demander la permission dans un code de ligne.

RxPermissions rxPermissions = new RxPermissions(this);
rxPermissions
.request(Manifest.permission.CAMERA,
         Manifest.permission.READ_PHONE_STATE)
.subscribe(granted -> {
    if (granted) {
       // All requested permissions are granted
    } else {
       // At least one permission is denied
    }
});

ajouter à votre build.gradle

allprojects {
    repositories {
        ...
        maven { url 'https://jitpack.io' }
    }
}

dependencies {
    implementation 'com.github.tbruyelle:rxpermissions:0.10.1'
    implementation 'com.jakewharton.rxbinding2:rxbinding:2.1.1'
}

N'est-ce pas facile?

1
répondu Khemraj 2018-07-10 17:25:52

Consultez ce lien pour pleinement comprendre de multiples permission, aussi complet téléchargement du code source, cliquez Ici

   private boolean checkAndRequestPermissions() {
    int permissionReadPhoneState = ContextCompat.checkSelfPermission(this, Manifest.permission.READ_PHONE_STATE);
    int permissionProcessOutGogingCalls = ContextCompat.checkSelfPermission(this, Manifest.permission.PROCESS_OUTGOING_CALLS);
    int permissionProcessReadContacts = ContextCompat.checkSelfPermission(this, Manifest.permission.READ_CONTACTS);
    int permissionProcessReadCallLog = ContextCompat.checkSelfPermission(this, Manifest.permission.READ_CALL_LOG);

    int permissionWriteStorage = ContextCompat.checkSelfPermission(this, Manifest.permission.WRITE_EXTERNAL_STORAGE);
    int permissionReadStorage = ContextCompat.checkSelfPermission(this, Manifest.permission.READ_EXTERNAL_STORAGE);

    List<String> listPermissionsNeeded = new ArrayList<>();
    if (permissionReadPhoneState != PackageManager.PERMISSION_GRANTED) {
        listPermissionsNeeded.add(Manifest.permission.READ_PHONE_STATE);
    }
    if (permissionProcessOutGogingCalls != PackageManager.PERMISSION_GRANTED) {
        listPermissionsNeeded.add(Manifest.permission.PROCESS_OUTGOING_CALLS);
    }
    if (permissionProcessReadContacts != PackageManager.PERMISSION_GRANTED) {
        listPermissionsNeeded.add(Manifest.permission.READ_CONTACTS);
    }
    if (permissionProcessReadCallLog != PackageManager.PERMISSION_GRANTED) {
        listPermissionsNeeded.add(Manifest.permission.READ_CALL_LOG);
    }
    if (permissionWriteStorage != PackageManager.PERMISSION_GRANTED) {
        listPermissionsNeeded.add(Manifest.permission.WRITE_EXTERNAL_STORAGE);
    }
    if (permissionReadStorage != PackageManager.PERMISSION_GRANTED) {
        listPermissionsNeeded.add(Manifest.permission.READ_EXTERNAL_STORAGE);
    }
    if (!listPermissionsNeeded.isEmpty()) {
        ActivityCompat.requestPermissions(this, listPermissionsNeeded.toArray(new String[listPermissionsNeeded.size()]), REQUEST_ID_MULTIPLE_PERMISSIONS);
        return false;
    }
    return true;
}

@Override
public void onRequestPermissionsResult(int requestCode, String permissions[], int[] grantResults) {
    super.onRequestPermissionsResult(requestCode, permissions, grantResults);
    if (grantResults.length == 0 || grantResults == null) {
        /*If result is null*/
    } else if (grantResults[0] == PackageManager.PERMISSION_GRANTED) {
        /*If We accept permission*/
    } else if (grantResults[0] == PackageManager.PERMISSION_DENIED) {
        /*If We Decline permission*/
    }
}
1
répondu Hitesh Tarbundiya 2018-09-15 05:13:07

j'ai trouvé ceci est dans L'exemple de permissions d'exécution de Google github.

 private static String[] PERMISSIONS_CONTACT = {Manifest.permission.READ_CONTACTS,
        Manifest.permission.WRITE_CONTACTS};
private static final int REQUEST_CONTACTS = 1;
ActivityCompat.requestPermissions(this, PERMISSIONS_CONTACT, REQUEST_CONTACTS);
0
répondu A.Sanchez.SD 2015-12-17 19:42:26

cochez la rubrique "demander plusieurs permissions à la fois" dans cet article:

choses que vous devez savoir à propos de Android M permissions

C'est très bien expliqué, et peut également toucher d'autres sujets connexes que vous n'avez pas idée.

0
répondu 2015-12-17 19:53:36

Court et doux :). ce en quoi je crois.

int PERMISSION_ALL = 1;
String[] PERMISSIONS = {Manifest.permission.CAMERA, Manifest.permission.WRITE_EXTERNAL_STORAGE}; // List of permissions required

public void askPermission()
{
    for (String permission : PERMISSIONS) {
        if (ActivityCompat.checkSelfPermission(this, permission) != PackageManager.PERMISSION_GRANTED) {
            requestPermissions(PERMISSIONS, PERMISSION_ALL);
            return;
        }
    }
}

@Override
public void onRequestPermissionsResult(int requestCode, String[] permissions,
                                       int[] grantResults) {

    switch (requestCode) {
        case 1:{
            if(grantResults.length > 0 && grantResults[0] == PackageManager.PERMISSION_GRANTED && grantResults[1] == PackageManager.PERMISSION_GRANTED){
                //Do your work.
            } else {
                Toast.makeText(this, "Until you grant the permission, we cannot proceed further", Toast.LENGTH_SHORT).show();
            }
            return;
        }
    }
0
répondu androidStud 2017-02-16 11:49:02

utilisez helper comme ceci (les noms de permissions n'ont pas d'importance).

public class MyPermission {

private static final int PERMISSION_REQUEST_ALL = 127;
private MainActivity mMainActivity;

MyPermission(MainActivity mainActivity) {
    mMainActivity = mainActivity;
}

public static boolean hasPermission(String permission, Context context) {
    if (isNewPermissionModel()) {
        return (ActivityCompat.checkSelfPermission(context, permission) == PackageManager.PERMISSION_GRANTED);
    }
    return true;
}

private static boolean hasPermissions(Context context, String... permissions) {
    if (isNewPermissionModel() && context != null && permissions != null) {
        for (String permission : permissions) {
            if (ActivityCompat.checkSelfPermission(context, permission) != PackageManager.PERMISSION_GRANTED) {
                return false;
            }
        }
    }
    return true;
}

private static boolean shouldShowRationale(Activity activity, String permission) {
    return isNewPermissionModel() && ActivityCompat.shouldShowRequestPermissionRationale(activity, permission);
}

private static boolean isNewPermissionModel() {
    return VERSION.SDK_INT > VERSION_CODES.LOLLIPOP_MR1;
}


/**
 * check all permissions
 */
void checkAll() {
    //check dangerous permissions, make request if need (Android will ask only for the ones it needs)
    String[] PERMISSIONS = {
            permission.READ_CALENDAR,           
            permission.ACCESS_COARSE_LOCATION   
    };

    if (!hasPermissions(mMainActivity, PERMISSIONS)) {
        ActivityCompat.requestPermissions(mMainActivity, PERMISSIONS, PERMISSION_REQUEST_ALL);
    }
}

void onRequestPermissionsResult(int requestCode, @NonNull String[] permissions, @NonNull int[] grantResults) {
    if (requestCode == PERMISSION_REQUEST_ALL) {
        if (grantResults.length > 0) {
            //for not granted
            for (int i = 0; i < permissions.length; i++) {

                if (permissions[i].equals(permission.READ_CALENDAR)) {
                    if (grantResults[i] != PackageManager.PERMISSION_GRANTED) {
                        smartRequestPermissions(permission.READ_CALENDAR, R.string.permission_required_dialog_read_calendar);
                    }
                } else if (permissions[i].equals(permission.ACCESS_COARSE_LOCATION)) {
                    if (grantResults[i] != PackageManager.PERMISSION_GRANTED) {
                        smartRequestPermissions(permission.ACCESS_COARSE_LOCATION, R.string.permission_required_dialog_access_coarse_location);
                    }
                }

            }
        }
    }
}

private void smartRequestPermissions(final String permissionName, int permissionRequiredDialog) {
    if (shouldShowRationale(mMainActivity, permissionName)) {// If the user turned down the permission request in the past and chose the Don't ask again option in the permission request system dialog, this method returns false.

        //Show an explanation to the user with action
        mMainActivity.mSnackProgressBarManager.show(
                new SnackProgressBar(
                        SnackProgressBar.TYPE_ACTION, mMainActivity.getString(permissionRequiredDialog)
                )
                        .setAction("OK", new OnActionClickListener() {
                            @Override
                            public void onActionClick() {
                                checkAll();
                            }
                        })
                        .setSwipeToDismiss(true).setAllowUserInput(true)
                , MainActivity.SNACKBAR_WARNING_DURATION
        );

    } // else do nothing
}

}

0
répondu Andrew Glukhoff 2017-06-23 06:19:51

Simple façon de poser plusieurs permission,

https://github.com/sachinvarma/EasyPermission

comment ajouter :

repositories {
        maven { url "https://jitpack.io" }
    }

implementation 'com.github.sachinvarma:EasyPermission:1.0.1'

Comment demander la permission:

 List<String> permission = new ArrayList<>();
 permission.add(EasyPermissionList.READ_EXTERNAL_STORAGE);
 permission.add(EasyPermissionList.ACCESS_FINE_LOCATION);

 new EasyPermissionInit(MainActivity.this, permission);

pour plus de détails - >

https://github.com/sachinvarma/EasyPermission/blob/master/app/src/main/java/com/sachinvarma/easypermissionsample/MainActivity.java

ça pourrait aider quelqu'un à l'avenir.

0
répondu Sachin Varma 2018-04-28 12:05:31

j'utilise juste un tableau pour réaliser plusieurs requêtes, j'espère qu'il aidera quelqu'un. (Kotlin)

    // got all permission
    private fun requestPermission(){
        var mIndex: Int = -1
        var requestList: Array<String> = Array(10, { "" } )

        // phone call Permission
        if (ContextCompat.checkSelfPermission(this, Manifest.permission.CALL_PHONE) != PackageManager.PERMISSION_GRANTED) {
            mIndex ++
            requestList[mIndex] = Manifest.permission.CALL_PHONE
        }
        // SMS Permission
        if (ContextCompat.checkSelfPermission(this, Manifest.permission.READ_CONTACTS) != PackageManager.PERMISSION_GRANTED) {
            mIndex ++
            requestList[mIndex] = Manifest.permission.SEND_SMS
        }

        // Access photos Permission
        if (ActivityCompat.checkSelfPermission(this, Manifest.permission.READ_EXTERNAL_STORAGE) != PackageManager.PERMISSION_GRANTED) {
            mIndex ++
            requestList[mIndex] = Manifest.permission.READ_EXTERNAL_STORAGE
        }

        // Location Permission
        if (ActivityCompat.checkSelfPermission(mContext, Manifest.permission.ACCESS_FINE_LOCATION) != PackageManager.PERMISSION_GRANTED
                && ActivityCompat.checkSelfPermission(mContext, Manifest.permission.ACCESS_COARSE_LOCATION) != PackageManager.PERMISSION_GRANTED) {
            mIndex ++
            requestList[mIndex] = Manifest.permission.ACCESS_FINE_LOCATION
        }

        if(mIndex != -1){
            ActivityCompat.requestPermissions(this, requestList, PERMISSIONS_REQUEST_ALL)
        }
    }


    // permission response
    override fun onRequestPermissionsResult(requestCode: Int,
                                            permissions: Array<String>, grantResults: IntArray) {
        when (requestCode) {
            PERMISSIONS_REQUEST_ALL -> {
                // If request is cancelled, the result arrays are empty.
                if (grantResults.isNotEmpty() && grantResults[0] == PackageManager.PERMISSION_GRANTED) {
                    // permission accept location
                    if (ContextCompat.checkSelfPermission(this,
                                    Manifest.permission.CALL_PHONE) == PackageManager.PERMISSION_GRANTED) {
                        Log.d(TAG, "Phone Call permission accept.")
                    }

                    // permission accept location
                    if (ContextCompat.checkSelfPermission(this,
                                    Manifest.permission.SEND_SMS) == PackageManager.PERMISSION_GRANTED) {
                        Log.d(TAG, "SMS permission accept.")
                    }

                    // permission accept location
                    if (ContextCompat.checkSelfPermission(this,
                                    Manifest.permission.READ_EXTERNAL_STORAGE) == PackageManager.PERMISSION_GRANTED) {
                        Log.d(TAG, "SMS permission accept.")
                    }

                    // permission accept location
                    if (ContextCompat.checkSelfPermission(this,
                                    Manifest.permission.ACCESS_FINE_LOCATION) == PackageManager.PERMISSION_GRANTED) {
                        Log.d(TAG, "Location permission accept.")
                    }

                } else {
                    Toast.makeText(mContext, "Permission Failed!", Toast.LENGTH_LONG).show()
                }
                return
            }
        }
    }
0
répondu Md Imran Choudhury 2018-07-26 10:52:30

il n'y a rien de mal à ce que les réponses demandent des permissions multiples, mais le code de résultat de permission multiple n'est pas implémenté de manière très élégante et peut causer une mauvaise vérification du résultat de permission.

if (grantResults.length > 0 && grantResults[0] == PackageManager.PERMISSION_GRANTED) est une terrible logique pour vérifier le résultat de plusieurs permissions, Je ne sais pas pourquoi Google a mis en œuvre un code si terrible.

c'est un gâchis surtout quand vous vérifiez plusieurs permissions. Disons que vous demandez CAMERA , ACCESS_FINE_LOCATION et ACCESS_NETWORK_STATE .

vous devez vérifier pour ACCESS_FINE_LOCATION mais l'utilisateur seulement accordé CAMERA à la première course et vous vérifiez pour grantResults[1] mais dans la deuxième course ACCESS_FINE_LOCATION devient la permission avec l'index 0. J'ai eu tellement de problèmes avec l'utilisateur n'accordant pas toutes les permissions à la fois et doivent écrire si inutile logique de résultat de permission.

vous devez utiliser

   int size = permissions.length;
    boolean locationPermissionGranted = false;

    for (int i = 0; i < size; i++) {
        if (permissions[i].equals(Manifest.permission.ACCESS_FINE_LOCATION)
                && grantResults[i] == PackageManager.PERMISSION_GRANTED) {
            locationPermissionGranted = true;
        }
    }

ou plus simple

   if (ContextCompat.checkSelfPermission(this, Manifest.permission.ACCESS_FINE_LOCATION)
                == PackageManager.PERMISSION_GRANTED) {
           // Do something ...
        }

dans la méthode onPermissionRequestResult .

0
répondu Thracian 2018-09-20 19:11:54