الفرق بين المراجعتين لصفحة: «ReactNative/linking»
رقية-بورية (نقاش | مساهمات) |
جميل-بيلوني (نقاش | مساهمات) طلا ملخص تعديل |
||
(6 مراجعات متوسطة بواسطة مستخدمين اثنين آخرين غير معروضة) | |||
سطر 1: | سطر 1: | ||
<blockquote>{{DISPLAYTITLE:Linking في React Native}}<noinclude> | <blockquote>{{DISPLAYTITLE:الواجهة Linking في React Native}}<noinclude> | ||
'''خاصٌ بالمشاريع المكتوبة بشفرة Native''' | |||
تطبّق هذه المقالة على المشاريع المكتوبة بشفرة Native فقط؛ أمّا عند استخدام سير العمل <code>expo-cli</code>، فيمكن الاطّلاع على الدّليل [http://docs.expo.io/versions/latest/workflow/linking Linking] ضمن توثيق Expo لإيجاد البديل الملائم. | تطبّق هذه المقالة على المشاريع المكتوبة بشفرة Native فقط؛ أمّا عند استخدام سير العمل <code>expo-cli</code>، فيمكن الاطّلاع على الدّليل [http://docs.expo.io/versions/latest/workflow/linking Linking] ضمن توثيق Expo لإيجاد البديل الملائم. | ||
</blockquote>تُقدّم الواجهة <code>Linking</code> واجهةً عامّةً للتّفاعل مع الرّوابط الواردة، والصّادرة للتّطبيقات، ولكل رابط (URL) نوع يحدد ببادئة الرابط (يطلق عليه أحيانًا تخطيط العنوان أو [[wikipedia:List_of_URI_schemes|URL schema]])، مثل: البادئة <code>http</code>، أو <code>https</code> في عنوان الموقع، كما يوجد رابط <code>mailto</code>، الذي يقوم نظام التّشغيل -عند فتح رابطٍ يحويه- بفتح تطبيق البريد الإكترونيّ المنصّب على الجهاز، كما توجد روابط للاتّصال الهاتفيّ، وإرسال الرّسائل النّصّيّة، ستُشرح أنواع الرّوابط الضّمنيّة built-in URL لاحقًا بالتّفصيل. | |||
يمكن الرّبط مع التّطبيقات الأخرى -بشكلٍ مماثلٍ للرابط <code>mailto</code>- باستخدام نوع <code>URL</code> المخصصة، مثلًا: عند استلام البريد الإلكتروني Magic Link من تطبيق Slack سيكون المفتاح Launch Slack هو وسم الربط (anchor tag)، والذي يتضمّن رابطًا مرجعيّا فائقًا (href) له الشّكل التّالي: <code>slack://secret/magic-login/other-secret</code> يمكننا إخبار نظام التّشغيل بأننا نريد معالجة مخطط مخصّص كما في Slack، عند فتح تطبيق Slack فإنّه يستقبل الرّابط المُستخدَم في فتحه، ويمكن بنفس الطّريقة ربط أيّ تطبيقٍ باستخدام المخطّطات المخصّصة، وهو ما يسمى بالرّبط العميق (deep linking) والذي سيُشرح لاحقًا بالتّفصيل. | يمكن الرّبط مع التّطبيقات الأخرى -بشكلٍ مماثلٍ للرابط <code>mailto</code>- باستخدام نوع <code>URL</code> المخصصة، مثلًا: عند استلام البريد الإلكتروني Magic Link من تطبيق Slack سيكون المفتاح Launch Slack هو وسم الربط (anchor tag)، والذي يتضمّن رابطًا مرجعيّا فائقًا (href) له الشّكل التّالي: <code>slack://secret/magic-login/other-secret</code> يمكننا إخبار نظام التّشغيل بأننا نريد معالجة مخطط مخصّص كما في Slack، عند فتح تطبيق Slack فإنّه يستقبل الرّابط المُستخدَم في فتحه، ويمكن بنفس الطّريقة ربط أيّ تطبيقٍ باستخدام المخطّطات المخصّصة، وهو ما يسمى بالرّبط العميق (deep linking) والذي سيُشرح لاحقًا بالتّفصيل. | ||
سطر 86: | سطر 87: | ||
=== فتح الروابط الضمنية والعميقة (والشاملة) === | === فتح الروابط الضمنية والعميقة (والشاملة) === | ||
<syntaxhighlight lang="javascript"> | إليك المثال ([https://snack.expo.dev/@hsoubwiki/linking-function-component-example-open-links-and-deep-links تجربة حية]):<syntaxhighlight lang="javascript"> | ||
import React, { useCallback } from "react"; | import React, { useCallback } from "react"; | ||
import { Alert, Button, Linking, StyleSheet, View } from "react-native"; | import { Alert, Button, Linking, StyleSheet, View } from "react-native"; | ||
سطر 128: | سطر 129: | ||
=== فتح الإعدادات الشخصية === | === فتح الإعدادات الشخصية === | ||
<syntaxhighlight lang="javascript"> | إليك المثال ([https://snack.expo.dev/@hsoubwiki/linking-function-component-example-open-custom-settings تجربة حية]):<syntaxhighlight lang="javascript"> | ||
import React, { useCallback } from "react"; | import React, { useCallback } from "react"; | ||
import { Button, Linking, StyleSheet, View } from "react-native"; | import { Button, Linking, StyleSheet, View } from "react-native"; | ||
سطر 157: | سطر 158: | ||
=== الحصول على الرابط العميق === | === الحصول على الرابط العميق === | ||
<syntaxhighlight lang="javascript"> | إليك المثال ([https://snack.expo.dev/@hsoubwiki/linking-function-component-example-get-the-deep-link تجربة حية]):<syntaxhighlight lang="javascript"> | ||
import React, { useState, useEffect } from "react"; | import React, { useState, useEffect } from "react"; | ||
import { Linking, StyleSheet, Text, View } from "react-native"; | import { Linking, StyleSheet, Text, View } from "react-native"; | ||
سطر 206: | سطر 207: | ||
</syntaxhighlight> | </syntaxhighlight> | ||
=== إرسال نية الفعل (intent) | === إرسال نية الفعل (intent) على منصة Android === | ||
<syntaxhighlight lang="javascript"> | إليك المثال ([https://snack.expo.dev/@hsoubwiki/linking-function-component-example-send-intents تجربة حية]):<syntaxhighlight lang="javascript"> | ||
import React, { useCallback } from "react"; | import React, { useCallback } from "react"; | ||
import { Alert, Button, Linking, StyleSheet, View } from "react-native"; | import { Alert, Button, Linking, StyleSheet, View } from "react-native"; | ||
سطر 250: | سطر 251: | ||
== التوابع == | == التوابع == | ||
===<code>addEventListener()</code>=== | |||
=== <code>addEventListener()</code> === | |||
<syntaxhighlight lang="javascript"> | <syntaxhighlight lang="javascript"> | ||
addEventListener(type, handler); | addEventListener(type, handler); | ||
</syntaxhighlight>يضيف معالجًا لتغيّرات الرّبط، بالتّنصّت على الحدث من نوع <code>url</code>، وتزويد المعالج. | </syntaxhighlight>يضيف معالجًا لتغيّرات الرّبط، بالتّنصّت على الحدث من نوع <code>url</code>، وتزويد المعالج. | ||
=== <code> | === <code>canOpenURL()</code> === | ||
<syntaxhighlight lang="javascript"> | <syntaxhighlight lang="javascript"> | ||
canOpenURL(url); | |||
</syntaxhighlight> | </syntaxhighlight>يقرر وجود (أو عدم وجود) تطبيقٍ على الجهاز ، يكون قادرًا على معالجة عنوان <code>url</code> المعطى. | ||
يعيد هذا التابع وعدًا <code>[[JavaScript/Promise|Promise]]</code> يقبل عندما يقرر إمكانيّة (أو عدم إمكانيّة) معالجة العنوان <code>url</code> المعطى، ويكون معامله الأول هو إمكانية فتحه، ويرفَض هذا الوعد عندما لا يكون فحص إمكانيّة فتح <code>url</code> ممكنًا، كما يُرفض على منصّة IOS، إذا لم يوضع مخطّطٌ محدّدٌ في المفتاح <code>LSApplicationQueriesSchemes</code> داخل الملف <code>Info.plist</code>. | |||
< | |||
</ | |||
'''المعاملات''': | |||
{| class="wikitable" | {| class="wikitable" | ||
!الاسم | !الاسم | ||
سطر 285: | سطر 274: | ||
|نعم | |نعم | ||
|الرابط الذي سيتم فتحه | |الرابط الذي سيتم فتحه | ||
|}''' | |}'''تنبيهات:''' | ||
* يجب وضع البروتوكول ("http://", "<nowiki>https://</nowiki>") بشكلٍ موافقٍ لعناوين URL الخاصّة بالويب. | * يجب وضع البروتوكول ("http://", "<nowiki>https://</nowiki>") بشكلٍ موافقٍ لعناوين URL الخاصّة بالويب. | ||
* | * في منصّة IOS ذات الإصدار 9، يجب وضع مخطّطٍ محدّدٍ في المفتاح <code>LSApplicationQueriesSchemes</code> داخل الملف <code>Info.plist</code>، وإلّا سيعيد هذا التابع القيمة <code>false</code> دائمًا. | ||
* يعمل هذا التابع بشكلٍ محدودٍ على منصّة IOS ذات الإصدار 9 وما بعده، حسب الموقع الرسميّ لـ [https://developer.apple.com/documentation/uikit/uiapplication/1622952-canopenurl the official Apple documentation]. | |||
* يمكن تكرار استدعاء هذا التابع حتى 50 مرّةٍ عند ربط التطبيق على إصدارات IOS الأقدم من 9، وتشغيله على الإصدار 9، وما بعده. فإذا تجاوز عدد مرات استدعائه الحدّ المسموح به، فسيعيد القيمة <code>false</code> دومًا، ويمكن تصفير الحدّ المسموح عن طريق إعادة تنصيب التّطبيق، أو تحديثه. | |||
* بدءًا من الإصدار 9 من منصة iOS، يجب أن يوفر تطبيق المفتاح <code>LSApplicationQueriesSchemes</code> داخل <code>Info.plist</code> أو سيعيد <code>canOpenURL()</code> القيمة <code>false</code> دومًا. | |||
* إن أردت استهداف منصة Android ذات الإصدار 11 (SDK 30)، فيجب أن تحدد البروتوكولات التي تنوي معالجتها داخل AndroidManifext.xml، ويمكن أن تجد قائمة كاملة بتلك النوايا intent الشائعة [https://developer.android.com/guide/components/intents-common هنا]. فمثلًا، إن أردت معالجة البروتوكول https، فيجب أن تضيف ما يلي ضمن البيان manifest. | |||
<syntaxhighlight lang="js"> | |||
<manifest ...> | |||
<queries> | |||
<intent> | |||
<action android:name="android.intent.action.VIEW" /> | |||
<data android:scheme="https"/> | |||
</intent> | |||
<queries> | |||
</manifest> | |||
</syntaxhighlight> | |||
=== <code> | ===<code>getInitialURL()</code>=== | ||
<syntaxhighlight lang="javascript"> | |||
getInitialURL(); | |||
</syntaxhighlight>يعيد هذا التابع عنوان الرابط <code>url</code>، إذا أطلِق التّطبيق عن طريق رابطه، وإلا سيعيد <code>null</code>. | |||
'''ملاحظة:''' لدعم الرّبط العميق على منصّة Android، يرجى زيارة [http://developer.android.com/training/app-indexing/deep-linking.html#handling-intents deep-linking]، على developer.android. | |||
'''ملاحظة''': قد يعيد هذا التابع القيمة <code>null</code> إن كان وضح التنقيح debugging مفعلًا، لذا تأكد من تعطيل ذلك الوضع ليعمل عملًا صحيحًا. | |||
===<code>openSettings()</code>=== | |||
<syntaxhighlight lang="javascript"> | |||
openSettings(); | |||
</syntaxhighlight>فتح تطبيق الإعدادات (Settings) لإظهار الإعدادات الشّخصيّة للتّطبيقات إن وُجدت. | |||
=== <code>openURL()</code> === | |||
<syntaxhighlight lang="javascript"> | <syntaxhighlight lang="javascript"> | ||
openURL(url); | |||
</syntaxhighlight> | </syntaxhighlight>يحاول فتح عنوان <code>url</code> المعطى بواحدٍ من التّطبيقات الموجودة. | ||
يمكن استخدام عناوين URL أخرى كموقع (مثل: "<nowiki>geo:37.484847،-122.148386</nowiki>" على منصّة Android، و"[https://www.google.com/maps/@36.72778,5.9636,10z maps.apple] " على منصّة iOS)، أو جهات الاتصال (contact)، أو أيّ عناوين يمكن فتحها بالتّطبيقات. | |||
يعيد هذا التابع وعدًا <code>[[JavaScript/Promise|Promise]]</code> يقبل | يعيد هذا التابع وعدًا <code>[[JavaScript/Promise|Promise]]</code> يقبل عند موافقة المستخدم على مربع الحوار المفتوح، أو إذا كان الرابط <code>url</code> يفتح آليًا، ويُرفض إذا ألغى المستخدم مربع الحوار، أو عند عدم وجود تطبيقٍ مُسجّلٍ للعنوان <code>url</code>. | ||
'''المعاملات''': | |||
{| class="wikitable" | {| class="wikitable" | ||
!الاسم | !الاسم | ||
سطر 309: | سطر 328: | ||
|نعم | |نعم | ||
|الرابط الذي سيتم فتحه | |الرابط الذي سيتم فتحه | ||
|}''' | |}'''تنبيهات:''' | ||
* سيفشل هذا التابع، إذا لم يعلم كيفيّة فتح عنوان URL المحدّد، لذا يجب استخدام <code>code canOpenURL@</code> عند تمرير عناوين URL ليست من نوع .http(s) | |||
* يجب وضع البروتوكول ("http://", "<nowiki>https://</nowiki>") بشكلٍ موافقٍ لعناوين URL الخاصّة بالويب. | * يجب وضع البروتوكول ("http://", "<nowiki>https://</nowiki>") بشكلٍ موافقٍ لعناوين URL الخاصّة بالويب. | ||
* | * قد يعمل هذا التابع بطريقة مختلفة على المحاكي (simulator)، فمثلًا: لا تعالج الرّوابط ":tel" على محاكي IOS بسبب عدم وجود وصولٍ إلى تطبيق الاتصال. | ||
=== | === <code>removeEventListener()</code> === | ||
<syntaxhighlight lang="javascript"> | <syntaxhighlight lang="javascript"> | ||
removeEventListener(type, handler); | |||
</syntaxhighlight> | </syntaxhighlight>يزيل المعالج بتمرير الحدث من نوع <code>url</code>، والمعالج المطلوب. | ||
'''تنبيه''': أهمل هذا التابع، لذا استعمل التابع <code>remove()</code> مع إشتراك الحدث الذي يعيده التابع <code>addEventListener()</code>. | |||
< | |||
=== <code>sendIntent()</code> === | |||
=== | |||
<syntaxhighlight lang="javascript"> | <syntaxhighlight lang="javascript"> | ||
sendIntent(action: string, extras?: Array<{key: string, value: string | number | boolean}>) | sendIntent(action: string, extras?: Array<{key: string, value: string | number | boolean}>) | ||
</syntaxhighlight | </syntaxhighlight>يعمل على منصّة Android فقط، ويستخدم لإطلاق نيّة الفعل (intent) مع الإضافات (اختيارية). | ||
'''المعاملات''': | |||
{| class="wikitable" | |||
!الاسم | |||
!النوع | |||
!مطلوب | |||
|- | |||
|<code>action</code> | |||
|سلسلة نصية (string) | |||
|نعم | |||
|- | |||
|<code>extras</code> | |||
|مصفوفة من: | |||
{key: string, value: string \| number \| boolean} | |||
|لا | |||
|} | |||
== مصادر == | == مصادر == | ||
* [https://facebook.github.io/react-native/docs/linking صفحة Linking في توثيق React Native الرسميّ] | * [https://facebook.github.io/react-native/docs/linking صفحة Linking في توثيق React Native الرسميّ] | ||
[[تصنيف:ReactNative]] | [[تصنيف:ReactNative]] | ||
[[تصنيف:React Native API]] |
المراجعة الحالية بتاريخ 14:13، 9 أكتوبر 2021
خاصٌ بالمشاريع المكتوبة بشفرة Native
تطبّق هذه المقالة على المشاريع المكتوبة بشفرة Native فقط؛ أمّا عند استخدام سير العمل
expo-cli
، فيمكن الاطّلاع على الدّليل Linking ضمن توثيق Expo لإيجاد البديل الملائم.
تُقدّم الواجهة Linking
واجهةً عامّةً للتّفاعل مع الرّوابط الواردة، والصّادرة للتّطبيقات، ولكل رابط (URL) نوع يحدد ببادئة الرابط (يطلق عليه أحيانًا تخطيط العنوان أو URL schema)، مثل: البادئة http
، أو https
في عنوان الموقع، كما يوجد رابط mailto
، الذي يقوم نظام التّشغيل -عند فتح رابطٍ يحويه- بفتح تطبيق البريد الإكترونيّ المنصّب على الجهاز، كما توجد روابط للاتّصال الهاتفيّ، وإرسال الرّسائل النّصّيّة، ستُشرح أنواع الرّوابط الضّمنيّة built-in URL لاحقًا بالتّفصيل.
يمكن الرّبط مع التّطبيقات الأخرى -بشكلٍ مماثلٍ للرابط mailto
- باستخدام نوع URL
المخصصة، مثلًا: عند استلام البريد الإلكتروني Magic Link من تطبيق Slack سيكون المفتاح Launch Slack هو وسم الربط (anchor tag)، والذي يتضمّن رابطًا مرجعيّا فائقًا (href) له الشّكل التّالي: slack://secret/magic-login/other-secret
يمكننا إخبار نظام التّشغيل بأننا نريد معالجة مخطط مخصّص كما في Slack، عند فتح تطبيق Slack فإنّه يستقبل الرّابط المُستخدَم في فتحه، ويمكن بنفس الطّريقة ربط أيّ تطبيقٍ باستخدام المخطّطات المخصّصة، وهو ما يسمى بالرّبط العميق (deep linking) والذي سيُشرح لاحقًا بالتّفصيل.
روابط URL المخصصة ليست الطّريقة الوحيدة لفتح التّطبيقات على الهاتف المحمول، حيث يفضّل عدم استخدمها مع روابط البريد الإلكتروني لأن ذلك سيؤدّي إلى تعطيلها على سطح المكتب، لكن يمكن استخدامها مع روابط https
الاعتياديّة، مثل: https://www.myapp.io/records/1234546
يستخدم هذا الرّابط لفتح تطبيقٍ ما على الهاتف المحمول، وتدعى هذه الرّوابط بالروابط العميقة (Deep Links) على منصّة Android؛ أمّا على منصّة iOS فتدعى بالرّوابط الشّاملة (Universal Links).
مخططات الروابط الضمنية
إنّ هذه المخطّطات من الوظائف الأساسيّة، وتتوافر في الأنظمة كلّها، وأكثرها استخدامًا:
نوع الرابط | الوصف | iOS | Android |
---|---|---|---|
mailto
|
فتح تطبيق البريد الإلكتروني، مثل : mailto:support@expo.io | ✅ | ✅ |
tel
|
فتح نافذة الاتصال للاتصال بالرقم المعطى، مثل: tel:+123456789 | ✅ | ✅ |
sms
|
فتح تطبيق الرسائل النصية، مثل: sms:+123456789 | ✅ | ✅ |
https / http
|
فتح متصفح الويب مثل: https://expo.io | ✅ | ✅ |
تفعيل الروابط العميقة
على منصة Android
لمعرفة كيفيّة دعم الرّبط العميق على منصّة Android يمكن زيارة تفعيل الروابط العميقة لمحتوى التطبيق - إضافة الفلاتر إليها.
عند الرّغبة باستقبال نيّة الفعل (intent) على النسخة الموجودة من MainActivity، يجب ضبط launchMode
الخاصّ بنسخة MainActivity للقيمة singleTask
في AndroidManifest.xml
، ويمكن الاطّلاع على <activity> لمزيدٍ من المعلومات.
<activity
android:name=".MainActivity"
android:launchMode="singleTask">
على منصة IOS
ملاحظة: يجب ربط RCTLinking
مع المشروع وفق الخطوات المشروحة هنا، ويجب إضافة السّطور البرمجيّة التاليّة للملف *AppDelegate.m
عند الرغبة بالتّنصّت على روابط التّطبيق الواردة أثناء فترة عمل هذا التّطبيق :
// iOS 9.x or newer
#import <React/RCTLinkingManager.h>
- (BOOL)application:(UIApplication *)application
openURL:(NSURL *)url
options:(NSDictionary<UIApplicationOpenURLOptionsKey,id> *)options
{
return [RCTLinkingManager application:application openURL:url options:options];
}
أمّا في منصّة IOS ذات الإصدار 8.x، أو الأقدم منه، فتستخدم السّطور البرمجيّة التّالية عوضًا عن الأسطر السّابقة:
// iOS 8.x or older
#import <React/RCTLinkingManager.h>
- (BOOL)application:(UIApplication *)application openURL:(NSURL *)url
sourceApplication:(NSString *)sourceApplication annotation:(id)annotation
{
return [RCTLinkingManager application:application openURL:url
sourceApplication:sourceApplication annotation:annotation];
}
يجب إضافة السّطور البرمجيّة التّالية أيضًا، إذا استخدم التطبيق الرّوابط الشّاملة (Universal Links):
- (BOOL)application:(UIApplication *)application continueUserActivity:(nonnull NSUserActivity *)userActivity
restorationHandler:(nonnull void (^)(NSArray<id<UIUserActivityRestoring>> * _Nullable))restorationHandler
{
return [RCTLinkingManager application:application
continueUserActivity:userActivity
restorationHandler:restorationHandler];
}
معالجة الروابط العميقة
تعالَج الرّوابط URL التي تفتح التّطبيقات بطريقتين:
- إذا كان التّطبيق مفتوحًا مسبقًا، فإنه يُجلَب للواجهة، ويُطلق حدث الربط، باستخدام التّابع .
Linking.addEventListener(url, callback)
- إذا كان التطبيق يفتَح للمرّة الأولى، فإنّه يُفتح، ويُمرَّر الرّابط url كرابطٍ مبدئيٍّ
InitialURL
، باستخدام التّابع()Linking.getInitialURL
الذي يعيد وعداً (Promise) يُقبل كرابط url -عند وجوده-.
مثال
فتح الروابط الضمنية والعميقة (والشاملة)
إليك المثال (تجربة حية):
import React, { useCallback } from "react";
import { Alert, Button, Linking, StyleSheet, View } from "react-native";
const supportedURL = "https://google.com";
const unsupportedURL = "slack://open?team=123456";
const OpenURLButton = ({ url, children }) => {
const handlePress = useCallback(async () => {
// Checking if the link is supported for links with custom URL scheme.
const supported = await Linking.canOpenURL(url);
if (supported) {
// Opening the link with some app, if the URL scheme is "http" the web link should be opened
// by some browser in the mobile
await Linking.openURL(url);
} else {
Alert.alert(`Don't know how to open this URL: ${url}`);
}
}, [url]);
return <Button title={children} onPress={handlePress} />;
};
const App = () => {
return (
<View style={styles.container}>
<OpenURLButton url={supportedURL}>Open Supported URL</OpenURLButton>
<OpenURLButton url={unsupportedURL}>Open Unsupported URL</OpenURLButton>
</View>
);
};
const styles = StyleSheet.create({
container: { flex: 1, justifyContent: "center", alignItems: "center" },
});
export default App;
فتح الإعدادات الشخصية
إليك المثال (تجربة حية):
import React, { useCallback } from "react";
import { Button, Linking, StyleSheet, View } from "react-native";
const OpenSettingsButton = ({ children }) => {
const handlePress = useCallback(async () => {
// Open the custom settings if the app has one
await Linking.openSettings();
}, []);
return <Button title={children} onPress={handlePress} />;
};
const App = () => {
return (
<View style={styles.container}>
<OpenSettingsButton>Open Settings</OpenSettingsButton>
</View>
);
};
const styles = StyleSheet.create({
container: { flex: 1, justifyContent: "center", alignItems: "center" },
});
export default App;
الحصول على الرابط العميق
إليك المثال (تجربة حية):
import React, { useState, useEffect } from "react";
import { Linking, StyleSheet, Text, View } from "react-native";
const useMount = func => useEffect(() => func(), []);
const useInitialURL = () => {
const [url, setUrl] = useState(null);
const [processing, setProcessing] = useState(true);
useMount(() => {
const getUrlAsync = async () => {
// Get the deep link used to open the app
const initialUrl = await Linking.getInitialURL();
// The setTimeout is just for testing purpose
setTimeout(() => {
setUrl(initialUrl);
setProcessing(false);
}, 1000);
};
getUrlAsync();
});
return { url, processing };
};
const App = () => {
const { url: initialUrl, processing } = useInitialURL();
return (
<View style={styles.container}>
<Text>
{processing
? `Processing the initial url from a deep link`
: `The deep link is: ${initialUrl || "None"}`}
</Text>
</View>
);
};
const styles = StyleSheet.create({
container: { flex: 1, justifyContent: "center", alignItems: "center" },
});
export default App;
إرسال نية الفعل (intent) على منصة Android
إليك المثال (تجربة حية):
import React, { useCallback } from "react";
import { Alert, Button, Linking, StyleSheet, View } from "react-native";
const SendIntentButton = ({ action, extras, children }) => {
const handlePress = useCallback(async () => {
try {
await Linking.sendIntent(action, extras);
} catch (e) {
Alert.alert(e.message);
}
}, [action, extras]);
return <Button title={children} onPress={handlePress} />;
};
const App = () => {
return (
<View style={styles.container}>
<SendIntentButton action="android.intent.action.POWER_USAGE_SUMMARY">
Power Usage Summary
</SendIntentButton>
<SendIntentButton
action="android.settings.APP_NOTIFICATION_SETTINGS"
extras={[
{ "android.provider.extra.APP_PACKAGE": "com.facebook.katana" },
]}
>
App Notification Settings
</SendIntentButton>
</View>
);
};
const styles = StyleSheet.create({
container: { flex: 1, justifyContent: "center", alignItems: "center" },
});
export default App;
التوابع
addEventListener()
addEventListener(type, handler);
يضيف معالجًا لتغيّرات الرّبط، بالتّنصّت على الحدث من نوع url
، وتزويد المعالج.
canOpenURL()
canOpenURL(url);
يقرر وجود (أو عدم وجود) تطبيقٍ على الجهاز ، يكون قادرًا على معالجة عنوان url
المعطى.
يعيد هذا التابع وعدًا Promise
يقبل عندما يقرر إمكانيّة (أو عدم إمكانيّة) معالجة العنوان url
المعطى، ويكون معامله الأول هو إمكانية فتحه، ويرفَض هذا الوعد عندما لا يكون فحص إمكانيّة فتح url
ممكنًا، كما يُرفض على منصّة IOS، إذا لم يوضع مخطّطٌ محدّدٌ في المفتاح LSApplicationQueriesSchemes
داخل الملف Info.plist
.
المعاملات:
الاسم | النوع | مطلوب | الوصف |
---|---|---|---|
url
|
سلسلة نصية (string) | نعم | الرابط الذي سيتم فتحه |
تنبيهات:
- يجب وضع البروتوكول ("http://", "https://") بشكلٍ موافقٍ لعناوين URL الخاصّة بالويب.
- في منصّة IOS ذات الإصدار 9، يجب وضع مخطّطٍ محدّدٍ في المفتاح
LSApplicationQueriesSchemes
داخل الملفInfo.plist
، وإلّا سيعيد هذا التابع القيمةfalse
دائمًا. - يعمل هذا التابع بشكلٍ محدودٍ على منصّة IOS ذات الإصدار 9 وما بعده، حسب الموقع الرسميّ لـ the official Apple documentation.
- يمكن تكرار استدعاء هذا التابع حتى 50 مرّةٍ عند ربط التطبيق على إصدارات IOS الأقدم من 9، وتشغيله على الإصدار 9، وما بعده. فإذا تجاوز عدد مرات استدعائه الحدّ المسموح به، فسيعيد القيمة
false
دومًا، ويمكن تصفير الحدّ المسموح عن طريق إعادة تنصيب التّطبيق، أو تحديثه. - بدءًا من الإصدار 9 من منصة iOS، يجب أن يوفر تطبيق المفتاح
LSApplicationQueriesSchemes
داخلInfo.plist
أو سيعيدcanOpenURL()
القيمةfalse
دومًا. - إن أردت استهداف منصة Android ذات الإصدار 11 (SDK 30)، فيجب أن تحدد البروتوكولات التي تنوي معالجتها داخل AndroidManifext.xml، ويمكن أن تجد قائمة كاملة بتلك النوايا intent الشائعة هنا. فمثلًا، إن أردت معالجة البروتوكول https، فيجب أن تضيف ما يلي ضمن البيان manifest.
<manifest ...>
<queries>
<intent>
<action android:name="android.intent.action.VIEW" />
<data android:scheme="https"/>
</intent>
<queries>
</manifest>
getInitialURL()
getInitialURL();
يعيد هذا التابع عنوان الرابط url
، إذا أطلِق التّطبيق عن طريق رابطه، وإلا سيعيد null
.
ملاحظة: لدعم الرّبط العميق على منصّة Android، يرجى زيارة deep-linking، على developer.android.
ملاحظة: قد يعيد هذا التابع القيمة null
إن كان وضح التنقيح debugging مفعلًا، لذا تأكد من تعطيل ذلك الوضع ليعمل عملًا صحيحًا.
openSettings()
openSettings();
فتح تطبيق الإعدادات (Settings) لإظهار الإعدادات الشّخصيّة للتّطبيقات إن وُجدت.
openURL()
openURL(url);
يحاول فتح عنوان url
المعطى بواحدٍ من التّطبيقات الموجودة.
يمكن استخدام عناوين URL أخرى كموقع (مثل: "geo:37.484847،-122.148386" على منصّة Android، و"maps.apple " على منصّة iOS)، أو جهات الاتصال (contact)، أو أيّ عناوين يمكن فتحها بالتّطبيقات.
يعيد هذا التابع وعدًا Promise
يقبل عند موافقة المستخدم على مربع الحوار المفتوح، أو إذا كان الرابط url
يفتح آليًا، ويُرفض إذا ألغى المستخدم مربع الحوار، أو عند عدم وجود تطبيقٍ مُسجّلٍ للعنوان url
.
المعاملات:
الاسم | النوع | مطلوب | الوصف |
---|---|---|---|
url
|
سلسلة نصية (string) | نعم | الرابط الذي سيتم فتحه |
تنبيهات:
- سيفشل هذا التابع، إذا لم يعلم كيفيّة فتح عنوان URL المحدّد، لذا يجب استخدام
code canOpenURL@
عند تمرير عناوين URL ليست من نوع .http(s) - يجب وضع البروتوكول ("http://", "https://") بشكلٍ موافقٍ لعناوين URL الخاصّة بالويب.
- قد يعمل هذا التابع بطريقة مختلفة على المحاكي (simulator)، فمثلًا: لا تعالج الرّوابط ":tel" على محاكي IOS بسبب عدم وجود وصولٍ إلى تطبيق الاتصال.
removeEventListener()
removeEventListener(type, handler);
يزيل المعالج بتمرير الحدث من نوع url
، والمعالج المطلوب.
تنبيه: أهمل هذا التابع، لذا استعمل التابع remove()
مع إشتراك الحدث الذي يعيده التابع addEventListener()
.
sendIntent()
sendIntent(action: string, extras?: Array<{key: string, value: string | number | boolean}>)
يعمل على منصّة Android فقط، ويستخدم لإطلاق نيّة الفعل (intent) مع الإضافات (اختيارية).
المعاملات:
الاسم | النوع | مطلوب |
---|---|---|
action
|
سلسلة نصية (string) | نعم |
extras
|
مصفوفة من:
{key: string, value: string \| number \| boolean} |
لا |