النوايا الشائعة

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

عند استدعاء startActivity() أو startActivityForResult() وتمريره إلى هدف ضمني، يحيل النظام الغرض إلى تطبيق يمكنه معالجة الغرض ويبدأ في تشغيل Activity المقابل له. إذا كان هناك أكثر من تطبيق واحد يمكنه تنفيذ intent، يعرض النظام للمستخدم مربع حوار لاختيار التطبيق الذي تريد استخدامه.

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

تنبيه: إذا لم يكن هناك تطبيقات على الجهاز يمكن أن تتلقّى هدفًا ضمنيًا، يتعطّل التطبيق عند طلب الرقم startActivity(). للتحقّق أولاً من توفُّر تطبيق لتلقّي intent، اطلب رقم resolveActivity() في عنصر Intent. إذا لم تكن النتيجة خالية، يعني هذا أنّ هناك تطبيقًا واحدًا على الأقل يمكنه تنفيذ الغرض، ويمكنك طلب الرقم startActivity() بأمان. وإذا كانت النتيجة خالية، لا تستخدم intent، وإن أمكن، أوقِف الميزة التي تستدعي الغرض.

إذا لم تكن تعرف كيفية إنشاء فلاتر الأهداف أو فلاتر الأهداف، اقرأ أولاً فلاتر الأهداف وفلاتر الأهداف.

لمعرفة كيفية تنشيط الأهداف المُدرجة في هذه الصفحة من مضيف التطوير، راجِع قسم التحقق من الأهداف باستخدام Android Debug Bridge.

إجراءات Google Voice

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

منبّه

في ما يلي الإجراءات الشائعة لتطبيقات المنبّه، بما في ذلك المعلومات التي تحتاج إليها لإنشاء فلتر أهداف للإعلان عن قدرة تطبيقك على تنفيذ كل إجراء.

إنشاء منبّه

إجراءات Google Voice

  • "تعيير منبّه على الساعة 7 صباحًا"

لإنشاء منبّه جديد، استخدِم الإجراء ACTION_SET_ALARM وحدِّد تفاصيل المنبّه، مثل الوقت والرسالة، وذلك باستخدام العناصر الإضافية التالية.

ملاحظة: لا تتوفر سوى الساعة والدقائق والرسائل الإضافية في Android 2.3 (المستوى 9 من واجهة برمجة التطبيقات) والإصدارات الأقدم. تتوفر الميزات الإضافية الأخرى في إصدارات أعلى من المنصة.

الإجراء
ACTION_SET_ALARM
معرّف الموارد المنتظم (URI) للبيانات
ما مِن قيمة محدّدة
نوع MIME
بدون
الإضافات
EXTRA_HOUR
ساعة المنبّه.
EXTRA_MINUTES
دقائق المنبه
EXTRA_MESSAGE
رسالة مخصّصة لتحديد المنبّه.
EXTRA_DAYS
ArrayList بما في ذلك كل يوم أسبوع يتكرر فيه هذا المنبّه. يجب تعريف كل يوم باستخدام عدد صحيح من الفئة Calendar، مثل MONDAY.

للمنبّه الذي يُستخدَم لمرة واحدة، لا تُحدِّد الرقم الإضافي.

EXTRA_RINGTONE
معرّف موارد منتظم (URI) content: يحدّد نغمة رنين لاستخدامها مع المنبّه، أو VALUE_RINGTONE_SILENT لعدم وجود نغمة رنين.

لاستخدام نغمة الرنين الافتراضية، لا تحدِّد هذه القيمة الإضافية.

EXTRA_VIBRATE
قيمة منطقية تحدد ما إذا كان سيتم اهتزاز هذا المنبه.
EXTRA_SKIP_UI
قيمة منطقية تحدد ما إذا كان على التطبيق المستجيب أن يتخطى واجهة المستخدم عند ضبط المنبّه. في حال ضبط السياسة على "صحيح"، يجب أن يتجاوز التطبيق أي واجهة مستخدم للتأكيد ويضبط المنبّه المحدّد.

مثال على الغرض:

Kotlin

fun createAlarm(message: String, hour: Int, minutes: Int) {
    val intent = Intent(AlarmClock.ACTION_SET_ALARM).apply {
        putExtra(AlarmClock.EXTRA_MESSAGE, message)
        putExtra(AlarmClock.EXTRA_HOUR, hour)
        putExtra(AlarmClock.EXTRA_MINUTES, minutes)
    }
    if (intent.resolveActivity(packageManager) != null) {
        startActivity(intent)
    }
}

Java

public void createAlarm(String message, int hour, int minutes) {
    Intent intent = new Intent(AlarmClock.ACTION_SET_ALARM)
            .putExtra(AlarmClock.EXTRA_MESSAGE, message)
            .putExtra(AlarmClock.EXTRA_HOUR, hour)
            .putExtra(AlarmClock.EXTRA_MINUTES, minutes);
    if (intent.resolveActivity(getPackageManager()) != null) {
        startActivity(intent);
    }
}
ملاحظة:

لاستدعاء intent ACTION_SET_ALARM، يجب أن يحصل تطبيقك على إذن SET_ALARM:

<uses-permission android:name="com.android.alarm.permission.SET_ALARM" />

مثال على فلتر الأهداف:

<activity ...>
    <intent-filter>
        <action android:name="android.intent.action.SET_ALARM" />
        <category android:name="android.intent.category.DEFAULT" />
    </intent-filter>
</activity>

إنشاء موقّت

إجراءات Google Voice

  • "ضبط موقّت لمدة 5 دقائق"

لإنشاء موقّت عد تنازلي، استخدِم الإجراء ACTION_SET_TIMER وحدِّد تفاصيل الموقّت، مثل المدة باستخدام المزايا الإضافية التالية.

ملاحظة: يتوفّر هذا intent في Android 4.4 (المستوى 19 من واجهة برمجة التطبيقات) والإصدارات الأحدث.

الإجراء
ACTION_SET_TIMER
معرّف الموارد المنتظم (URI) للبيانات
ما مِن قيمة محدّدة
نوع MIME
بدون
الإضافات
EXTRA_LENGTH
مدة الموقّت بالثواني.
EXTRA_MESSAGE
رسالة مخصّصة لتحديد الموقّت
EXTRA_SKIP_UI
قيمة منطقية تحدد ما إذا كان على التطبيق المستجيب أن يتخطى واجهة المستخدم عند ضبط الموقّت. في حال ضبط السياسة على "صحيح"، يجب أن يتخطّى التطبيق أيّ واجهة مستخدم للتأكيد وأن يبدأ الموقّت.

مثال على الغرض:

Kotlin

fun startTimer(message: String, seconds: Int) {
    val intent = Intent(AlarmClock.ACTION_SET_TIMER).apply {
        putExtra(AlarmClock.EXTRA_MESSAGE, message)
        putExtra(AlarmClock.EXTRA_LENGTH, seconds)
        putExtra(AlarmClock.EXTRA_SKIP_UI, true)
    }
    if (intent.resolveActivity(packageManager) != null) {
        startActivity(intent)
    }
}

Java

public void startTimer(String message, int seconds) {
    Intent intent = new Intent(AlarmClock.ACTION_SET_TIMER)
            .putExtra(AlarmClock.EXTRA_MESSAGE, message)
            .putExtra(AlarmClock.EXTRA_LENGTH, seconds)
            .putExtra(AlarmClock.EXTRA_SKIP_UI, true);
    if (intent.resolveActivity(getPackageManager()) != null) {
        startActivity(intent);
    }
}
ملاحظة:

لاستدعاء intent ACTION_SET_TIMER، يجب أن يحصل تطبيقك على إذن SET_ALARM:

<uses-permission android:name="com.android.alarm.permission.SET_ALARM" />

مثال على فلتر الأهداف:

<activity ...>
    <intent-filter>
        <action android:name="android.intent.action.SET_TIMER" />
        <category android:name="android.intent.category.DEFAULT" />
    </intent-filter>
</activity>

إظهار جميع المنبهات

لعرض قائمة المنبّهات، استخدِم الإجراء ACTION_SHOW_ALARMS.

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

ملاحظة: يتوفّر هذا intent في Android 4.4 (المستوى 19 من واجهة برمجة التطبيقات) والإصدارات الأحدث.

الإجراء
ACTION_SHOW_ALARMS
معرّف الموارد المنتظم (URI) للبيانات
ما مِن قيمة محدّدة
نوع MIME
بدون

مثال على فلتر الأهداف:

<activity ...>
    <intent-filter>
        <action android:name="android.intent.action.SHOW_ALARMS" />
        <category android:name="android.intent.category.DEFAULT" />
    </intent-filter>
</activity>

تقويم Google

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

إضافة حدث في التقويم

لإضافة حدث جديد إلى تقويم المستخدم، استخدِم الإجراء ACTION_INSERT وحدِّد معرِّف الموارد المنتظم (URI) للبيانات باستخدام Events.CONTENT_URI. ويمكنك بعد ذلك تحديد تفاصيل مختلفة عن الحدث باستخدام الميزات الإضافية التالية.

الإجراء
ACTION_INSERT
معرّف الموارد المنتظم (URI) للبيانات
Events.CONTENT_URI
نوع MIME
"vnd.android.cursor.dir/event"
الإضافات
EXTRA_EVENT_ALL_DAY
قيمة منطقية تحدد ما إذا كان هذا الحدث يستمر طوال اليوم.
EXTRA_EVENT_BEGIN_TIME
وقت بدء الحدث (بالمللي ثانية منذ تاريخ بدء الحدث)
EXTRA_EVENT_END_TIME
وقت انتهاء الحدث (بالمللي ثانية منذ تاريخ بدء الحدث)
TITLE
عنوان الحدث
DESCRIPTION
وصف الحدث.
EVENT_LOCATION
موقع الحدث.
EXTRA_EMAIL
قائمة بعناوين البريد الإلكتروني مفصولة بفواصل والتي تحدِّد المدعوين.

يمكن تحديد المزيد من تفاصيل الحدث باستخدام الثوابت المحدّدة في الفئة CalendarContract.EventsColumns.

مثال على الغرض:

Kotlin

fun addEvent(title: String, location: String, begin: Long, end: Long) {
    val intent = Intent(Intent.ACTION_INSERT).apply {
        data = Events.CONTENT_URI
        putExtra(Events.TITLE, title)
        putExtra(Events.EVENT_LOCATION, location)
        putExtra(CalendarContract.EXTRA_EVENT_BEGIN_TIME, begin)
        putExtra(CalendarContract.EXTRA_EVENT_END_TIME, end)
    }
    if (intent.resolveActivity(packageManager) != null) {
        startActivity(intent)
    }
}

Java

public void addEvent(String title, String location, long begin, long end) {
    Intent intent = new Intent(Intent.ACTION_INSERT)
            .setData(Events.CONTENT_URI)
            .putExtra(Events.TITLE, title)
            .putExtra(Events.EVENT_LOCATION, location)
            .putExtra(CalendarContract.EXTRA_EVENT_BEGIN_TIME, begin)
            .putExtra(CalendarContract.EXTRA_EVENT_END_TIME, end);
    if (intent.resolveActivity(getPackageManager()) != null) {
        startActivity(intent);
    }
}

مثال على فلتر الأهداف:

<activity ...>
    <intent-filter>
        <action android:name="android.intent.action.INSERT" />
        <data android:mimeType="vnd.android.cursor.dir/event" />
        <category android:name="android.intent.category.DEFAULT" />
    </intent-filter>
</activity>

الكاميرا

في ما يلي الإجراءات الشائعة لتطبيقات الكاميرا، بما في ذلك المعلومات التي تحتاجها لإنشاء فلتر أهداف للإعلان عن قدرة تطبيقك على تنفيذ كل إجراء.

التقِط صورة أو فيديو وأعِدهما

لفتح تطبيق كاميرا وتلقّي الصورة أو الفيديو الناتجَين، استخدِم الإجراء ACTION_IMAGE_CAPTURE أو ACTION_VIDEO_CAPTURE. حدِّد أيضًا موقع معرّف الموارد المنتظم (URI) الذي تريد أن تحفظ فيه الكاميرا الصورة أو الفيديو، في علامة EXTRA_OUTPUT الإضافية.

الإجراء
ACTION_IMAGE_CAPTURE أو
ACTION_VIDEO_CAPTURE
مخطط معرّف الموارد المنتظم (URI) للبيانات
ما مِن قيمة محدّدة
نوع MIME
ما مِن قيمة محدّدة
الإضافات
EXTRA_OUTPUT
مكان معرّف الموارد المنتظم (URI) الذي يحفظ فيه تطبيق الكاميرا الصورة أو ملف الفيديو (ككائن Uri).

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

ملاحظة: عند استخدام ACTION_IMAGE_CAPTURE لالتقاط صورة، قد تعرض الكاميرا أيضًا نسخة أو صورة مصغّرة مصغّرة من الصورة في النتيجة Intent، يتم حفظها بتنسيق Bitmap في حقل إضافي باسم "data".

مثال على الغرض:

Kotlin

const val REQUEST_IMAGE_CAPTURE = 1
val locationForPhotos: Uri = ...

fun capturePhoto(targetFilename: String) {
    val intent = Intent(MediaStore.ACTION_IMAGE_CAPTURE).apply {
        putExtra(MediaStore.EXTRA_OUTPUT, Uri.withAppendedPath(locationForPhotos, targetFilename))
    }
    if (intent.resolveActivity(packageManager) != null) {
        startActivityForResult(intent, REQUEST_IMAGE_CAPTURE)
    }
}

override fun onActivityResult(requestCode: Int, resultCode: Int, data: Intent) {
    if (requestCode == REQUEST_IMAGE_CAPTURE && resultCode == Activity.RESULT_OK) {
        val thumbnail: Bitmap = data.getParcelableExtra("data")
        // Do other work with full size photo saved in locationForPhotos.
        ...
    }
}

Java

static final int REQUEST_IMAGE_CAPTURE = 1;
static final Uri locationForPhotos;

public void capturePhoto(String targetFilename) {
    Intent intent = new Intent(MediaStore.ACTION_IMAGE_CAPTURE);
    intent.putExtra(MediaStore.EXTRA_OUTPUT,
            Uri.withAppendedPath(locationForPhotos, targetFilename));
    if (intent.resolveActivity(getPackageManager()) != null) {
        startActivityForResult(intent, REQUEST_IMAGE_CAPTURE);
    }
}

@Override
protected void onActivityResult(int requestCode, int resultCode, Intent data) {
    if (requestCode == REQUEST_IMAGE_CAPTURE && resultCode == RESULT_OK) {
        Bitmap thumbnail = data.getParcelableExtra("data");
        // Do other work with full size photo saved in locationForPhotos.
        ...
    }
}

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

مثال على الغرض:

Kotlin

val REQUEST_IMAGE_CAPTURE = 1

private fun dispatchTakePictureIntent() {
    val takePictureIntent = Intent(MediaStore.ACTION_IMAGE_CAPTURE)
    try {
        startActivityForResult(takePictureIntent, REQUEST_IMAGE_CAPTURE)
    } catch (e: ActivityNotFoundException) {
        // Display error state to the user.
    }
}

Java

static final int REQUEST_IMAGE_CAPTURE = 1;

private void dispatchTakePictureIntent() {
    Intent takePictureIntent = new Intent(MediaStore.ACTION_IMAGE_CAPTURE);
    try {
        startActivityForResult(takePictureIntent, REQUEST_IMAGE_CAPTURE);
    } catch (ActivityNotFoundException e) {
        // Display error state to the user.
    }
}
</section></div>

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

مثال على فلتر الأهداف:

<activity ...>
    <intent-filter>
        <action android:name="android.media.action.IMAGE_CAPTURE" />
        <category android:name="android.intent.category.DEFAULT" />
    </intent-filter>
</activity>

عند معالجة هذا الهدف، اجعل النشاط يتحقق من وجود EXTRA_OUTPUT إضافية في Intent الواردة، ثم احفظ الصورة أو الفيديو الذي تم التقاطه في الموقع الجغرافي الذي تم تحديده من خلال تلك المساحة الإضافية واتّصِل بـ setResult() مع إضافة Intent يتضمّن صورة مصغّرة مضغوطة في شكل إضافي باسم "data".

تشغيل تطبيق الكاميرا في وضع الصور الثابتة

إجراءات Google Voice

  • "أريد التقاط صورة"

لفتح تطبيق كاميرا في وضع الصور الثابتة، استخدِم إجراء INTENT_ACTION_STILL_IMAGE_CAMERA.

الإجراء
INTENT_ACTION_STILL_IMAGE_CAMERA
مخطط معرّف الموارد المنتظم (URI) للبيانات
ما مِن قيمة محدّدة
نوع MIME
ما مِن قيمة محدّدة
الإضافات
لا شيء

مثال على الغرض:

Kotlin

private fun dispatchTakePictureIntent() {
    val takePictureIntent = Intent(MediaStore.ACTION_IMAGE_CAPTURE)
    try {
        startActivityForResult(takePictureIntent, REQUEST_IMAGE_CAPTURE)
    } catch (e: ActivityNotFoundException) {
        // Display error state to the user.
    }
}

Java

public void capturePhoto(String targetFilename) {
    Intent intent = new Intent(MediaStore.ACTION_IMAGE_CAPTURE);
    intent.putExtra(MediaStore.EXTRA_OUTPUT,
            Uri.withAppendedPath(locationForPhotos, targetFilename));
    if (intent.resolveActivity(getPackageManager()) != null) {
        startActivityForResult(intent, REQUEST_IMAGE_CAPTURE);
    }
}

مثال على فلتر الأهداف:

<activity ...>
    <intent-filter>
        <action android:name="android.media.action.STILL_IMAGE_CAMERA" />
        <category android:name="android.intent.category.DEFAULT" />
    </intent-filter>
</activity>

تشغيل تطبيق الكاميرا في وضع الفيديو

إجراءات Google Voice

  • "تسجيل فيديو"

لفتح تطبيق كاميرا في وضع الفيديو، استخدِم إجراء INTENT_ACTION_VIDEO_CAMERA.

الإجراء
INTENT_ACTION_VIDEO_CAMERA
مخطط معرّف الموارد المنتظم (URI) للبيانات
ما مِن قيمة محدّدة
نوع MIME
ما مِن قيمة محدّدة
الإضافات
لا شيء

مثال على الغرض:

Kotlin

fun capturePhoto() {
    val intent = Intent(MediaStore.INTENT_ACTION_VIDEO_CAMERA)
    if (intent.resolveActivity(packageManager) != null) {
        startActivityForResult(intent, REQUEST_IMAGE_CAPTURE)
    }
}

Java

public void capturePhoto() {
    Intent intent = new Intent(MediaStore.INTENT_ACTION_VIDEO_CAMERA);
    if (intent.resolveActivity(getPackageManager()) != null) {
        startActivityForResult(intent, REQUEST_IMAGE_CAPTURE);
    }
}

مثال على فلتر الأهداف:

<activity ...>
    <intent-filter>
        <action android:name="android.media.action.VIDEO_CAMERA" />
        <category android:name="android.intent.category.DEFAULT" />
    </intent-filter>
</activity>

تطبيق جهات الاتصال/الأشخاص

في ما يلي الإجراءات الشائعة لتطبيقات إدارة جهات الاتصال، بما في ذلك المعلومات التي تحتاجها لإنشاء فلتر أهداف للإعلان عن قدرة تطبيقك على تنفيذ كل إجراء.

اختيار جهة الاتصال

لكي يختار المستخدم جهة اتصال ويمنح تطبيقك إمكانية الوصول إلى جميع معلومات الاتصال، يجب استخدام الإجراء ACTION_PICK وتحديد نوع MIME Contacts.CONTENT_TYPE.

تشتمل النتيجة Intent التي تم إرسالها إلى معاودة الاتصال onActivityResult() على معرّف الموارد المنتظم (URI) content: الذي يشير إلى جهة الاتصال المحددة. يمنح الردّ تطبيقك أذونات مؤقتة لقراءة جهة الاتصال هذه باستخدام واجهة برمجة تطبيقات مقدِّم خدمات الاتصال، حتى إذا كان تطبيقك لا يتضمّن إذن READ_CONTACTS.

ملاحظة: إذا كنت تريد الوصول إلى معلومات اتصال محدّدة فقط، مثل رقم هاتف أو عنوان بريد إلكتروني، يمكنك بدلاً من ذلك الاطّلاع على القسم التالي حول كيفية اختيار بيانات اتصال محدّدة.

الإجراء
ACTION_PICK
مخطط معرّف الموارد المنتظم (URI) للبيانات
ما مِن قيمة محدّدة
نوع MIME
Contacts.CONTENT_TYPE

مثال على الغرض:

Kotlin

const val REQUEST_SELECT_CONTACT = 1

fun selectContact() {
    val intent = Intent(Intent.ACTION_PICK).apply {
        type = ContactsContract.Contacts.CONTENT_TYPE
    }
    if (intent.resolveActivity(packageManager) != null) {
        startActivityForResult(intent, REQUEST_SELECT_CONTACT)
    }
}

override fun onActivityResult(requestCode: Int, resultCode: Int, data: Intent) {
    if (requestCode == REQUEST_SELECT_CONTACT && resultCode == RESULT_OK) {
        val contactUri: Uri = data.data
        // Do something with the selected contact at contactUri.
        //...
    }
}

Java

static final int REQUEST_SELECT_CONTACT = 1;

public void selectContact() {
    Intent intent = new Intent(Intent.ACTION_PICK);
    intent.setType(ContactsContract.Contacts.CONTENT_TYPE);
    if (intent.resolveActivity(getPackageManager()) != null) {
        startActivityForResult(intent, REQUEST_SELECT_CONTACT);
    }
}

@Override
protected void onActivityResult(int requestCode, int resultCode, Intent data) {
    if (requestCode == REQUEST_SELECT_CONTACT && resultCode == RESULT_OK) {
        Uri contactUri = data.getData();
        // Do something with the selected contact at contactUri.
        ...
    }
}

لمزيد من المعلومات حول كيفية استرداد تفاصيل الاتصال بعد الحصول على معرّف الموارد المنتظم (URI) لجهة الاتصال، اقرأ استرداد تفاصيل جهة اتصال.

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

اختيار بيانات اتصال معيّنة

ليختار المستخدم معلومة معيّنة من جهة اتصال، مثل رقم هاتف أو عنوان بريد إلكتروني أو نوع بيانات آخر، استخدِم الإجراء ACTION_PICK وحدِّد نوع MIME لأحد أنواع المحتوى التالية، مثل CommonDataKinds.Phone.CONTENT_TYPE للحصول على رقم هاتف جهة الاتصال.

ملاحظة: في كثير من الحالات، يحتاج تطبيقك إلى READ_CONTACTS الإذن بعرض معلومات محدّدة عن جهة اتصال معيّنة.

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

تشتمل النتيجة Intent التي تم إرسالها إلى معاودة الاتصال onActivityResult() على معرّف الموارد المنتظم (URI) content: الذي يشير إلى بيانات جهة الاتصال المحددة. يمنح الردّ تطبيقك أذونات مؤقتة لقراءة بيانات جهة الاتصال هذه حتى إذا لم يتضمّن تطبيقك إذن READ_CONTACTS.

الإجراء
ACTION_PICK
مخطط معرّف الموارد المنتظم (URI) للبيانات
ما مِن قيمة محدّدة
نوع MIME
CommonDataKinds.Phone.CONTENT_TYPE
اختَر من جهات الاتصال التي لها رقم هاتف.
CommonDataKinds.Email.CONTENT_TYPE
اختَر من جهات الاتصال التي لها عنوان بريد إلكتروني.
CommonDataKinds.StructuredPostal.CONTENT_TYPE
اختَر من جهات الاتصال التي لها عنوان بريدي.

أو إحدى قيم CONTENT_TYPE الأخرى العديدة ضمن ContactsContract.

مثال على الغرض:

Kotlin

const val REQUEST_SELECT_PHONE_NUMBER = 1

fun selectContact() {
    // Start an activity for the user to pick a phone number from contacts.
    val intent = Intent(Intent.ACTION_PICK).apply {
        type = CommonDataKinds.Phone.CONTENT_TYPE
    }
    if (intent.resolveActivity(packageManager) != null) {
        startActivityForResult(intent, REQUEST_SELECT_PHONE_NUMBER)
    }
}

override fun onActivityResult(requestCode: Int, resultCode: Int, data: Intent) {
    if (requestCode == REQUEST_SELECT_PHONE_NUMBER && resultCode == Activity.RESULT_OK) {
        // Get the URI and query the content provider for the phone number.
        val contactUri: Uri = data.data
        val projection: Array<String> = arrayOf(CommonDataKinds.Phone.NUMBER)
        contentResolver.query(contactUri, projection, null, null, null).use { cursor ->
            // If the cursor returned is valid, get the phone number.
            if (cursor.moveToFirst()) {
                val numberIndex = cursor.getColumnIndex(CommonDataKinds.Phone.NUMBER)
                val number = cursor.getString(numberIndex)
                // Do something with the phone number.
                ...
            }
        }
    }
}

Java

static final int REQUEST_SELECT_PHONE_NUMBER = 1;

public void selectContact() {
    // Start an activity for the user to pick a phone number from contacts.
    Intent intent = new Intent(Intent.ACTION_PICK);
    intent.setType(CommonDataKinds.Phone.CONTENT_TYPE);
    if (intent.resolveActivity(getPackageManager()) != null) {
        startActivityForResult(intent, REQUEST_SELECT_PHONE_NUMBER);
    }
}

@Override
protected void onActivityResult(int requestCode, int resultCode, Intent data) {
    if (requestCode == REQUEST_SELECT_PHONE_NUMBER && resultCode == RESULT_OK) {
        // Get the URI and query the content provider for the phone number.
        Uri contactUri = data.getData();
        String[] projection = new String[]{CommonDataKinds.Phone.NUMBER};
        Cursor cursor = getContentResolver().query(contactUri, projection,
                null, null, null);
        // If the cursor returned is valid, get the phone number.
        if (cursor != null && cursor.moveToFirst()) {
            int numberIndex = cursor.getColumnIndex(CommonDataKinds.Phone.NUMBER);
            String number = cursor.getString(numberIndex);
            // Do something with the phone number.
            //...
        }
    }
}

عرض جهة اتصال

لعرض تفاصيل جهة اتصال معروفة، استخدِم الإجراء ACTION_VIEW وحدِّد جهة الاتصال التي تتضمّن معرّف موارد منتظم (URI) content: كبيانات intent.

هناك طريقتان أساسيتان لاسترداد عنوان URI لجهة الاتصال في البداية:

  • استخدِم معرّف الموارد المنتظم (URI) لجهة الاتصال الذي يعرضه الإجراء ACTION_PICK المعروض في القسم السابق. لا تتطلب هذه الطريقة أي أذونات للتطبيقات.
  • يمكنك الوصول إلى قائمة جميع جهات الاتصال مباشرةً، كما هو موضَّح في استرداد قائمة جهات الاتصال. تتطلّب هذه الطريقة الحصول على إذن READ_CONTACTS.
الإجراء
ACTION_VIEW
مخطط معرّف الموارد المنتظم (URI) للبيانات
content:<URI>
نوع MIME
بدون. يتم استنتاج النوع من معرّف الموارد المنتظم (URI) لجهة الاتصال.

مثال على الغرض:

Kotlin

fun viewContact(contactUri: Uri) {
    val intent = Intent(Intent.ACTION_VIEW, contactUri)
    if (intent.resolveActivity(packageManager) != null) {
        startActivity(intent)
    }
}

Java

public void viewContact(Uri contactUri) {
    Intent intent = new Intent(Intent.ACTION_VIEW, contactUri);
    if (intent.resolveActivity(getPackageManager()) != null) {
        startActivity(intent);
    }
}

تعديل جهة اتصال حالية

لتعديل جهة اتصال معروفة، استخدِم الإجراء ACTION_EDIT، وحدِّد جهة الاتصال التي تتضمّن معرف موارد منتظم (URI) لـ content: كبيانات للهدف، وأدرِج أي معلومات اتصال معروفة في العناصر الإضافية التي تحدّدها الثابت في ContactsContract.Intents.Insert.

هناك طريقتان أساسيتان لاسترداد عنوان URI لجهة الاتصال مبدئيًا:

  • استخدِم معرّف الموارد المنتظم (URI) لجهة الاتصال الذي يعرضه الإجراء ACTION_PICK المعروض في القسم السابق. لا تتطلب هذه الطريقة أي أذونات للتطبيقات.
  • يمكنك الوصول إلى قائمة جميع جهات الاتصال مباشرةً، كما هو موضَّح في استرداد قائمة جهات الاتصال. تتطلّب هذه الطريقة الحصول على إذن READ_CONTACTS.
الإجراء
ACTION_EDIT
مخطط معرّف الموارد المنتظم (URI) للبيانات
content:<URI>
نوع MIME
يتم استنتاج النوع من معرّف الموارد المنتظم (URI) لجهة الاتصال.
الإضافات
عنصر واحد أو أكثر من العناصر الإضافية المحدّدة في ContactsContract.Intents.Insert كي تتمكّن من تعبئة حقول تفاصيل الاتصال.

مثال على الغرض:

Kotlin

fun editContact(contactUri: Uri, email: String) {
    val intent = Intent(Intent.ACTION_EDIT).apply {
        data = contactUri
        putExtra(ContactsContract.Intents.Insert.EMAIL, email)
    }
    if (intent.resolveActivity(packageManager) != null) {
        startActivity(intent)
    }
}

Java

public void editContact(Uri contactUri, String email) {
    Intent intent = new Intent(Intent.ACTION_EDIT);
    intent.setData(contactUri);
    intent.putExtra(Intents.Insert.EMAIL, email);
    if (intent.resolveActivity(getPackageManager()) != null) {
        startActivity(intent);
    }
}

لمزيد من المعلومات حول كيفية تعديل جهة اتصال، اقرأ تعديل جهات الاتصال باستخدام الأهداف.

إدراج جهة اتصال

لإدراج جهة اتصال جديدة، استخدِم الإجراء ACTION_INSERT، وحدِّد Contacts.CONTENT_TYPE كنوع MIME وأدرِج أي معلومات اتصال معروفة في الإضافات التي تحدّدها الثوابت في ContactsContract.Intents.Insert.

الإجراء
ACTION_INSERT
مخطط معرّف الموارد المنتظم (URI) للبيانات
ما مِن قيمة محدّدة
نوع MIME
Contacts.CONTENT_TYPE
الإضافات
تم تحديد عنصر واحد أو أكثر من العناصر الإضافية في ContactsContract.Intents.Insert.

مثال على الغرض:

Kotlin

fun insertContact(name: String, email: String) {
    val intent = Intent(Intent.ACTION_INSERT).apply {
        type = ContactsContract.Contacts.CONTENT_TYPE
        putExtra(ContactsContract.Intents.Insert.NAME, name)
        putExtra(ContactsContract.Intents.Insert.EMAIL, email)
    }
    if (intent.resolveActivity(packageManager) != null) {
        startActivity(intent)
    }
}

Java

public void insertContact(String name, String email) {
    Intent intent = new Intent(Intent.ACTION_INSERT);
    intent.setType(Contacts.CONTENT_TYPE);
    intent.putExtra(Intents.Insert.NAME, name);
    intent.putExtra(Intents.Insert.EMAIL, email);
    if (intent.resolveActivity(getPackageManager()) != null) {
        startActivity(intent);
    }
}

للمزيد من المعلومات عن كيفية إدراج جهة اتصال، يُرجى الاطّلاع على المقالة تعديل جهات الاتصال باستخدام عناصر intent.

عنوان البريد الإلكتروني

يعد إنشاء رسالة إلكترونية بمرفقات اختيارية إجراءً شائعًا لتطبيقات البريد الإلكتروني. يمكنك إنشاء فلتر أهداف للإعلان عن قدرة تطبيقك على تنفيذ هذا الإجراء باستخدام المعلومات الواردة في القسم التالي.

إنشاء رسالة إلكترونية تحتوي على مرفقات اختيارية

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

الإجراء
ACTION_SENDTO (للمرفقات) أو
ACTION_SEND (لمرفق واحد) أو
ACTION_SEND_MULTIPLE (لمرفقات متعددة)
مخطط معرّف الموارد المنتظم (URI) للبيانات
ما مِن قيمة محدّدة
نوع MIME
"text/plain"
"*/*"
الإضافات
Intent.EXTRA_EMAIL
مصفوفة سلسلة لجميع عناوين البريد الإلكتروني لمستلمي "إلى".
Intent.EXTRA_CC
مصفوفة سلسلة لجميع عناوين البريد الإلكتروني للمستلِمين في الحقل "نسخة إلى".
Intent.EXTRA_BCC
مصفوفة سلسلة لجميع عناوين البريد الإلكتروني للمستلمين "نسخة مخفية الوجهة"
Intent.EXTRA_SUBJECT
سلسلة تحتوي على موضوع الرسالة الإلكترونية
Intent.EXTRA_TEXT
سلسلة تحتوي على نص الرسالة الإلكترونية
Intent.EXTRA_STREAM
Uri يشير إلى المرفق. في حال استخدام الإجراء ACTION_SEND_MULTIPLE، سيتم بدلاً من ذلك عنصر ArrayList يحتوي على عناصر Uri متعددة.

مثال على الغرض:

Kotlin

fun composeEmail(addresses: Array<String>, subject: String, attachment: Uri) {
    val intent = Intent(Intent.ACTION_SEND).apply {
        type = "*/*"
        putExtra(Intent.EXTRA_EMAIL, addresses)
        putExtra(Intent.EXTRA_SUBJECT, subject)
        putExtra(Intent.EXTRA_STREAM, attachment)
    }
    if (intent.resolveActivity(packageManager) != null) {
        startActivity(intent)
    }
}

Java

public void composeEmail(String[] addresses, String subject, Uri attachment) {
    Intent intent = new Intent(Intent.ACTION_SEND);
    intent.setType("*/*");
    intent.putExtra(Intent.EXTRA_EMAIL, addresses);
    intent.putExtra(Intent.EXTRA_SUBJECT, subject);
    intent.putExtra(Intent.EXTRA_STREAM, attachment);
    if (intent.resolveActivity(getPackageManager()) != null) {
        startActivity(intent);
    }
}

إذا أردت التأكّد من أنّه سيتمّ تنفيذ هدفك من خلال تطبيق بريد إلكتروني فقط، وليس من خلال تطبيق رسائل نصية أو تطبيقات اجتماعية، استخدِم الإجراء ACTION_SENDTO وأدرِج مخطط بيانات "mailto:" كما هو موضّح في المثال التالي:

Kotlin

fun composeEmail(addresses: Array<String>, subject: String) {
    val intent = Intent(Intent.ACTION_SENDTO).apply {
        data = Uri.parse("mailto:") // Only email apps handle this.
        putExtra(Intent.EXTRA_EMAIL, addresses)
        putExtra(Intent.EXTRA_SUBJECT, subject)
    }
    if (intent.resolveActivity(packageManager) != null) {
        startActivity(intent)
    }
}

Java

public void composeEmail(String[] addresses, String subject) {
    Intent intent = new Intent(Intent.ACTION_SENDTO);
    intent.setData(Uri.parse("mailto:")); // Only email apps handle this.
    intent.putExtra(Intent.EXTRA_EMAIL, addresses);
    intent.putExtra(Intent.EXTRA_SUBJECT, subject);
    if (intent.resolveActivity(getPackageManager()) != null) {
        startActivity(intent);
    }
}

مثال على فلتر الأهداف:

<activity ...>
    <intent-filter>
        <action android:name="android.intent.action.SEND" />
        <data android:type="*/*" />
        <category android:name="android.intent.category.DEFAULT" />
    </intent-filter>
    <intent-filter>
        <action android:name="android.intent.action.SENDTO" />
        <data android:scheme="mailto" />
        <category android:name="android.intent.category.DEFAULT" />
    </intent-filter>
</activity>

تخزين الملفات

في ما يلي الإجراءات الشائعة لتطبيقات تخزين الملفات، بما في ذلك المعلومات التي تحتاجها لإنشاء فلتر أهداف للإعلان عن قدرة تطبيقك على تنفيذ كل إجراء.

استرداد نوع معيّن من الملفات

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

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

يتضمن الغرض من النتيجة المقدم إلى طريقة onActivityResult() بيانات تحتوي على عنوان URI يشير إلى الملف. يمكن أن يكون معرّف الموارد المنتظم (URI) أي عنصر، مثل معرّف الموارد المنتظم (URI) http: أو معرّف الموارد المنتظم (URI) file: أو معرّف الموارد المنتظم (URI) content:. أما إذا أردت حصر الملفات القابلة للاختيار على الملفات التي يمكن الوصول إليها من موفّر محتوى فقط (معرّف الموارد المنتظم (URI) لـ content:) والمتوفّرة كمصدر بيانات للملفات باستخدام openFileDescriptor()، فعليك إضافة الفئة CATEGORY_OPENABLE إلى هدفك.

في نظام التشغيل Android 4.3 (المستوى 18 من واجهة برمجة التطبيقات) والإصدارات الأحدث، يمكنك أيضًا السماح للمستخدم باختيار ملفات متعدّدة من خلال إضافة EXTRA_ALLOW_MULTIPLE إلى الغرض، وضبطه على true. يمكنك بعد ذلك الوصول إلى كل ملف من الملفات المحددة في كائن ClipData تم عرضه من خلال getClipData().

الإجراء
ACTION_GET_CONTENT
مخطط معرّف الموارد المنتظم (URI) للبيانات
ما مِن قيمة محدّدة
نوع MIME
نوع MIME المتوافق مع نوع الملف الذي يحتاج المستخدم إلى اختياره.
الإضافات
EXTRA_ALLOW_MULTIPLE
قيمة منطقية توضّح ما إذا كان بإمكان المستخدم اختيار أكثر من ملف واحد في المرّة الواحدة.
EXTRA_LOCAL_ONLY
قيمة منطقية توضّح ما إذا كان يجب أن يكون الملف المعروض متاحًا من الجهاز مباشرةً، بدلاً من طلب تنزيله من خدمة عن بُعد.
الفئة (اختيارية)
CATEGORY_OPENABLE
لعرض الملفات "القابلة للفتح" فقط التي يمكن تمثيلها كتدفق ملفات باستخدام openFileDescriptor().

مثال على الرغبة في الحصول على صورة:

Kotlin

const val REQUEST_IMAGE_GET = 1

fun selectImage() {
    val intent = Intent(Intent.ACTION_GET_CONTENT).apply {
        type = "image/*"
    }
    if (intent.resolveActivity(packageManager) != null) {
        startActivityForResult(intent, REQUEST_IMAGE_GET)
    }
}

override fun onActivityResult(requestCode: Int, resultCode: Int, data: Intent) {
    if (requestCode == REQUEST_IMAGE_GET && resultCode == Activity.RESULT_OK) {
        val thumbnail: Bitmap = data.getParcelableExtra("data")
        val fullPhotoUri: Uri = data.data
        // Do work with photo saved at fullPhotoUri.
        ...
    }
}

Java

static final int REQUEST_IMAGE_GET = 1;

public void selectImage() {
    Intent intent = new Intent(Intent.ACTION_GET_CONTENT);
    intent.setType("image/*");
    if (intent.resolveActivity(getPackageManager()) != null) {
        startActivityForResult(intent, REQUEST_IMAGE_GET);
    }
}

@Override
protected void onActivityResult(int requestCode, int resultCode, Intent data) {
    if (requestCode == REQUEST_IMAGE_GET && resultCode == RESULT_OK) {
        Bitmap thumbnail = data.getParcelable("data");
        Uri fullPhotoUri = data.getData();
        // Do work with photo saved at fullPhotoUri.
        ...
    }
}

مثال على فلتر الأهداف لعرض صورة:

<activity ...>
    <intent-filter>
        <action android:name="android.intent.action.GET_CONTENT" />
        <data android:type="image/*" />
        <category android:name="android.intent.category.DEFAULT" />
        <!-- The OPENABLE category declares that the returned file is accessible
             from a content provider that supports OpenableColumns
             and ContentResolver.openFileDescriptor(). -->
        <category android:name="android.intent.category.OPENABLE" />
    </intent-filter>
</activity>

فتح نوع معيّن من الملفات

بدلاً من استرداد نسخة من ملف يجب استيراده إلى تطبيقك، يمكنك استخدام الإجراء ACTION_GET_CONTENT عند تشغيل الإصدار 4.4 من نظام التشغيل Android أو إصدار أحدث، ويمكنك بدلاً من ذلك طلب فتح ملف يديره تطبيق آخر باستخدام إجراء ACTION_OPEN_DOCUMENT وتحديد نوع MIME. للسماح للمستخدم أيضًا بإنشاء مستند جديد يمكن لتطبيقك الكتابة إليه، يمكنك استخدام إجراء ACTION_CREATE_DOCUMENT بدلاً من ذلك.

على سبيل المثال، بدلاً من الاختيار من مستندات PDF الحالية، تتيح نية ACTION_CREATE_DOCUMENT للمستخدمين اختيار المكان الذي يريدون إنشاء مستند جديد فيه، مثل داخل تطبيق آخر يدير مساحة تخزين المستند. يتلقى تطبيقك بعد ذلك موقع URI الذي يمكنه فيه كتابة المستند الجديد.

في حين أنّ الغرض الذي يتم إرساله إلى طريقة onActivityResult() من الإجراء ACTION_GET_CONTENT قد يعرض معرّف موارد منتظم (URI) من أي نوع، فإنّ الغرض من النتيجة من ACTION_OPEN_DOCUMENT وACTION_CREATE_DOCUMENT يحدّد دائمًا الملف المختار على أنّه معرّف الموارد المنتظم (URI) content: المدعوم بـ DocumentsProvider. يمكنك فتح الملف باستخدام openFileDescriptor() والاستعلام عن تفاصيله باستخدام أعمدة من DocumentsContract.Document.

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

ويمكنك أيضًا السماح للمستخدم باختيار ملفات متعدّدة من خلال إضافة EXTRA_ALLOW_MULTIPLE إلى الغرض، وضبطه على true. إذا اختار المستخدم عنصرًا واحدًا فقط، يمكنك استرداد العنصر من خلال getData(). إذا اختار المستخدم أكثر من عنصر، ستعرِض السمة getData() قيمة فارغة، وعليك بدلاً من ذلك استرداد كل عنصر من كائن ClipData الذي يعرضه getClipData().

ملاحظة: يجب أن يحدّد الغرض نوع MIME ويجب أن يفصح عن الفئة CATEGORY_OPENABLE. يمكنك تحديد أكثر من نوع MIME واحد عن طريق إضافة مصفوفة من أنواع MIME مع إضافة EXTRA_MIME_TYPES، وفي حال إجراء ذلك، عليك ضبط نوع MIME الأساسي في setType() على "*/*".

الإجراء
ACTION_OPEN_DOCUMENT أو
ACTION_CREATE_DOCUMENT
مخطط معرّف الموارد المنتظم (URI) للبيانات
ما مِن قيمة محدّدة
نوع MIME
نوع MIME المتوافق مع نوع الملف الذي يحتاج المستخدم إلى اختياره.
الإضافات
EXTRA_MIME_TYPES
يجب تحديد مصفوفة من أنواع MIME تتوافق مع أنواع الملفات التي يطلبها تطبيقك. عند استخدام هذه القيمة الإضافية، يجب ضبط نوع MIME الأساسي في setType() على "*/*".
EXTRA_ALLOW_MULTIPLE
قيمة منطقية توضّح ما إذا كان بإمكان المستخدم اختيار أكثر من ملف واحد في المرّة الواحدة.
EXTRA_TITLE
تُستخدم مع ACTION_CREATE_DOCUMENT لتحديد اسم ملف مبدئي.
EXTRA_LOCAL_ONLY
قيمة منطقية توضّح ما إذا كان يجب أن يكون الملف المعروض متاحًا من الجهاز مباشرةً، بدلاً من طلب تنزيله من خدمة عن بُعد.
الفئة
CATEGORY_OPENABLE
لعرض الملفات "القابلة للفتح" فقط التي يمكن تمثيلها كتدفق ملفات باستخدام openFileDescriptor().

مثال على الرغبة في الحصول على صورة:

Kotlin

const val REQUEST_IMAGE_OPEN = 1

fun selectImage2() {
    val intent = Intent(Intent.ACTION_OPEN_DOCUMENT).apply {
        type = "image/*"
        addCategory(Intent.CATEGORY_OPENABLE)
    }
    // Only the system receives the ACTION_OPEN_DOCUMENT, so no need to test.
    startActivityForResult(intent, REQUEST_IMAGE_OPEN)
}

override fun onActivityResult(requestCode: Int, resultCode: Int, data: Intent) {
    if (requestCode == REQUEST_IMAGE_OPEN && resultCode == Activity.RESULT_OK) {
        val fullPhotoUri: Uri = data.data
        // Do work with full size photo saved at fullPhotoUri.
        ...
    }
}

Java

static final int REQUEST_IMAGE_OPEN = 1;

public void selectImage() {
    Intent intent = new Intent(Intent.ACTION_OPEN_DOCUMENT);
    intent.setType("image/*");
    intent.addCategory(Intent.CATEGORY_OPENABLE);
    // Only the system receives the ACTION_OPEN_DOCUMENT, so no need to test.
    startActivityForResult(intent, REQUEST_IMAGE_OPEN);
}

@Override
protected void onActivityResult(int requestCode, int resultCode, Intent data) {
    if (requestCode == REQUEST_IMAGE_OPEN && resultCode == RESULT_OK) {
        Uri fullPhotoUri = data.getData();
        // Do work with full size photo saved at fullPhotoUri.
        ...
    }
}

لا يمكن للتطبيقات التابعة لجهات خارجية الاستجابة لهدف من خلال إجراء ACTION_OPEN_DOCUMENT. وبدلاً من ذلك، يتلقّى النظام هذه الرسالة ويعرض جميع الملفات المتاحة من تطبيقات مختلفة في واجهة مستخدم موحّدة.

لتقديم ملفات تطبيقك في واجهة المستخدم هذه والسماح للتطبيقات الأخرى بفتحها، يجب تنفيذ DocumentsProvider وتضمين فلتر أهداف لـ PROVIDER_INTERFACE ("android.content.action.DOCUMENTS_PROVIDER")، كما هو موضّح في المثال التالي:

<provider ...
    android:grantUriPermissions="true"
    android:exported="true"
    android:permission="android.permission.MANAGE_DOCUMENTS">
    <intent-filter>
        <action android:name="android.content.action.DOCUMENTS_PROVIDER" />
    </intent-filter>
</provider>

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

الإجراءات المحلية

يُعد استدعاء السيارة إجراءً محليًا شائعًا. أنشئ فلتر أهداف للإعلان عن قدرة تطبيقك على تنفيذ هذا الإجراء باستخدام المعلومات الواردة في القسم التالي.

الاتصال بسيارة

إجراءات Google Voice

  • "أريد سيارة أجرة"
  • "الاتصال بسيارة"

(Wear OS فقط)

للاتصال بسيارة أجرة، استخدِم الإجراء ACTION_RESERVE_TAXI_RESERVATION.

ملاحظة: يجب أن تطلب التطبيقات تأكيدًا من المستخدم قبل إكمال هذا الإجراء.

الإجراء
ACTION_RESERVE_TAXI_RESERVATION
معرّف الموارد المنتظم (URI) للبيانات
ما مِن قيمة محدّدة
نوع MIME
ما مِن قيمة محدّدة
الإضافات
لا شيء

مثال على الغرض:

Kotlin

fun callCar() {
    val intent = Intent(ReserveIntents.ACTION_RESERVE_TAXI_RESERVATION)
    if (intent.resolveActivity(packageManager) != null) {
        startActivity(intent)
    }
}

Java

public void callCar() {
    Intent intent = new Intent(ReserveIntents.ACTION_RESERVE_TAXI_RESERVATION);
    if (intent.resolveActivity(getPackageManager()) != null) {
        startActivity(intent);
    }
}

مثال على فلتر الأهداف:

<activity ...>
    <intent-filter>
        <action android:name="com.google.android.gms.actions.RESERVE_TAXI_RESERVATION" />
        <category android:name="android.intent.category.DEFAULT" />
    </intent-filter>
</activity>

Maps

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

عرض موقع جغرافي على الخريطة

لفتح خريطة، استخدِم الإجراء ACTION_VIEW وحدِّد معلومات الموقع الجغرافي في بيانات الأهداف باستخدام أحد المخطّطات التالية.

الإجراء
ACTION_VIEW
مخطط معرّف الموارد المنتظم (URI) للبيانات
geo:latitude,longitude
اعرض الخريطة عند خط الطول وخط العرض المحدّدَين.

مثال: "geo:47.6,-122.3"

geo:latitude,longitude?z=zoom
يمكنك عرض الخريطة على خط الطول وخط العرض المحدَّدين عند مستوى معيّن من التكبير. ويعرِض مستوى التكبير/التصغير 1 الأرض بأكملها، في مركز النص خط الطول وخط الطول والعرض المحدد. أعلى مستوى (أقرب) للتكبير هو 23.

مثال: "geo:47.6,-122.3?z=11"

geo:0,0?q=lat,lng(label)
اعرض الخريطة عند خط الطول وخط العرض المحدّدَين مع تصنيف سلسلة.

مثال: "geo:0,0?q=34.99,-106.61(Treasure)"

geo:0,0?q=my+street+address
عرض الموقع الجغرافي لـ "عنوان الشارع الخاص بي"، والذي يمكن أن يكون عنوانًا محددًا أو طلب بحث عن الموقع الجغرافي.

مثال: "geo:0,0?q=1600+Amphitheatre+Parkway%2C+CA"

ملاحظة: يجب ترميز جميع السلاسل التي يتم تمريرها في معرّف الموارد المنتظم (URI) geo. على سبيل المثال، تصبح السلسلة 1st & Pike, Seattle 1st%20%26%20Pike%2C%20Seattle. يتم ترميز المسافات في السلسلة باستخدام %20 أو استبدالها بعلامة الجمع (+).

نوع MIME
ما مِن قيمة محدّدة

مثال على الغرض:

Kotlin

fun showMap(geoLocation: Uri) {
    val intent = Intent(Intent.ACTION_VIEW).apply {
        data = geoLocation
    }
    if (intent.resolveActivity(packageManager) != null) {
        startActivity(intent)
    }
}

Java

public void showMap(Uri geoLocation) {
    Intent intent = new Intent(Intent.ACTION_VIEW);
    intent.setData(geoLocation);
    if (intent.resolveActivity(getPackageManager()) != null) {
        startActivity(intent);
    }
}

مثال على فلتر الأهداف:

<activity ...>
    <intent-filter>
        <action android:name="android.intent.action.VIEW" />
        <data android:scheme="geo" />
        <category android:name="android.intent.category.DEFAULT" />
    </intent-filter>
</activity>

موسيقى أو فيديو

في ما يلي الإجراءات الشائعة لتطبيقات الموسيقى والفيديو، بما في ذلك المعلومات التي تحتاجها لإنشاء فلتر أهداف للإعلان عن قدرة تطبيقك على تنفيذ كل إجراء.

تشغيل ملف وسائط

لتشغيل ملف موسيقى، استخدِم الإجراء ACTION_VIEW وحدِّد مكان معرّف الموارد المنتظم (URI) للملف في بيانات intent.

الإجراء
ACTION_VIEW
مخطط معرّف الموارد المنتظم (URI) للبيانات
file:<URI>
content:<URI>
http:<URL>
نوع MIME
"audio/*"
"application/ogg"
"application/x-ogg"
"application/itunes"
أو أي نظام آخر يتطلبه تطبيقك.

مثال على الغرض:

Kotlin

fun playMedia(file: Uri) {
    val intent = Intent(Intent.ACTION_VIEW).apply {
        data = file
    }
    if (intent.resolveActivity(packageManager) != null) {
        startActivity(intent)
    }
}

Java

public void playMedia(Uri file) {
    Intent intent = new Intent(Intent.ACTION_VIEW);
    intent.setData(file);
    if (intent.resolveActivity(getPackageManager()) != null) {
        startActivity(intent);
    }
}

مثال على فلتر الأهداف:

<activity ...>
    <intent-filter>
        <action android:name="android.intent.action.VIEW" />
        <data android:type="audio/*" />
        <data android:type="application/ogg" />
        <category android:name="android.intent.category.DEFAULT" />
    </intent-filter>
</activity>

تشغيل الموسيقى استنادًا إلى طلب بحث

إجراءات Google Voice

  • "تشغيل أغاني مايكل جاكسون بيلي جين"

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

في هذا الغرض، ضمِّن سلسلة EXTRA_MEDIA_FOCUS إضافية (extra) التي تحدّد وضع البحث المقصود. على سبيل المثال، يمكن أن يحدد وضع البحث ما إذا كان البحث عن اسم فنان أو اسم أغنية.

الإجراء
INTENT_ACTION_MEDIA_PLAY_FROM_SEARCH
مخطط معرّف الموارد المنتظم (URI) للبيانات
ما مِن قيمة محدّدة
نوع MIME
ما مِن قيمة محدّدة
الإضافات
MediaStore.EXTRA_MEDIA_FOCUS (مطلوب)

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

أيّ - "vnd.android.cursor.item/*"

شغِّل أي محتوى موسيقي. يشغّل التطبيق المستقبِل بعض الموسيقى استنادًا إلى خيار ذكي، مثل آخر قائمة تشغيل استمع إليها المستخدم.

ميزات إضافية:

  • QUERY (مطلوب): سلسلة فارغة. ويتم توفير هذه الميزات الإضافية دائمًا للتوافق مع الأنظمة القديمة. وبالنسبة إلى التطبيقات الحالية التي لا تعرف أوضاع البحث، يمكنها معالجة الغرض من عملية البحث على أنّها عملية بحث غير منظَّم.

غير مهيكلة - "vnd.android.cursor.item/*"

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

ميزات إضافية:

  • QUERY (مطلوبة): سلسلة تحتوي على أي مجموعة من أعمال الفنّان أو الألبوم أو اسم الأغنية أو النوع

النوع - Audio.Genres.ENTRY_CONTENT_TYPE

تشغيل موسيقى من نوع معيّن

ميزات إضافية:

  • "android.intent.extra.genre" (مطلوب) - النوع.
  • QUERY (مطلوب): النوع. ويتم توفير هذه الميزات الإضافية دائمًا للتوافق مع الأنظمة القديمة. أمّا التطبيقات الحالية التي لا تعرف أوضاع البحث، فيمكنها معالجة هذا الغرض على أنّه عملية بحث غير منظَّمة.

الفنان - Audio.Artists.ENTRY_CONTENT_TYPE

تشغيل موسيقى لفنّان محدّد

ميزات إضافية:

  • EXTRA_MEDIA_ARTIST (مطلوب): الفنّان.
  • "android.intent.extra.genre": النوع
  • QUERY (مطلوبة): سلسلة تحتوي على أي مجموعة من أعمال الفنّان أو النوع. ويتم توفير هذه الميزات الإضافية دائمًا للتوافق مع الأنظمة القديمة. وبالنسبة إلى التطبيقات الحالية التي لا تعرف أوضاع البحث، يمكنها معالجة الغرض من عملية البحث على أنّها عملية بحث غير منظَّم.

ألبوم - Audio.Albums.ENTRY_CONTENT_TYPE

تشغيل موسيقى من ألبوم معيّن

ميزات إضافية:

  • EXTRA_MEDIA_ALBUM (مطلوب): الألبوم.
  • EXTRA_MEDIA_ARTIST: الفنّان
  • "android.intent.extra.genre": النوع
  • QUERY (مطلوبة): سلسلة تحتوي على أي تركيبة من الألبوم أو الفنّان ويتم توفير هذه الميزات الإضافية دائمًا للتوافق مع الأنظمة القديمة. أمّا التطبيقات الحالية التي لا تعرف أوضاع البحث، يمكنها معالجة الغرض من البحث على أنّها عملية بحث غير منظَّم.

أغنية - "vnd.android.cursor.item/audio"

تشغيل أغنية معيّنة

ميزات إضافية:

  • EXTRA_MEDIA_ALBUM: الألبوم
  • EXTRA_MEDIA_ARTIST: الفنّان
  • "android.intent.extra.genre": النوع
  • EXTRA_MEDIA_TITLE (مطلوب): اسم الأغنية.
  • QUERY (مطلوبة): سلسلة تحتوي على أي مجموعة من الألبوم أو الفنان أو النوع أو العنوان. ويتم توفير هذه الميزات الإضافية دائمًا للتوافق مع الأنظمة القديمة. ويمكن للتطبيقات الحالية التي لا تعرف أوضاع البحث أن تعالج هذا الهدف على أنّه عملية بحث غير منظَّم.

قائمة تشغيل - Audio.Playlists.ENTRY_CONTENT_TYPE

لتشغيل قائمة تشغيل معيّنة أو قائمة تشغيل معيّنة تطابق بعض المعايير المحددة بواسطة عناصر إضافية إضافية.

ميزات إضافية:

  • EXTRA_MEDIA_ALBUM: الألبوم
  • EXTRA_MEDIA_ARTIST: الفنّان
  • "android.intent.extra.genre": النوع
  • "android.intent.extra.playlist": قائمة التشغيل
  • EXTRA_MEDIA_TITLE: اسم الأغنية التي تستند إليها قائمة التشغيل
  • QUERY (مطلوبة): سلسلة تحتوي على أي مجموعة من الألبوم أو الفنّان أو النوع أو قائمة التشغيل أو العنوان ويتم توفير هذه الميزات الإضافية دائمًا للتوافق مع الأنظمة القديمة. وبالنسبة إلى التطبيقات الحالية التي لا تعرف أوضاع البحث، يمكنها معالجة الغرض من عملية البحث على أنّها عملية بحث غير منظَّم.

مثال على الغرض:

إذا أراد المستخدم الاستماع إلى موسيقى من فنّان معيّن، قد ينشئ تطبيق البحث الغرض التالي:

Kotlin

fun playSearchArtist(artist: String) {
    val intent = Intent(MediaStore.INTENT_ACTION_MEDIA_PLAY_FROM_SEARCH).apply {
        putExtra(MediaStore.EXTRA_MEDIA_FOCUS, MediaStore.Audio.Artists.ENTRY_CONTENT_TYPE)
        putExtra(MediaStore.EXTRA_MEDIA_ARTIST, artist)
        putExtra(SearchManager.QUERY, artist)
    }
    if (intent.resolveActivity(packageManager) != null) {
        startActivity(intent)
    }
}

Java

public void playSearchArtist(String artist) {
    Intent intent = new Intent(MediaStore.INTENT_ACTION_MEDIA_PLAY_FROM_SEARCH);
    intent.putExtra(MediaStore.EXTRA_MEDIA_FOCUS,
                    MediaStore.Audio.Artists.ENTRY_CONTENT_TYPE);
    intent.putExtra(MediaStore.EXTRA_MEDIA_ARTIST, artist);
    intent.putExtra(SearchManager.QUERY, artist);
    if (intent.resolveActivity(getPackageManager()) != null) {
        startActivity(intent);
    }
}

مثال على فلتر الأهداف:

<activity ...>
    <intent-filter>
        <action android:name="android.media.action.MEDIA_PLAY_FROM_SEARCH" />
        <category android:name="android.intent.category.DEFAULT" />
    </intent-filter>
</activity>

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

Kotlin

override fun onCreate(savedInstanceState: Bundle?) {
    ...
    if (intent.action.compareTo(MediaStore.INTENT_ACTION_MEDIA_PLAY_FROM_SEARCH) == 0) {

        val mediaFocus: String? = intent.getStringExtra(MediaStore.EXTRA_MEDIA_FOCUS)
        val query: String? = intent.getStringExtra(SearchManager.QUERY)

        // Some of these extras might not be available depending on the search mode.
        val album: String? = intent.getStringExtra(MediaStore.EXTRA_MEDIA_ALBUM)
        val artist: String? = intent.getStringExtra(MediaStore.EXTRA_MEDIA_ARTIST)
        val genre: String? = intent.getStringExtra("android.intent.extra.genre")
        val playlist: String? = intent.getStringExtra("android.intent.extra.playlist")
        val title: String? = intent.getStringExtra(MediaStore.EXTRA_MEDIA_TITLE)

        // Determine the search mode and use the corresponding extras.
        when {
            mediaFocus == null -> {
                // 'Unstructured' search mode (backward compatible)
                playUnstructuredSearch(query)
            }
            mediaFocus.compareTo("vnd.android.cursor.item/*") == 0 -> {
                if (query?.isNotEmpty() == true) {
                    // 'Unstructured' search mode.
                    playUnstructuredSearch(query)
                } else {
                    // 'Any' search mode.
                    playResumeLastPlaylist()
                }
            }
            mediaFocus.compareTo(MediaStore.Audio.Genres.ENTRY_CONTENT_TYPE) == 0 -> {
                // 'Genre' search mode.
                playGenre(genre)
            }
            mediaFocus.compareTo(MediaStore.Audio.Artists.ENTRY_CONTENT_TYPE) == 0 -> {
                // 'Artist' search mode.
                playArtist(artist, genre)
            }
            mediaFocus.compareTo(MediaStore.Audio.Albums.ENTRY_CONTENT_TYPE) == 0 -> {
                // 'Album' search mode.
                playAlbum(album, artist)
            }
            mediaFocus.compareTo("vnd.android.cursor.item/audio") == 0 -> {
                // 'Song' search mode.
                playSong(album, artist, genre, title)
            }
            mediaFocus.compareTo(MediaStore.Audio.Playlists.ENTRY_CONTENT_TYPE) == 0 -> {
                // 'Playlist' search mode.
                playPlaylist(album, artist, genre, playlist, title)
            }
        }
    }
}

Java

protected void onCreate(Bundle savedInstanceState) {
    //...
    Intent intent = this.getIntent();
    if (intent.getAction().compareTo(MediaStore.INTENT_ACTION_MEDIA_PLAY_FROM_SEARCH) == 0) {

        String mediaFocus = intent.getStringExtra(MediaStore.EXTRA_MEDIA_FOCUS);
        String query = intent.getStringExtra(SearchManager.QUERY);

        // Some of these extras might not be available depending on the search mode.
        String album = intent.getStringExtra(MediaStore.EXTRA_MEDIA_ALBUM);
        String artist = intent.getStringExtra(MediaStore.EXTRA_MEDIA_ARTIST);
        String genre = intent.getStringExtra("android.intent.extra.genre");
        String playlist = intent.getStringExtra("android.intent.extra.playlist");
        String title = intent.getStringExtra(MediaStore.EXTRA_MEDIA_TITLE);

        // Determine the search mode and use the corresponding extras.
        if (mediaFocus == null) {
            // 'Unstructured' search mode (backward compatible).
            playUnstructuredSearch(query);

        } else if (mediaFocus.compareTo("vnd.android.cursor.item/*") == 0) {
            if (query.isEmpty()) {
                // 'Any' search mode.
                playResumeLastPlaylist();
            } else {
                // 'Unstructured' search mode.
                playUnstructuredSearch(query);
            }

        } else if (mediaFocus.compareTo(MediaStore.Audio.Genres.ENTRY_CONTENT_TYPE) == 0) {
            // 'Genre' search mode.
            playGenre(genre);

        } else if (mediaFocus.compareTo(MediaStore.Audio.Artists.ENTRY_CONTENT_TYPE) == 0) {
            // 'Artist' search mode.
            playArtist(artist, genre);

        } else if (mediaFocus.compareTo(MediaStore.Audio.Albums.ENTRY_CONTENT_TYPE) == 0) {
            // 'Album' search mode.
            playAlbum(album, artist);

        } else if (mediaFocus.compareTo("vnd.android.cursor.item/audio") == 0) {
            // 'Song' search mode.
            playSong(album, artist, genre, title);

        } else if (mediaFocus.compareTo(MediaStore.Audio.Playlists.ENTRY_CONTENT_TYPE) == 0) {
            // 'Playlist' search mode.
            playPlaylist(album, artist, genre, playlist, title);
        }
    }
}

ملاحظة جديدة

يعد إنشاء ملاحظة إجراءً شائعًا لتطبيقات تدوين الملاحظات. يمكنك إنشاء فلتر أهداف للإعلان عن قدرة تطبيقك على تنفيذ هذا الإجراء باستخدام المعلومات الواردة في القسم التالي.

إنشاء ملاحظة

لإنشاء ملاحظة جديدة، استخدِم الإجراء ACTION_CREATE_NOTE وحدِّد تفاصيل الملاحظة، مثل الموضوع والنص، وذلك باستخدام العناصر الإضافية التالية.

ملاحظة: يجب أن تطلب التطبيقات تأكيدًا من المستخدم قبل إكمال هذا الإجراء.

الإجراء
ACTION_CREATE_NOTE
مخطط معرّف الموارد المنتظم (URI) للبيانات
ما مِن قيمة محدّدة
نوع MIME
PLAIN_TEXT_TYPE
"*/*"
الإضافات
EXTRA_NAME
سلسلة تشير إلى عنوان الملاحظة أو موضوعها.
EXTRA_TEXT
سلسلة تشير إلى نص الملاحظة.

مثال على الغرض:

Kotlin

fun createNote(subject: String, text: String) {
    val intent = Intent(NoteIntents.ACTION_CREATE_NOTE).apply {
        putExtra(NoteIntents.EXTRA_NAME, subject)
        putExtra(NoteIntents.EXTRA_TEXT, text)
    }
    if (intent.resolveActivity(packageManager) != null) {
        startActivity(intent)
    }
}

Java

public void createNote(String subject, String text) {
    Intent intent = new Intent(NoteIntents.ACTION_CREATE_NOTE)
            .putExtra(NoteIntents.EXTRA_NAME, subject)
            .putExtra(NoteIntents.EXTRA_TEXT, text);
    if (intent.resolveActivity(getPackageManager()) != null) {
        startActivity(intent);
    }
}

مثال على فلتر الأهداف:

<activity ...>
    <intent-filter>
        <action android:name="com.google.android.gms.actions.CREATE_NOTE" />
        <category android:name="android.intent.category.DEFAULT" />
        <data android:mimeType="*/*" />
    </intent-filter>
</activity>

الهاتف

إنّ بدء مكالمة هو إجراء شائع لتطبيقات الهاتف. يمكنك إنشاء فلتر أهداف للإعلان عن قدرة تطبيقك على تنفيذ هذا الإجراء باستخدام المعلومات الواردة في القسم التالي.

بدء مكالمة هاتفية

لفتح تطبيق الهاتف وطلب رقم هاتف، استخدِم الإجراء ACTION_DIAL وحدِّد رقم هاتف باستخدام نظام معرِّف الموارد المنتظم (URI) التالي. عند فتح تطبيق الهاتف، يعرض رقم الهاتف، ويتعين على المستخدم النقر على زر الاتصال لبدء المكالمة الهاتفية.

إجراءات Google Voice

  • "الاتصال بالرقم 555-5555"
  • "الاتصال ببوب"
  • "الاتصال بالبريد الصوتي"

لإجراء مكالمة هاتفية مباشرةً، استخدِم الإجراء ACTION_CALL وحدِّد رقم هاتف باستخدام مخطط معرِّف الموارد المنتظم (URI) التالي. عند فتح تطبيق الهاتف، يبدأ المكالمة الهاتفية. ولا يحتاج المستخدم إلى النقر على زر الاتصال.

يتطلّب الإجراء ACTION_CALL إضافة إذن CALL_PHONE إلى ملف البيان:

<uses-permission android:name="android.permission.CALL_PHONE" />
الإجراء
  • ACTION_DIAL: لفتح برنامج الاتصال أو تطبيق الهاتف.
  • ACTION_CALL - الأماكن لإجراء مكالمة هاتفية (تتطلّب إذن CALL_PHONE)
مخطط معرّف الموارد المنتظم (URI) للبيانات
  • tel:<phone-number>
  • voicemail:<phone-number>
نوع MIME
ما مِن قيمة محدّدة

وأرقام الهاتف الصالحة هي تلك المحددة في معيار IETF RFC 3966. تشمل الأمثلة الصالحة ما يلي:

  • tel:2125551212
  • tel:(212) 555 1212

يُعد برنامج الاتصال في تطبيق الهاتف جيدًا في تسوية المخططات، مثل أرقام الهاتف. وبالتالي، فإن المخطط الموضّح ليس مطلوبًا بشكل صارم في طريقة Uri.parse(). مع ذلك، إذا لم تكن قد جرّبت مخطّطًا أو لم تكن متأكدًا من إمكانية التعامل معه، استخدِم الطريقة Uri.fromParts() بدلاً من ذلك.

مثال على الغرض:

Kotlin

fun dialPhoneNumber(phoneNumber: String) {
    val intent = Intent(Intent.ACTION_DIAL).apply {
        data = Uri.parse("tel:$phoneNumber")
    }
    if (intent.resolveActivity(packageManager) != null) {
        startActivity(intent)
    }
}

Java

public void dialPhoneNumber(String phoneNumber) {
    Intent intent = new Intent(Intent.ACTION_DIAL);
    intent.setData(Uri.parse("tel:" + phoneNumber));
    if (intent.resolveActivity(getPackageManager()) != null) {
        startActivity(intent);
    }
}

في ما يلي الإجراءات الشائعة لتطبيقات البحث، بما في ذلك المعلومات التي تحتاجها لإنشاء فلتر أهداف للإعلان عن قدرة تطبيقك على تنفيذ كل إجراء.

البحث باستخدام تطبيق معيّن

إجراءات Google Voice

  • "البحث عن فيديوهات عن القطط على myvideoapp"

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

ملاحظة: لا ننصح باستخدام SEARCH_ACTION للبحث في التطبيق. بدلاً من ذلك، يمكنك تنفيذ إجراء GET_THING للاستفادة من دعم "مساعد Google" المضمّن للبحث داخل التطبيق. ولمزيد من المعلومات، اطّلِع على مستندات الإجراءات المتعلّقة بالتطبيقات في "مساعد Google".

الإجراء
"com.google.android.gms.actions.SEARCH_ACTION"
دعم طلبات البحث من خدمة "الإجراءات الصوتية من Google"
الإضافات
QUERY
سلسلة تحتوي على طلب البحث

مثال على فلتر الأهداف:

<activity android:name=".SearchActivity">
    <intent-filter>
        <action android:name="com.google.android.gms.actions.SEARCH_ACTION"/>
        <category android:name="android.intent.category.DEFAULT"/>
    </intent-filter>
</activity>

إجراء بحث على الويب

لبدء بحث ويب، استخدِم الإجراء ACTION_WEB_SEARCH وحدِّد سلسلة البحث في عنصر SearchManager.QUERY الإضافي.

الإجراء
ACTION_WEB_SEARCH
مخطط معرّف الموارد المنتظم (URI) للبيانات
ما مِن قيمة محدّدة
نوع MIME
ما مِن قيمة محدّدة
الإضافات
SearchManager.QUERY
سلسلة البحث:

مثال على الغرض:

Kotlin

fun searchWeb(query: String) {
    val intent = Intent(Intent.ACTION_WEB_SEARCH).apply {
        putExtra(SearchManager.QUERY, query)
    }
    if (intent.resolveActivity(packageManager) != null) {
        startActivity(intent)
    }
}

Java

public void searchWeb(String query) {
    Intent intent = new Intent(Intent.ACTION_WEB_SEARCH);
    intent.putExtra(SearchManager.QUERY, query);
    if (intent.resolveActivity(getPackageManager()) != null) {
        startActivity(intent);
    }
}

الإعدادات

لفتح شاشة في تطبيق "إعدادات النظام" عندما يطلب تطبيقك من المستخدم تغيير عنصر ما، استخدِم أحد إجراءات intent التالية:

الإجراء
ACTION_SETTINGS
ACTION_WIRELESS_SETTINGS
ACTION_AIRPLANE_MODE_SETTINGS
ACTION_WIFI_SETTINGS
ACTION_APN_SETTINGS
ACTION_BLUETOOTH_SETTINGS
ACTION_DATE_SETTINGS
ACTION_LOCALE_SETTINGS
ACTION_INPUT_METHOD_SETTINGS
ACTION_DISPLAY_SETTINGS
ACTION_SECURITY_SETTINGS
ACTION_LOCATION_SOURCE_SETTINGS
ACTION_INTERNAL_STORAGE_SETTINGS
ACTION_MEMORY_CARD_SETTINGS

للحصول على شاشات الإعدادات الإضافية المتاحة، يُرجى الاطّلاع على مستندات Settings .

مخطط معرّف الموارد المنتظم (URI) للبيانات
ما مِن قيمة محدّدة
نوع MIME
ما مِن قيمة محدّدة

مثال على الغرض:

Kotlin

fun openWifiSettings() {
    val intent = Intent(Settings.ACTION_WIFI_SETTINGS)
    if (intent.resolveActivity(packageManager) != null) {
        startActivity(intent)
    }
}

Java

public void openWifiSettings() {
    Intent intent = new Intent(Settings.ACTION_WIFI_SETTINGS);
    if (intent.resolveActivity(getPackageManager()) != null) {
        startActivity(intent);
    }
}

المراسلة النصية

إنشاء رسالة قصيرة SMS/رسالة وسائط متعددة مع مرفق هو إجراء شائع لتطبيقات المراسلة النصية. يمكنك إنشاء فلتر أهداف للإعلان عن قدرة تطبيقك على تنفيذ هذا الإجراء باستخدام المعلومات الواردة في القسم التالي.

إنشاء رسالة قصيرة SMS أو رسالة وسائط متعددة مع مرفق

لبدء رسالة قصيرة SMS أو رسالة وسائط متعددة، يمكنك استخدام أحد الإجراءات التالية لتحديد تفاصيل الرسالة، مثل رقم الهاتف والموضوع ونص الرسالة باستخدام المفاتيح الإضافية التالية.

الإجراء
ACTION_SENDTO أو
ACTION_SEND أو
ACTION_SEND_MULTIPLE
مخطط معرّف الموارد المنتظم (URI) للبيانات
sms:<phone_number>
smsto:<phone_number>
mms:<phone_number>
mmsto:<phone_number>

يتم التعامل مع جميع هذه المخطّطات بالطريقة نفسها.

نوع MIME
"text/plain"
"image/*"
"video/*"
الإضافات
"subject"
سلسلة لموضوع الرسالة (عادةً لرسائل الوسائط المتعددة فقط)
"sms_body"
سلسلة للرسالة النصية
EXTRA_STREAM
صورة Uri تشير إلى الصورة أو الفيديو لإرفاقها في حال استخدام الإجراء ACTION_SEND_MULTIPLE، يكون العنصر الإضافي ArrayList من إجمالي Uri كائنًا يشير إلى الصور أو الفيديوهات المطلوب إرفاقها.

مثال على الغرض:

Kotlin

fun composeMmsMessage(message: String, attachment: Uri) {
    val intent = Intent(Intent.ACTION_SENDTO).apply {
        type = HTTP.PLAIN_TEXT_TYPE
        putExtra("sms_body", message)
        putExtra(Intent.EXTRA_STREAM, attachment)
    }
    if (intent.resolveActivity(packageManager) != null) {
        startActivity(intent)
    }
}

Java

public void composeMmsMessage(String message, Uri attachment) {
    Intent intent = new Intent(Intent.ACTION_SENDTO);
    intent.setType(HTTP.PLAIN_TEXT_TYPE);
    intent.putExtra("sms_body", message);
    intent.putExtra(Intent.EXTRA_STREAM, attachment);
    if (intent.resolveActivity(getPackageManager()) != null) {
        startActivity(intent);
    }
}

إذا كنت تريد التأكّد من أنّه سيتمّ تنفيذ هدفك من خلال تطبيق مراسلة نصية فقط، وليس تطبيقات بريد إلكتروني أو تطبيقات تواصل اجتماعي أخرى، استخدِم الإجراء ACTION_SENDTO وأدرِج نظام بيانات "smsto:" كما هو موضّح في المثال التالي:

Kotlin

fun composeMmsMessage(message: String, attachment: Uri) {
    val intent = Intent(Intent.ACTION_SEND).apply {
        data = Uri.parse("smsto:")  // Only SMS apps respond to this.
        putExtra("sms_body", message)
        putExtra(Intent.EXTRA_STREAM, attachment)
    }
    if (intent.resolveActivity(packageManager) != null) {
        startActivity(intent)
    }
}

Java

public void composeMmsMessage(String message, Uri attachment) {
    Intent intent = new Intent(Intent.ACTION_SEND);
    intent.setData(Uri.parse("smsto:"));  // Only SMS apps respond to this.
    intent.putExtra("sms_body", message);
    intent.putExtra(Intent.EXTRA_STREAM, attachment);
    if (intent.resolveActivity(getPackageManager()) != null) {
        startActivity(intent);
    }
}

مثال على فلتر الأهداف:

<activity ...>
    <intent-filter>
        <action android:name="android.intent.action.SEND" />
        <data android:type="text/plain" />
        <data android:type="image/*" />
        <category android:name="android.intent.category.DEFAULT" />
    </intent-filter>
</activity>

ملاحظة: إذا كنت تعمل على تطوير تطبيق للرسائل القصيرة SMS أو رسائل الوسائط المتعددة (MMS)، يجب تنفيذ فلاتر الأهداف لعدة إجراءات إضافية لتصبح متوفرة كتطبيق الرسائل القصيرة التلقائي على Android 4.4 والإصدارات الأحدث. لمزيد من المعلومات، راجِع المستندات في Telephony.

متصفح الويب

يعد تحميل عنوان URL للويب إجراءً شائعًا لتطبيقات متصفح الويب. يمكنك إنشاء فلتر أهداف للإعلان عن قدرة تطبيقك على تنفيذ هذا الإجراء باستخدام المعلومات الواردة في القسم التالي.

تحميل عنوان URL على الويب

إجراءات Google Voice

  • فتح example.com

لفتح صفحة ويب، استخدِم الإجراء ACTION_VIEW وحدِّد عنوان URL للويب في بيانات intent.

الإجراء
ACTION_VIEW
مخطط معرّف الموارد المنتظم (URI) للبيانات
http:<URL>
https:<URL>
نوع MIME
"text/plain"
"text/html"
"application/xhtml+xml"
"application/vnd.wap.xhtml+xml"

مثال على الغرض:

Kotlin

fun openWebPage(url: String) {
    val webpage: Uri = Uri.parse(url)
    val intent = Intent(Intent.ACTION_VIEW, webpage)
    if (intent.resolveActivity(packageManager) != null) {
        startActivity(intent)
    }
}

Java

public void openWebPage(String url) {
    Uri webpage = Uri.parse(url);
    Intent intent = new Intent(Intent.ACTION_VIEW, webpage);
    if (intent.resolveActivity(getPackageManager()) != null) {
        startActivity(intent);
    }
}

مثال على فلتر الأهداف:

<activity ...>
    <intent-filter>
        <action android:name="android.intent.action.VIEW" />
        <!-- Include the host attribute if you want your app to respond
             only to URLs with your app's domain. -->
        <data android:scheme="http" android:host="www.example.com" />
        <category android:name="android.intent.category.DEFAULT" />
        <!-- The BROWSABLE category is required to get links from web pages. -->
        <category android:name="android.intent.category.BROWSABLE" />
    </intent-filter>
</activity>

نصيحة: إذا كان تطبيق Android يوفّر وظائف مشابهة لموقعك الإلكتروني، ضمِّن فلتر أهداف لعناوين URL التي تشير إلى موقعك الإلكتروني. وبعد ذلك، إذا ثبَّت المستخدمون تطبيقك، سيتم فتح تطبيق Android بدلاً من صفحة الويب إذا كانت الروابط من الرسائل الإلكترونية أو صفحات الويب الأخرى التي تشير إلى موقعك الإلكتروني. تعرَّف على مزيد من المعلومات في التعامل مع ميزة Android App Links.

بدءًا من Android 12 (المستوى 31 من واجهة برمجة التطبيقات)، يتم تحويل هدف الويب العام إلى نشاط في تطبيقك فقط إذا تمت الموافقة على تطبيقك للنطاق المحدّد المضمن في هدف الويب هذا. وإذا لم تتم الموافقة على تطبيقك في النطاق، ستنتقل النية بالشراء إلى تطبيق الويب التلقائي لدى المستخدم بدلاً من ذلك.

التحقّق من الأهداف باستخدام Android Debug Bridge

للتأكّد من أنّ تطبيقك يتجاوب مع الأهداف التي تريد تعزيزها، يمكنك استخدام أداة adb لإطلاق نوايا محدّدة من خلال تنفيذ ما يلي:

  1. عليك إعداد جهاز Android للتطوير أو استخدام جهاز افتراضي.
  2. ثبِّت إصدارًا من تطبيقك ينفّذ الأهداف التي تريد تعزيزها.
  3. إرسال هدف باستخدام adb:
    adb shell am start -a <ACTION> -t <MIME_TYPE> -d <DATA> \
      -e <EXTRA_NAME> <EXTRA_VALUE> -n <ACTIVITY>
    

    على سبيل المثال:

    adb shell am start -a android.intent.action.DIAL \
      -d tel:555-5555 -n org.example.MyApp/.MyActivity
    
  4. إذا حدّدت فلاتر الأهداف المطلوبة، فتعامل مع الغرض.

لمزيد من المعلومات، اطّلِع على المشاكل في أوامر واجهة الأوامر.