طلب الوصول إلى الموقع الجغرافي في وقت التشغيل

عندما تحتاج إحدى الميزات في تطبيقك إلى إذن الوصول إلى الموقع الجغرافي، انتظِر إلى أن يتفاعل المستخدم مع الميزة قبل تقديم طلب الحصول على الإذن. تتّبع سير العمل هذا أفضل الممارسات المتعلّقة بطلب أذونات وقت التشغيل في السياق، كما هو موضّح في الدليل الذي يشرح كيفية طلب أذونات التطبيق.

يوضّح الشكل 1 مثالاً على كيفية تنفيذ هذه العملية. يحتوي التطبيق على ميزة "مشاركة الموقع الجغرافي" التي تتطلّب الوصول إلى بيانات الموقع الجغرافي أثناء عمل التطبيق في المقدّمة. لا يطلب التطبيق إذن الوصول إلى الموقع الجغرافي إلا بعد أن ينقر المستخدم على الزر مشاركة الموقع الجغرافي.

بعد أن ينقر المستخدم على زر "مشاركة الموقع الجغرافي"، يظهر مربّع حوار أذونات تحديد الموقع الجغرافي الخاص بالنظام.
الشكل 1. ميزة مشاركة الموقع الجغرافي التي تتطلّب إذن الوصول إلى بيانات الموقع الجغرافي في المقدّمة يتم تفعيل الميزة إذا اختار المستخدم السماح عند استخدام التطبيق فقط.

يمكن للمستخدم منح إذن الوصول إلى الموقع الجغرافي التقريبي فقط

على نظام التشغيل Android 12 (المستوى 31 من واجهة برمجة التطبيقات) أو الإصدارات الأحدث، يمكن للمستخدمين أن يطلبوا من تطبيقك استرداد معلومات الموقع الجغرافي التقريبي فقط، حتى عندما يطلب تطبيقك إذن وقت التشغيل ACCESS_FINE_LOCATION.

للتعامل مع هذا السلوك المحتمل للمستخدم، لا تطلب الإذن ACCESS_FINE_LOCATION بمفرده. بدلاً من ذلك، اطلب الإذن ACCESS_FINE_LOCATION والإذن ACCESS_COARSE_LOCATION في طلب واحد أثناء وقت التشغيل. إذا حاولت طلب ACCESS_FINE_LOCATION فقط، سيتجاهل النظام الطلب في بعض إصدارات Android 12. إذا كان تطبيقك يستهدف الإصدار 12 من نظام التشغيل Android أو الإصدارات الأحدث، سيسجّل النظام رسالة الخطأ التالية في Logcat:

ACCESS_FINE_LOCATION must be requested with ACCESS_COARSE_LOCATION.

عندما يطلب تطبيقك الإذن بالوصول إلى كل من ACCESS_FINE_LOCATION وACCESS_COARSE_LOCATION، يتضمّن مربّع حوار أذونات النظام الخيارات التالية للمستخدم:

  • دقيق: يتيح لتطبيقك الحصول على معلومات دقيقة عن الموقع الجغرافي.
  • الموقع الجغرافي التقريبي: يتيح لتطبيقك الحصول على معلومات الموقع الجغرافي التقريبي فقط.

يوضّح الشكل 3 أنّ مربّع الحوار يتضمّن إشارة مرئية لكلا الخيارَين، وذلك لمساعدة المستخدم في الاختيار. بعد أن يحدّد المستخدم مستوى دقة الموقع الجغرافي، ينقر على أحد الأزرار الثلاثة لاختيار مدة منح الإذن.

في نظام التشغيل Android 12 والإصدارات الأحدث، يمكن للمستخدمين الانتقال إلى إعدادات النظام لضبط دقة الموقع الجغرافي المفضّلة لأي تطبيق، بغض النظر عن إصدار حزمة SDK المستهدَف لهذا التطبيق. وينطبق ذلك حتى إذا تم تثبيت تطبيقك على جهاز يعمل بالإصدار 11 من نظام التشغيل Android أو إصدار أقدم، ثم قام المستخدم بترقية الجهاز إلى الإصدار 12 من نظام التشغيل Android أو إصدار أحدث.

يشير مربع الحوار إلى الموقع الجغرافي التقريبي فقط
         ويتضمّن 3 أزرار، أحدهما فوق الآخر
الشكل 2. مربّع حوار أذونات النظام الذي يظهر عندما يطلب تطبيقك ACCESS_COARSE_LOCATION فقط
يحتوي مربّع الحوار على مجموعتَين من الخيارات، إحداهما فوق الأخرى
الشكل 3. مربّع حوار أذونات النظام الذي يظهر عندما يطلب تطبيقك كلاً من ACCESS_FINE_LOCATION وACCESS_COARSE_LOCATION في طلب تشغيل واحد

تؤثّر خيارات المستخدم في منح الأذونات

يوضّح الجدول التالي الأذونات التي يمنحها النظام لتطبيقك، استنادًا إلى الخيارات التي يحدّدها المستخدم في مربّع حوار أذونات التشغيل:

دقيق تقريبي
أثناء استخدام التطبيق ACCESS_FINE_LOCATION و
ACCESS_COARSE_LOCATION
ACCESS_COARSE_LOCATION
هذه المرّة فقط ACCESS_FINE_LOCATION و
ACCESS_COARSE_LOCATION
ACCESS_COARSE_LOCATION
رفض لم يتم منح أذونات تحديد الموقع الجغرافي لم يتم منح أذونات تحديد الموقع الجغرافي

لمعرفة الأذونات التي منحها النظام لتطبيقك، تحقَّق من القيمة المعروضة عند طلب الأذونات. يمكنك استخدام مكتبات Jetpack في الرمز البرمجي المشابه لما يلي، أو يمكنك استخدام مكتبات النظام الأساسي حيث يمكنك إدارة رمز طلب الإذن بنفسك.

Kotlin

@RequiresApi(Build.VERSION_CODES.N)
fun requestPermissions() {
    val locationPermissionRequest = registerForActivityResult(
        ActivityResultContracts.RequestMultiplePermissions()
    ) { permissions ->
        when {
            permissions.getOrDefault(Manifest.permission.ACCESS_FINE_LOCATION, false) -> {
                // Precise location access granted.
            }
            permissions.getOrDefault(Manifest.permission.ACCESS_COARSE_LOCATION, false) -> {
                // Only approximate location access granted.
            }
            else -> {
                // No location access granted.
            }
        }
    }

    // Before you perform the actual permission request, check whether your app
    // already has the permissions, and whether your app needs to show a permission
    // rationale dialog. For more details, see Request permissions:
    // https://developer.android.com/training/permissions/requesting#request-permission
    locationPermissionRequest.launch(
        arrayOf(
            Manifest.permission.ACCESS_FINE_LOCATION,
            Manifest.permission.ACCESS_COARSE_LOCATION
        )
    )
}

Java

private void requestPermissions() {

    ActivityResultLauncher<String[]> locationPermissionRequest =
            registerForActivityResult(new ActivityResultContracts
                            .RequestMultiplePermissions(), result -> {

                Boolean fineLocationGranted = null;
                Boolean coarseLocationGranted = null;

                if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.N) {
                    fineLocationGranted = result.getOrDefault(
                            Manifest.permission.ACCESS_FINE_LOCATION, false);
                    coarseLocationGranted = result.getOrDefault(
                            Manifest.permission.ACCESS_COARSE_LOCATION,false);
                }

                if (fineLocationGranted != null && fineLocationGranted) {
                    // Precise location access granted.
                } else if (coarseLocationGranted != null && coarseLocationGranted) {
                    // Only approximate location access granted.
                } else {
                    // No location access granted.
                }
            }
        );

    // ...

    // Before you perform the actual permission request, check whether your app
    // already has the permissions, and whether your app needs to show a permission
    // rationale dialog. For more details, see Request permissions.
    locationPermissionRequest.launch(new String[] {
            Manifest.permission.ACCESS_FINE_LOCATION,
            Manifest.permission.ACCESS_COARSE_LOCATION
    });
}

طلب الترقية إلى الموقع الجغرافي الدقيق

يمكنك أن تطلب من المستخدم ترقية إذن الوصول إلى الموقع الجغرافي من الموقع الجغرافي التقريبي إلى الموقع الجغرافي الدقيق. قبل أن تطلب من المستخدم ترقية إذن الوصول إلى بيانات الموقع الجغرافي الدقيقة في تطبيقك، عليك مراعاة ما إذا كانت حالة استخدام تطبيقك تتطلّب هذا المستوى من الدقة. إذا كان تطبيقك يحتاج إلى إقران جهاز بأجهزة مجاورة عبر البلوتوث أو شبكة Wi-Fi، ننصحك باستخدام إقران الأجهزة المصاحبة أو أذونات البلوتوث بدلاً من طلب الإذن ACCESS_FINE_LOCATION.

لطلب ترقية إذن الوصول إلى بيانات الموقع الجغرافي من &quot;موقع جغرافي تقريبي&quot; إلى &quot;موقع جغرافي دقيق&quot;، اتّبِع الخطوات التالية:

  1. اشرح سبب احتياج تطبيقك إلى الإذن إذا لزم الأمر.
  2. يُرجى طلب الحصول على الإذنَين ACCESS_FINE_LOCATION وACCESS_COARSE_LOCATION معًا مرة أخرى. بما أنّ المستخدم قد سمح للنظام بمنح تطبيقك إذن الوصول إلى الموقع الجغرافي التقريبي، سيكون مربّع حوار النظام مختلفًا هذه المرة، كما هو موضّح في الشكل 4 والشكل 5:
يحتوي مربّع الحوار على الخيارات &quot;التغيير إلى الموقع الجغرافي الدقيق&quot; و&quot;هذه المرة فقط&quot; و&quot;رفض&quot;.
الشكل 4. سبق أن اختار المستخدم الموقع الجغرافي التقريبي وأثناء استخدام التطبيق (في مربّع الحوار من الشكل 3).
يحتوي مربّع الحوار على الخيارَين &quot;هذه المرّة فقط&quot; و&quot;رفض&quot;.
الشكل 5. سبق أن اختار المستخدم الموقع الجغرافي التقريبي وهذه المرة فقط (في مربّع الحوار من الشكل 3).

طلب إذن الوصول إلى بيانات الموقع الجغرافي في المقدّمة فقط في البداية

حتى إذا كانت عدة ميزات في تطبيقك تتطلّب الوصول إلى بيانات الموقع الجغرافي، من المحتمل أن تتطلّب بعضها فقط الوصول إلى بيانات الموقع الجغرافي في الخلفية. لذلك، ننصح تطبيقك بإجراء طلبات متزايدة للحصول على أذونات الموقع الجغرافي، أي طلب إذن الوصول إلى بيانات الموقع الجغرافي في المقدّمة أولاً ثم طلب إذن الوصول إلى بيانات الموقع الجغرافي في الخلفية. من خلال تنفيذ الطلبات المتزايدة، يمكنك منح المستخدمين المزيد من التحكّم والشفافية لأنّهم سيتمكّنون من فهم الميزات التي تحتاج إلى إذن تحديد الموقع الجغرافي في الخلفية بشكل أفضل.

يعرض الشكل 6 مثالاً على تطبيق مصمّم للتعامل مع الطلبات المتزايدة. تتطلّب ميزتا "عرض الموقع الجغرافي الحالي" و "اقتراح أماكن قريبة" إذن الوصول إلى الموقع الجغرافي في المقدّمة. ومع ذلك، لا تتطلّب سوى ميزة "اقتراح أماكن قريبة" إذن الوصول إلى بيانات الموقع الجغرافي في الخلفية.

يتم وضع الزر الذي يتيح الوصول إلى بيانات الموقع الجغرافي في المقدّمة على بُعد نصف طول الشاشة من الزر الذي يتيح الوصول إلى بيانات الموقع الجغرافي في الخلفية.
الشكل 6. تتطلّب كلتا الميزتين إذن الوصول إلى بيانات الموقع الجغرافي، ولكن ميزة "اقتراح ميزات قريبة" فقط تتطلّب إذن الوصول إلى بيانات الموقع الجغرافي في الخلفية.

في ما يلي عملية تنفيذ الطلبات المتزايدة:

  1. في البداية، يجب أن يوجّه تطبيقك المستخدمين إلى الميزات التي تتطلّب إذن الوصول إلى بيانات الموقع الجغرافي أثناء استخدام التطبيق، مثل ميزة "مشاركة الموقع الجغرافي" في الشكل 1 أو ميزة "عرض الموقع الجغرافي الحالي" في الشكل 2.

    ننصحك بإيقاف إمكانية وصول المستخدمين إلى الميزات التي تتطلّب إذن الوصول إلى بيانات الموقع الجغرافي في الخلفية إلى أن يحصل تطبيقك على إذن الوصول إلى بيانات الموقع الجغرافي في المقدّمة.

  2. في وقت لاحق، عندما يستكشف المستخدم الميزات التي تتطلّب إذن الوصول إلى الموقع الجغرافي في الخلفية، يمكنك طلب إذن الوصول إلى الموقع الجغرافي في الخلفية.

مراجع إضافية

لمزيد من المعلومات حول أذونات تحديد الموقع الجغرافي في Android، يمكنك الاطّلاع على المواد التالية:

الدروس التطبيقية حول الترميز

الفيديوهات

نماذج

  • تطبيق نموذجي لتوضيح كيفية استخدام أذونات تحديد الموقع الجغرافي