أساسيات تقنية NFC

يصف هذا المستند مهام NFC الأساسية التي تؤديها في Android. وهي تشرح طريقة إرسال بيانات NFC واستقبالها في شكل رسائل NDEF وتصف واجهات برمجة تطبيقات إطار عمل Android التي تتوافق مع هذه الميزات. للاطّلاع على مواضيع أكثر تقدمًا، بما في ذلك مناقشة استخدام بيانات غير تابعة لـ NDEF، يمكنك مراجعة تقنية الاتصال القصير المدى (NFC) المتقدمة.

هناك حالتا استخدام رئيسيتان عند التعامل مع بيانات NDEF وAndroid:

  • قراءة بيانات NDEF من علامة NFC
  • إرسال رسائل NDEF من جهاز إلى آخر باستخدام Android BeamTM

تتم معالجة قراءة بيانات NDEF من علامة NFC باستخدام نظام إرسال العلامات الذي يحلّل علامات NFC التي تم اكتشافها ويصنّف البيانات بشكل مناسب ثم يبدأ تشغيل تطبيق مهتم بالبيانات المصنَّفة. ويمكن للتطبيق الذي يريد التعامل مع علامة NFC التي تم فحصها الإعلان عن فلتر الأهداف وطلب معالجة البيانات.

تسمح ميزة Android BeamTM للجهاز بإرسال رسالة NDEF على جهاز آخر من خلال التلامس بين الجهازين معًا. يوفّر هذا التفاعل طريقة أسهل لإرسال البيانات مقارنةً بالتقنيات اللاسلكية الأخرى مثل البلوتوث، لأنه باستخدام تقنية NFC، لا حاجة إلى اكتشاف الجهاز أو إقرانه يدويًا. يبدأ الاتصال تلقائيًا عندما يصل جهازان إلى النطاق. يتوفر شعاع Android من خلال مجموعة من واجهات برمجة تطبيقات NFC، وبالتالي يمكن لأي تطبيق نقل المعلومات بين الأجهزة. على سبيل المثال، تستخدم تطبيقات جهات الاتصال والمتصفح وYouTube شعاع Android لمشاركة جهات الاتصال وصفحات الويب ومقاطع الفيديو مع الأجهزة الأخرى.

نظام إرسال العلامات

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

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

  1. تحليل علامة NFC وتحديد نوع MIME أو معرّف الموارد المنتظم (URI) الذي يعرّف حمولة البيانات في العلامة.
  2. تغليف نوع MIME أو عنوان URI والحمولة في هدف ما. ويمكنك الاطّلاع على هاتين الخطوتَين في القسم كيفية ربط علامات NFC بأنواع MIME وعناوين URL.
  3. بدء نشاط بناءً على الغرض يمكنك الاطّلاع على مزيد من التفاصيل في القسم طريقة إرسال علامات NFC إلى التطبيقات.

كيفية ربط علامات NFC بأنواع MIME وURI

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

يتم تضمين بيانات NDEF داخل رسالة (NdefMessage) تحتوي على سجل واحد أو أكثر (NdefRecord). يجب أن يكون كل سجل NDEF صحيحًا وفقًا لمواصفات نوع السجل الذي تريد إنشاءه. يتيح Android أيضًا استخدام أنواع أخرى من العلامات التي لا تحتوي على بيانات NDEF، ويمكنك التعامل معها باستخدام الفئات المتوفّرة في حزمة android.nfc.tech. لمزيد من المعلومات حول هذه التقنيات، يُرجى الاطّلاع على موضوع تقنية الاتصال القصير المدى (NFC) المتقدمة. يتضمّن العمل باستخدام هذه الأنواع الأخرى من العلامات كتابة حزمة البروتوكول الخاصة بك للتواصل مع العلامات، لذلك ننصح باستخدام NDEF عندما يكون ذلك ممكنًا لسهولة التطوير والحصول على أقصى دعم ممكن للأجهزة التي تعمل بنظام التشغيل Android.

ملاحظة: لتنزيل مواصفات NDEF الكاملة، يمكنك الانتقال إلى الموقع الإلكتروني مواصفات منتدى NDEF والاطِّلاع على مقالة إنشاء أنواع شائعة من سجلات NDEF للاطّلاع على أمثلة حول كيفية إنشاء سجلات NDEF.

الآن وبعد أن أصبح لديك بعض المعلومات الأساسية عن علامات NFC، ستصف الأقسام التالية بمزيد من التفصيل كيفية تعامل Android مع علامات NDEF المنسقة. عندما يفحص جهاز يعمل بنظام التشغيل Android علامة NFC تحتوي على بيانات بتنسيق NDEF، يحلّل الرسالة ويحاول تحديد نوع MIME للبيانات أو معرّف الموارد المنتظم (URI) للبيانات. لإجراء ذلك، يقرأ النظام أول NdefRecord داخل NdefMessage لتحديد كيفية تفسير رسالة NDEF بأكملها (يمكن أن تحتوي رسالة NDEF على سجلات NDEF متعددة). في رسالة NDEF جيدة الصياغة، يحتوي أول NdefRecord على الحقول التالية:

3 بت TNF (تنسيق اسم النوع)
يشير إلى كيفية تفسير حقل نوع متغير الطول. يتم وصف القيم الصالحة في الجدول 1.
نوع الطول المتغيّر
يصف هذا الحقل نوع السجلّ. في حال استخدام TNF_WELL_KNOWN، استخدِم هذا الحقل لتحديد "تعريف نوع السجلّ" (RTD). يتم توضيح قيم RTD الصالحة في الجدول 2.
رقم تعريف الطول المتغيّر
معرّف فريد للسجلّ. لا يتم استخدام هذا الحقل كثيرًا، ولكن إذا كنت بحاجة إلى تعريف علامة بشكلٍ فريد، يمكنك إنشاء معرِّف لها.
حمولة متغيرة الطول
حمولة البيانات الفعلية التي تريد قراءتها أو كتابتها يمكن أن تحتوي رسالة NDEF على عدة سجلات NDEF، لذا لا تفترض أن الحمولة الكاملة موجودة في سجل NDEF الأول لرسالة NDEF.

يستخدِم نظام إرسال العلامات حقول TNF والنوع لمحاولة ربط نوع MIME أو معرّف موارد منتظم (URI) لرسالة NDEF. في حال نجاح هذا الإجراء، يتم تضمين هذه المعلومات داخل الغرض ACTION_NDEF_DISCOVERED مع الحمولة الفعلية. ومع ذلك، هناك حالات لا يتمكن فيها نظام إرسال العلامات من تحديد نوع البيانات استنادًا إلى سجل NDEF الأول. ويحدث ذلك عندما يتعذّر ربط بيانات NDEF بنوع MIME أو معرّف موارد منتظم (URI)، أو عندما لا تحتوي علامة NFC على بيانات NDEF لتبدأ بها. وفي مثل هذه الحالات، يتم تضمين كائن Tag الذي يحتوي على معلومات حول تقنيات العلامة والحمولة في هدف ACTION_TECH_DISCOVERED بدلاً من ذلك.

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

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

الجدول 1. أرقام TNF المتوافقة وعمليات ربطها

اكتب تنسيق الاسم (TNF) تعيين
TNF_ABSOLUTE_URI معرّف موارد منتظم (URI) استنادًا إلى حقل النوع.
TNF_EMPTY يعود إلى ACTION_TECH_DISCOVERED.
TNF_EXTERNAL_TYPE معرّف موارد منتظم (URI) استنادً إلى رقم URN في حقل النوع. يتم ترميز رقم URN في حقل النوع NDEF بشكل مختصر: <domain_name>:<service_name>. يربط Android هذا معرّف الموارد المنتظم (URI) بالصيغة: vnd.android.nfc://ext/<domain_name>:<service_name>.
TNF_MIME_MEDIA نوع MIME استنادًا إلى حقل النوع.
TNF_UNCHANGED غير صالح في السجل الأول، لذا سيتم الرجوع إلى ACTION_TECH_DISCOVERED.
TNF_UNKNOWN يعود إلى ACTION_TECH_DISCOVERED.
TNF_WELL_KNOWN نوع MIME أو معرف الموارد المنتظم (URI) استنادًا إلى تعريف نوع السجل (RTD)، الذي تعيّنه في حقل النوع. يُرجى الاطّلاع على الجدول 2 للحصول على مزيد من المعلومات حول مواعيد التسليم المقدَّرة المتاحة وعمليات الربط الخاصة بها.

الجدول 2. ملفات RTD المتوافقة مع TNF_WELL_KNOWN والتعيينات التابعة لها

تعريف نوع السجلّ (RTD) تعيين
RTD_ALTERNATIVE_CARRIER يعود إلى ACTION_TECH_DISCOVERED.
RTD_HANDOVER_CARRIER يعود إلى ACTION_TECH_DISCOVERED.
RTD_HANDOVER_REQUEST يعود إلى ACTION_TECH_DISCOVERED.
RTD_HANDOVER_SELECT يعود إلى ACTION_TECH_DISCOVERED.
RTD_SMART_POSTER معرّف الموارد المنتظم (URI) الذي يستند إلى تحليل الحمولة.
RTD_TEXT text/plain نوع MIME.
RTD_URI معرّف موارد منتظم (URI) استنادا إلى الحمولة.

كيفية إرسال علامات NFC إلى التطبيقات

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

  1. ACTION_NDEF_DISCOVERED: يُستخدم هذا الغرض لبدء نشاط عندما يتم فحص علامة تحتوي على حمولة NDEF وتكون من نوع معروف. ويمثل هذا الهدف أولوية قصوى، ويحاول نظام إرسال العلامات بدء نشاط بهذا الهدف قبل أي هدف آخر، كلما أمكن ذلك.
  2. ACTION_TECH_DISCOVERED: إذا لم يتمّ تسجيل أي أنشطة لمعالجة هدف ACTION_NDEF_DISCOVERED، يحاول نظام إرسال العلامات بدء تطبيق بهذا الغرض. يبدأ هذا الهدف أيضًا مباشرةً (بدون البدء بـ ACTION_NDEF_DISCOVERED أولاً) إذا كانت العلامة التي يتم مسحها ضوئيًا تحتوي على بيانات NDEF لا يمكن ربطها بنوع MIME أو معرّف موارد منتظم (URI)، أو إذا كانت العلامة لا تحتوي على بيانات NDEF ولكنها تشكّل تكنولوجيا علامات معروفة.
  3. ACTION_TAG_DISCOVERED: يبدأ هذا الغرض إذا لم تعالج أي أنشطة الغرض من ACTION_NDEF_DISCOVERED أو ACTION_TECH_DISCOVERED.

في ما يلي الطريقة الأساسية التي يعمل بها نظام إرسال العلامات:

  1. حاوِل بدء نشاط بقصد الذي أنشأه نظام إرسال العلامات عند تحليل علامة NFC (إما ACTION_NDEF_DISCOVERED أو ACTION_TECH_DISCOVERED).
  2. في حال عدم فلترة أي أنشطة لهذا الغرض، حاوِل بدء نشاط ذي أولوية أدنى تالية (إما ACTION_TECH_DISCOVERED أو ACTION_TAG_DISCOVERED) إلى أن يفلتر أحد التطبيقات الغرض أو إلى أن يجرِّب نظام إرسال العلامة كل الأغراض الممكنة.
  3. وفي حال عدم فلترة أي تطبيقات لأيٍّ من الأغراض، لا تتخذ أي إجراء.
الشكل 1. نظام إرسال العلامات

كلّما أمكن، استخدِم رسائل NDEF وهدف ACTION_NDEF_DISCOVERED، لأنّه الأكثر تحديدًا من بين هذه السمات الثلاث. يسمح لك هذا الغرض ببدء تطبيقك في وقت أكثر ملاءمة من الهدفين الآخرين، ما يمنح المستخدم تجربة أفضل.

طلب الوصول إلى NFC في ملف بيان Android

قبل أن تتمكن من الوصول إلى جهاز NFC على جهازك والتعامل مع أهداف الاتصال القصير المدى (NFC) بشكلٍ صحيح، يُرجى توضيح العناصر التالية في ملف AndroidManifest.xml:

  • عنصر NFC <uses-permission> للوصول إلى جهاز NFC:
    <uses-permission android:name="android.permission.NFC" />
    
  • تمثّل هذه السمة الحد الأدنى لإصدار حزمة تطوير البرامج (SDK) الذي يمكن أن يتوافق مع تطبيقك. يتيح المستوى 9 من واجهة برمجة التطبيقات إرسال علامات بشكل محدود من خلال ACTION_TAG_DISCOVERED فقط، ويتيح الوصول إلى رسائل NDEF من خلال عنصر EXTRA_NDEF_MESSAGES الإضافي. ولا يمكن الوصول إلى خصائص العلامات الأخرى أو عمليات وحدات الإدخال والإخراج. ويشمل المستوى 10 من واجهة برمجة التطبيقات دعمًا شاملاً للقارئ/الكتّاب بالإضافة إلى إرسال حزمة NDEF في المقدّمة، كما يوفّر المستوى 14 من واجهة برمجة التطبيقات طريقة أسهل لإرسال رسائل NDEF إلى الأجهزة الأخرى باستخدام شعاع Android وطرق ملائمة إضافية لإنشاء سجلات NDEF.
    <uses-sdk android:minSdkVersion="10"/>
    
  • العنصر uses-feature الذي لكي يظهر تطبيقك في Google Play فقط على الأجهزة التي تحتوي على أجهزة NFC:
    <uses-feature android:name="android.hardware.nfc" android:required="true" />
    

    إذا كان تطبيقك يستخدم وظيفة NFC ولكن هذه الوظيفة غير بالغة الأهمية لتطبيقك، يمكنك حذف العنصر uses-feature والتحقّق من مدى توفّر NFC في وقت التشغيل من خلال التأكد مما إذا كان getDefaultAdapter() هو null.

فلتر لأهداف الاتصال القصير المدى (NFC)

لبدء تطبيقك عندما يتم مسح علامة NFC التي تريد التعامل معها، يمكن للتطبيق الفلترة للعثور على هدف واحد أو اثنتين أو جميع أهداف NFC الثلاثة في ملف بيان Android. ومع ذلك، عادةً ما تريد الفلترة للوصول إلى الغرض من ACTION_NDEF_DISCOVERED للوصول إلى أكبر قدر من التحكّم في وقت بدء تشغيل التطبيق. الغرض ACTION_TECH_DISCOVERED هو عنصر احتياطي في ACTION_NDEF_DISCOVERED عند عدم فلترة التطبيقات للسمة ACTION_NDEF_DISCOVERED أو عندما لا تكون الحمولة NDEF. عادةً ما تكون تصفية ACTION_TAG_DISCOVERED عامة جدًا لفئة بحيث لا يمكن الفلترة وفقًا لها. تُجري العديد من التطبيقات الفلترة حسب ACTION_NDEF_DISCOVERED أو ACTION_TECH_DISCOVERED قبل ACTION_TAG_DISCOVERED، لذا من المحتمل أن يبدأ تطبيقك ضعيفًا. لا يتوفّر ACTION_TAG_DISCOVERED إلا كحلٍ أخير للتطبيقات للفلترة في الحالات التي لم يتم فيها تثبيت تطبيقات أخرى للتعامل مع الغرض من ACTION_NDEF_DISCOVERED أو ACTION_TECH_DISCOVERED.

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

تم اكتشاف ACTION_NDEF_DISCOVERED

لفلترة أغراض ACTION_NDEF_DISCOVERED، حدِّد فلتر النية مع نوع البيانات التي تريد الفلترة للحصول عليها. إليك أمثلة فلاتر على أغراض ACTION_NDEF_DISCOVERED باستخدام نوع MIME text/plain:

<intent-filter>
    <action android:name="android.nfc.action.NDEF_DISCOVERED"/>
    <category android:name="android.intent.category.DEFAULT"/>
    <data android:mimeType="text/plain" />
</intent-filter>

يعرض المثال التالي فلاتر لعنوان URL على شكل https://developer.android.com/index.html.

<intent-filter>
    <action android:name="android.nfc.action.NDEF_DISCOVERED"/>
    <category android:name="android.intent.category.DEFAULT"/>
   <data android:scheme="https"
              android:host="developer.android.com"
              android:pathPrefix="/index.html" />
</intent-filter>

تم اكتشافه

إذا كان نشاطك يفلتر الغرض ACTION_TECH_DISCOVERED، عليك إنشاء ملف مورد XML يحدد التقنيات التي يتيحها نشاطك ضمن مجموعة tech-list. ويُعتبر نشاطك مطابقًا إذا كانت مجموعة tech-list هي مجموعة فرعية من التكنولوجيات المتوافقة مع العلامة، والتي يمكنك الحصول عليها من خلال طلب getTechList().

على سبيل المثال، إذا كانت العلامة التي يتم فحصها متوافقة مع Mifare Classic وNdefFormatable وNfcA، يجب أن تحدد مجموعة tech-list جميع التقنيات الثلاث أو اثنين أو إحدى التقنيات (وليس أي شيء آخر) لكي تتم مطابقة نشاطك.

يحدد النموذج التالي جميع التقنيات. يجب إزالة التطبيقات التي لا تتوافق مع علامة NFC. احفظ هذا الملف (يمكنك تسميته كما تريد) في مجلد <project-root>/res/xml.

<resources xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
    <tech-list>
        <tech>android.nfc.tech.IsoDep</tech>
        <tech>android.nfc.tech.NfcA</tech>
        <tech>android.nfc.tech.NfcB</tech>
        <tech>android.nfc.tech.NfcF</tech>
        <tech>android.nfc.tech.NfcV</tech>
        <tech>android.nfc.tech.Ndef</tech>
        <tech>android.nfc.tech.NdefFormatable</tech>
        <tech>android.nfc.tech.MifareClassic</tech>
        <tech>android.nfc.tech.MifareUltralight</tech>
    </tech-list>
</resources>

يمكنك أيضًا تحديد مجموعات tech-list متعددة. تُعدّ كل مجموعة من مجموعات tech-list مستقلة، ويُعتبر نشاطك مطابقًا إذا كانت أي مجموعة tech-list فردية عبارة عن مجموعة فرعية من التقنيات التي يعرضها getTechList(). يوفّر ذلك دلالات AND وOR لتقنيات المطابقة. يتطابق المثال التالي مع العلامات التي يمكن أن تتيح استخدام تقنيتَي NfcA وNdef أو التي يمكنها التوافق مع تقنيات NfcB وNdef:

<resources xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
    <tech-list>
        <tech>android.nfc.tech.NfcA</tech>
        <tech>android.nfc.tech.Ndef</tech>
    </tech-list>
    <tech-list>
        <tech>android.nfc.tech.NfcB</tech>
        <tech>android.nfc.tech.Ndef</tech>
    </tech-list>
</resources>

في ملف AndroidManifest.xml، حدِّد ملف المورد الذي أنشأته للتو في العنصر <meta-data> داخل العنصر <activity>، كما في المثال التالي:

<activity>
...
<intent-filter>
    <action android:name="android.nfc.action.TECH_DISCOVERED"/>
</intent-filter>

<meta-data android:name="android.nfc.action.TECH_DISCOVERED"
    android:resource="@xml/nfc_tech_filter" />
...
</activity>

لمزيد من المعلومات حول استخدام تقنيات العلامات وهدف ACTION_TECH_DISCOVERED، يُرجى الاطّلاع على التعامل مع تقنيات العلامات المتوافقة في مستند تقنية NFC المتقدّمة.

تم اكتشاف ACTION_TAG_

للفلترة حسب ACTION_TAG_DISCOVERED، استخدِم فلتر الأهداف التالي:

<intent-filter>
    <action android:name="android.nfc.action.TAG_DISCOVERED"/>
</intent-filter>

الحصول على معلومات من الأغراض

إذا بدأ النشاط بسبب النية من استخدام NFC، يمكنك الحصول على معلومات عن علامة NFC التي تم مسحها ضوئيًا من الهدف. يمكن أن تحتوي ملفات Intent على العناصر الإضافية التالية بناءً على العلامة التي تم فحصها:

  • EXTRA_TAG (مطلوب): كائن Tag يمثل العلامة الممسوحة ضوئيًا.
  • EXTRA_NDEF_MESSAGES (اختياري): صفيف من رسائل NDEF تم تحليلها من العلامة. إنّ هذه السمة الإضافية إلزامية في ACTION_NDEF_DISCOVERED أغراض.
  • EXTRA_ID (اختياري): رقم تعريف العلامة ذو المستوى المنخفض.

للحصول على هذه العناصر الإضافية، يُرجى التحقق ممّا إذا كان قد تم إطلاق نشاطك باستخدام إحدى غايات NFC لضمان مسح العلامة ضوئيًا، ثم الحصول على العناصر الإضافية بالاستناد إلى النية. يتحقّق المثال التالي من الغرض ACTION_NDEF_DISCOVERED ويحصل على رسائل NDEF من عنصر intent إضافي.

لغة Kotlin

override fun onNewIntent(intent: Intent) {
    super.onNewIntent(intent)
    ...
    if (NfcAdapter.ACTION_NDEF_DISCOVERED == intent.action) {
        intent.getParcelableArrayExtra(NfcAdapter.EXTRA_NDEF_MESSAGES)?.also { rawMessages ->
            val messages: List<NdefMessage> = rawMessages.map { it as NdefMessage }
            // Process the messages array.
            ...
        }
    }
}

جافا

@Override
protected void onNewIntent(Intent intent) {
    super.onNewIntent(intent);
    ...
    if (NfcAdapter.ACTION_NDEF_DISCOVERED.equals(intent.getAction())) {
        Parcelable[] rawMessages =
            intent.getParcelableArrayExtra(NfcAdapter.EXTRA_NDEF_MESSAGES);
        if (rawMessages != null) {
            NdefMessage[] messages = new NdefMessage[rawMessages.length];
            for (int i = 0; i < rawMessages.length; i++) {
                messages[i] = (NdefMessage) rawMessages[i];
            }
            // Process the messages array.
            ...
        }
    }
}

بدلاً من ذلك، يمكنك الحصول على الكائن Tag من الغرض، والذي سيحتوي على الحمولة ويسمح لك بتعداد تقنيات العلامة:

لغة Kotlin

val tag: Tag = intent.getParcelableExtra(NfcAdapter.EXTRA_TAG)

جافا

Tag tag = intent.getParcelableExtra(NfcAdapter.EXTRA_TAG);

إنشاء أنواع شائعة من سجلات NDEF

يشرح هذا القسم طريقة إنشاء أنواع شائعة من سجلات NDEF لمساعدتك عند الكتابة إلى علامات NFC أو إرسال البيانات باستخدام شعاع Android. بدءًا من نظام التشغيل Android 4.0 (المستوى 14 لواجهة برمجة التطبيقات)، تُتاح طريقة createUri() لمساعدتك في إنشاء سجلات عناوين URL تلقائيًا. بدءًا من Android 4.1 (المستوى 16 لواجهة برمجة التطبيقات)، يتوفّر createExternal() وcreateMime() لمساعدتك في إنشاء سجلات NDEF من النوع الخارجي MIME. استخدِم هذه الطرق المساعِدة كلما أمكن ذلك لتجنب الأخطاء عند إنشاء سجلات NDEF يدويًا.

ويوضّح هذا القسم أيضًا كيفية إنشاء فلتر النية المقابل للسجلّ. يجب أن تكون جميع أمثلة سجلات NDEF هذه ضمن سجل NDEF الأول لرسالة NDEF التي تكتبها في علامة أو تمثلها.

معرّف الموارد المنتظم (URI) TNF_ABSOLUTE

ملاحظة: ننصح باستخدام النوع RTD_URI بدلاً من النوع TNF_ABSOLUTE_URI لأنه أكثر فعالية.

يمكنك إنشاء سجل NDEF TNF_ABSOLUTE_URI على النحو التالي :

لغة Kotlin

val uriRecord = ByteArray(0).let { emptyByteArray ->
    NdefRecord(
            TNF_ABSOLUTE_URI,
            "https://developer.android.com/index.html".toByteArray(Charset.forName("US-ASCII")),
            emptyByteArray,
            emptyByteArray
    )
}

جافا

NdefRecord uriRecord = new NdefRecord(
    NdefRecord.TNF_ABSOLUTE_URI ,
    "https://developer.android.com/index.html".getBytes(Charset.forName("US-ASCII")),
    new byte[0], new byte[0]);

سيظهر فلتر الأهداف لسجل NDEF السابق على النحو التالي:

<intent-filter>
    <action android:name="android.nfc.action.NDEF_DISCOVERED" />
    <category android:name="android.intent.category.DEFAULT" />
    <data android:scheme="https"
        android:host="developer.android.com"
        android:pathPrefix="/index.html" />
</intent-filter>

معيار TNF_MIME_MEDIA

يمكنك إنشاء سجل NDEF TNF_MIME_MEDIA بالطرق التالية:

استخدام طريقة createMime():

لغة Kotlin

val mimeRecord = NdefRecord.createMime(
        "application/vnd.com.example.android.beam",
        "Beam me up, Android".toByteArray(Charset.forName("US-ASCII"))
)

جافا

NdefRecord mimeRecord = NdefRecord.createMime("application/vnd.com.example.android.beam",
    "Beam me up, Android".getBytes(Charset.forName("US-ASCII")));

إنشاء NdefRecord يدويًا:

لغة Kotlin

val mimeRecord = Charset.forName("US-ASCII").let { usAscii ->
    NdefRecord(
            NdefRecord.TNF_MIME_MEDIA,
            "application/vnd.com.example.android.beam".toByteArray(usAscii),
            ByteArray(0),
            "Beam me up, Android!".toByteArray(usAscii)
    )
}

جافا

NdefRecord mimeRecord = new NdefRecord(
    NdefRecord.TNF_MIME_MEDIA ,
    "application/vnd.com.example.android.beam".getBytes(Charset.forName("US-ASCII")),
    new byte[0], "Beam me up, Android!".getBytes(Charset.forName("US-ASCII")));

سيظهر فلتر الأهداف لسجل NDEF السابق على النحو التالي:

<intent-filter>
    <action android:name="android.nfc.action.NDEF_DISCOVERED" />
    <category android:name="android.intent.category.DEFAULT" />
    <data android:mimeType="application/vnd.com.example.android.beam" />
</intent-filter>

TNF_WELL_KNOWN بـ RTD_TEXT

يمكنك إنشاء سجل NDEF TNF_WELL_KNOWN بالطريقة التالية:

لغة Kotlin

fun createTextRecord(payload: String, locale: Locale, encodeInUtf8: Boolean): NdefRecord {
    val langBytes = locale.language.toByteArray(Charset.forName("US-ASCII"))
    val utfEncoding = if (encodeInUtf8) Charset.forName("UTF-8") else Charset.forName("UTF-16")
    val textBytes = payload.toByteArray(utfEncoding)
    val utfBit: Int = if (encodeInUtf8) 0 else 1 shl 7
    val status = (utfBit + langBytes.size).toChar()
    val data = ByteArray(1 + langBytes.size + textBytes.size)
    data[0] = status.toByte()
    System.arraycopy(langBytes, 0, data, 1, langBytes.size)
    System.arraycopy(textBytes, 0, data, 1 + langBytes.size, textBytes.size)
    return NdefRecord(NdefRecord.TNF_WELL_KNOWN, NdefRecord.RTD_TEXT, ByteArray(0), data)
}

جافا

public NdefRecord createTextRecord(String payload, Locale locale, boolean encodeInUtf8) {
    byte[] langBytes = locale.getLanguage().getBytes(Charset.forName("US-ASCII"));
    Charset utfEncoding = encodeInUtf8 ? Charset.forName("UTF-8") : Charset.forName("UTF-16");
    byte[] textBytes = payload.getBytes(utfEncoding);
    int utfBit = encodeInUtf8 ? 0 : (1 << 7);
    char status = (char) (utfBit + langBytes.length);
    byte[] data = new byte[1 + langBytes.length + textBytes.length];
    data[0] = (byte) status;
    System.arraycopy(langBytes, 0, data, 1, langBytes.length);
    System.arraycopy(textBytes, 0, data, 1 + langBytes.length, textBytes.length);
    NdefRecord record = new NdefRecord(NdefRecord.TNF_WELL_KNOWN,
    NdefRecord.RTD_TEXT, new byte[0], data);
    return record;
}

سيظهر فلتر الأهداف لسجل NDEF السابق على النحو التالي:

<intent-filter>
    <action android:name="android.nfc.action.NDEF_DISCOVERED" />
    <category android:name="android.intent.category.DEFAULT" />
    <data android:mimeType="text/plain" />
</intent-filter>

TNF_WELL_KNOWN بـ RTD_URI

يمكنك إنشاء سجل NDEF TNF_WELL_KNOWN بالطرق التالية:

استخدام طريقة createUri(String):

لغة Kotlin

val rtdUriRecord1 = NdefRecord.createUri("https://example.com")

جافا

NdefRecord rtdUriRecord1 = NdefRecord.createUri("https://example.com");

استخدام طريقة createUri(Uri):

لغة Kotlin

val rtdUriRecord2 = Uri.parse("https://example.com").let { uri ->
    NdefRecord.createUri(uri)
}

جافا

Uri uri = Uri.parse("https://example.com");
NdefRecord rtdUriRecord2 = NdefRecord.createUri(uri);

إنشاء NdefRecord يدويًا:

لغة Kotlin

val uriField = "example.com".toByteArray(Charset.forName("US-ASCII"))
val payload = ByteArray(uriField.size + 1)                   //add 1 for the URI Prefix
payload [0] = 0x01                                           //prefixes https://www. to the URI
System.arraycopy(uriField, 0, payload, 1, uriField.size)     //appends URI to payload
val rtdUriRecord = NdefRecord(NdefRecord.TNF_WELL_KNOWN, NdefRecord.RTD_URI, ByteArray(0), payload)

جافا

byte[] uriField = "example.com".getBytes(Charset.forName("US-ASCII"));
byte[] payload = new byte[uriField.length + 1];              //add 1 for the URI Prefix
payload[0] = 0x01;                                           //prefixes https://www. to the URI
System.arraycopy(uriField, 0, payload, 1, uriField.length);  //appends URI to payload
NdefRecord rtdUriRecord = new NdefRecord(
    NdefRecord.TNF_WELL_KNOWN, NdefRecord.RTD_URI, new byte[0], payload);

سيظهر فلتر الأهداف لسجل NDEF السابق على النحو التالي:

<intent-filter>
    <action android:name="android.nfc.action.NDEF_DISCOVERED" />
    <category android:name="android.intent.category.DEFAULT" />
    <data android:scheme="https"
        android:host="example.com"
        android:pathPrefix="" />
</intent-filter>

TNF_EXTERNAL_TYPE

يمكنك إنشاء سجل NDEF TNF_EXTERNAL_TYPE بالطرق التالية:

استخدام طريقة createExternal():

لغة Kotlin

var payload: ByteArray //assign to your data
val domain = "com.example" //usually your app's package name
val type = "externalType"
val extRecord = NdefRecord.createExternal(domain, type, payload)

جافا

byte[] payload; //assign to your data
String domain = "com.example"; //usually your app's package name
String type = "externalType";
NdefRecord extRecord = NdefRecord.createExternal(domain, type, payload);

إنشاء NdefRecord يدويًا:

لغة Kotlin

var payload: ByteArray
...
val extRecord = NdefRecord(
        NdefRecord.TNF_EXTERNAL_TYPE,
        "com.example:externalType".toByteArray(Charset.forName("US-ASCII")),
        ByteArray(0),
        payload
)

جافا

byte[] payload;
...
NdefRecord extRecord = new NdefRecord(
    NdefRecord.TNF_EXTERNAL_TYPE, "com.example:externalType".getBytes(Charset.forName("US-ASCII")),
    new byte[0], payload);

سيظهر فلتر الأهداف لسجل NDEF السابق على النحو التالي:

<intent-filter>
    <action android:name="android.nfc.action.NDEF_DISCOVERED" />
    <category android:name="android.intent.category.DEFAULT" />
    <data android:scheme="vnd.android.nfc"
        android:host="ext"
        android:pathPrefix="/com.example:externalType"/>
</intent-filter>

يمكنك استخدام "TNF_EXTERNAL_TYPE" لإجراء عمليات نشر علامة NFC عامة أكثر لدعم كلّ من الأجهزة التي تعمل بنظام التشغيل Android والأجهزة التي لا تعمل بنظام التشغيل Android.

ملاحظة: أرقام URN في TNF_EXTERNAL_TYPE لها تنسيق أساسي على النحو التالي: urn:nfc:ext:example.com:externalType، ومع ذلك، تشير مواصفات اختبار RTD في منتدى NFC إلى أنّه يجب حذف جزء urn:nfc:ext: من URN من سجلّ NDEF. لذا، كل ما عليك تقديمه هو النطاق (example.com في المثال) والنوع (externalType في المثال) مفصول بنقطتين. عند إرسال TNF_EXTERNAL_TYPE، يحوِّل نظام Android رقم URN urn:nfc:ext:example.com:externalType إلى معرّف موارد منتظم vnd.android.nfc://ext/example.com:externalType، وهو ما يوضِّحه فلتر النية في المثال.

سجلات تطبيقات Android

في الإصدار 4.0 من نظام التشغيل Android (المستوى 14 من واجهة برمجة التطبيقات)، يوفّر سجلّ تطبيقات Android (AAR) تأكيدًا أقوى من بدء تشغيل تطبيقك عندما يتم مسح علامة NFC ضوئيًا. يحتوي AAR على اسم الحزمة لتطبيق مضمن داخل سجل NDEF. يمكنك إضافة AAR إلى أي سجل NDEF لرسالة NDEF، لأن Android يبحث في رسالة NDEF بأكملها عن هذه الاقتراحات. وفي حال العثور على AAR، يتم تشغيل التطبيق استنادًا إلى اسم الحزمة داخل AAR. في حال عدم توفّر التطبيق على الجهاز، يتم إطلاق Google Play لتنزيل التطبيق.

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

إذا كانت إحدى العلامات تحتوي على ميزة AAR، يتم إرسال نظام إرسال العلامة على النحو التالي:

  1. حاوِل بدء نشاط باستخدام فلتر أهداف على النحو المعتاد. إذا كان النشاط الذي يتطابق مع الغرض أيضًا يتطابق مع AAR، فابدأ النشاط.
  2. في حال عدم تطابق النشاط الذي يفلتر الغرض من ذلك الإجراء، أو إذا كان بإمكان أنشطة متعددة معالجة الغرض، أو إذا لم يكن هناك نشاط يستهدف الغرض، ابدأ التطبيق المحدد من قِبل الاقتراحات المطبّقة تلقائيًا.
  3. إذا تعذّر على أي تطبيق بدء استخدام AAR، انتقِل إلى Google Play لتنزيل التطبيق استنادًا إلى AAR.

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

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

يوفر Android واجهة برمجة تطبيقات بسيطة لإنشاء AAR، createApplicationRecord(). كل ما عليك فعله هو تضمين AAR في أي مكان في NdefMessage. لا تريد استخدام السجلّ الأول من NdefMessage، إلّا إذا كانت ميزة AAR هي السجلّ الوحيد في NdefMessage. ويرجع ذلك إلى أنّ نظام Android يفحص السجلّ الأول للسمة NdefMessage لتحديد نوع MIME أو معرّف الموارد المنتظم (URI) للعلامة، ويُستخدم هذا الإجراء لإنشاء هدف تطبّقه التطبيقات. توضح لك التعليمة البرمجية التالية كيفية إنشاء AAR:

لغة Kotlin

val msg = NdefMessage(
        arrayOf(
                ...,
                NdefRecord.createApplicationRecord("com.example.android.beam")
        )
)

جافا

NdefMessage msg = new NdefMessage(
        new NdefRecord[] {
            ...,
            NdefRecord.createApplicationRecord("com.example.android.beam")}
        );
)

إرسال رسائل NDEF إلى أجهزة أخرى

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

ملاحظة: كان إرسال NDEF في الواجهة الأمامية متاحًا على المستوى 10 من واجهة برمجة التطبيقات، والذي يوفّر وظائف مشابهة لميزة "شعاع Android". تم إيقاف واجهات برمجة التطبيقات هذه منذ ذلك الحين، ولكنها متوفرة لدعم الأجهزة القديمة. يُرجى الاطّلاع على enableForegroundNdefPush() للحصول على المزيد من المعلومات.

يمكنك تمكين شعاع Android لتطبيقك من خلال استدعاء إحدى الطريقتين التاليتين:

  • setNdefPushMessage(): تقبل NdefMessage لضبطها كالرسالة المراد إرسالها. إرسال الرسالة تلقائيًا عندما يكون جهازان على مسافة قريبة بما فيه الكفاية.
  • setNdefPushMessageCallback(): تقبل معاودة الاتصال التي تحتوي على createNdefMessage() والتي يتم استدعاؤها عندما يكون الجهاز في النطاق الذي سيتم إرسال البيانات إليه. يتيح لك معاودة الاتصال إنشاء رسالة NDEF عند الضرورة فقط.

لا يمكن أن يؤدي النشاط إلا إلى إرسال رسالة NDEF واحدة في كل مرة، وبالتالي تكون الأولوية للسمة setNdefPushMessageCallback() على setNdefPushMessage() في حال ضبط كلتا الرسالتين. لاستخدام ميزة شعاع Android، يجب تلبية الإرشادات العامة التالية:

  • يجب أن يكون النشاط الذي يرسل البيانات في المقدّمة. يجب أن يتم فتح قفل شاشتهما على كلا الجهازين.
  • يجب تضمين البيانات التي ترسلها في كائن NdefMessage.
  • يجب أن يتوافق جهاز NFC الذي يتلقى البيانات الإرسالية مع بروتوكول إرسال NDEF com.android.npp أو بروتوكول SNEP (البروتوكول البسيط لتبادل NDEF) التابع لمنتدى NFC. يجب استخدام بروتوكول com.android.npp للأجهزة التي تعمل بالمستوى 9 من واجهة برمجة التطبيقات (Android 2.3) إلى المستوى 13 من واجهة برمجة التطبيقات (Android 3.2). com.android.npp وSNEP مطلوبان على المستوى 14 من واجهة برمجة التطبيقات (Android 4.0) والإصدارات الأحدث.

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

لتمكين شعاع Android:

  1. أنشِئ NdefMessage يتضمّن علامات NdefRecord التي تريد فرضها على الجهاز الآخر.
  2. يمكنك استدعاء "setNdefPushMessage()" باستخدام NdefMessage أو استدعاء setNdefPushMessageCallback لتمرير عنصر NfcAdapter.CreateNdefMessageCallback من خلال طريقة onCreate() لنشاطك. تتطلب هذه الطرق نشاطًا واحدًا على الأقل تريد تفعيله باستخدام ميزة شعاع Android، بالإضافة إلى قائمة اختيارية بالأنشطة الأخرى المطلوب تنشيطها.

    بشكل عام، عادةً ما تستخدم setNdefPushMessage() إذا كان نشاطك يحتاج فقط إلى إرسال رسالة NDEF نفسها في جميع الأوقات، عندما يكون هناك جهازان في النطاق للاتصال. ويمكنك استخدام setNdefPushMessageCallback عندما يهتم تطبيقك بالسياق الحالي للتطبيق ويريد إرسال رسالة NDEF بناءً على ما يفعله المستخدم في تطبيقك.

يوضح النموذج التالي كيفية استدعاء نشاط بسيط NfcAdapter.CreateNdefMessageCallback في طريقة onCreate() لأحد الأنشطة (يمكنك الاطلاع على AndroidBeamDemo للحصول على النموذج الكامل). يتضمّن هذا المثال أيضًا طرقًا لمساعدتك في إنشاء سجلّ MIME:

لغة Kotlin

package com.example.android.beam

import android.app.Activity
import android.content.Intent
import android.nfc.NdefMessage
import android.nfc.NdefRecord
import android.nfc.NfcAdapter
import android.nfc.NfcAdapter.CreateNdefMessageCallback
import android.nfc.NfcEvent
import android.os.Bundle
import android.os.Parcelable
import android.widget.TextView
import android.widget.Toast
import java.nio.charset.Charset

class Beam : Activity(), NfcAdapter.CreateNdefMessageCallback {
    
    private var nfcAdapter: NfcAdapter? = null
    private lateinit var textView: TextView

    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        setContentView(R.layout.main)
        textView = findViewById(R.id.textView)
        // Check for available NFC Adapter
        nfcAdapter = NfcAdapter.getDefaultAdapter(this)
        if (nfcAdapter == null) {
            Toast.makeText(this, "NFC is not available", Toast.LENGTH_LONG).show()
            finish()
            return
        }
        // Register callback
        nfcAdapter?.setNdefPushMessageCallback(this, this)
    }

    override fun createNdefMessage(event: NfcEvent): NdefMessage {
        val text = "Beam me up, Android!\n\n" +
                "Beam Time: " + System.currentTimeMillis()
        return NdefMessage(
                arrayOf(
                        createMime("application/vnd.com.example.android.beam", text.toByteArray())
                )
                /**
                 * The Android Application Record (AAR) is commented out. When a device
                 * receives a push with an AAR in it, the application specified in the AAR
                 * is guaranteed to run. The AAR overrides the tag dispatch system.
                 * You can add it back in to guarantee that this
                 * activity starts when receiving a beamed message. For now, this code
                 * uses the tag dispatch system.
                 *///,NdefRecord.createApplicationRecord("com.example.android.beam")
        )
    }

    override fun onResume() {
        super.onResume()
        // Check to see that the Activity started due to an Android Beam
        if (NfcAdapter.ACTION_NDEF_DISCOVERED == intent.action) {
            processIntent(intent)
        }
    }

    override fun onNewIntent(intent: Intent) {
        // onResume gets called after this to handle the intent
        setIntent(intent)
    }

    /**
     * Parses the NDEF Message from the intent and prints to the TextView
     */
    private fun processIntent(intent: Intent) {
        textView = findViewById(R.id.textView)
        // only one message sent during the beam
        intent.getParcelableArrayExtra(NfcAdapter.EXTRA_NDEF_MESSAGES)?.also { rawMsgs ->
            (rawMsgs[0] as NdefMessage).apply {
                // record 0 contains the MIME type, record 1 is the AAR, if present
                textView.text = String(records[0].payload)
            }
        }
    }
}

جافا

package com.example.android.beam;

import android.app.Activity;
import android.content.Intent;
import android.nfc.NdefMessage;
import android.nfc.NdefRecord;
import android.nfc.NfcAdapter;
import android.nfc.NfcAdapter.CreateNdefMessageCallback;
import android.nfc.NfcEvent;
import android.os.Bundle;
import android.os.Parcelable;
import android.widget.TextView;
import android.widget.Toast;
import java.nio.charset.Charset;


public class Beam extends Activity implements CreateNdefMessageCallback {
    NfcAdapter nfcAdapter;
    TextView textView;

    @Override
    public void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.main);
        TextView textView = (TextView) findViewById(R.id.textView);
        // Check for available NFC Adapter
        nfcAdapter = NfcAdapter.getDefaultAdapter(this);
        if (nfcAdapter == null) {
            Toast.makeText(this, "NFC is not available", Toast.LENGTH_LONG).show();
            finish();
            return;
        }
        // Register callback
        nfcAdapter.setNdefPushMessageCallback(this, this);
    }

    @Override
    public NdefMessage createNdefMessage(NfcEvent event) {
        String text = ("Beam me up, Android!\n\n" +
                "Beam Time: " + System.currentTimeMillis());
        NdefMessage msg = new NdefMessage(
                new NdefRecord[] { createMime(
                        "application/vnd.com.example.android.beam", text.getBytes())
         /**
          * The Android Application Record (AAR) is commented out. When a device
          * receives a push with an AAR in it, the application specified in the AAR
          * is guaranteed to run. The AAR overrides the tag dispatch system.
          * You can add it back in to guarantee that this
          * activity starts when receiving a beamed message. For now, this code
          * uses the tag dispatch system.
          */
          //,NdefRecord.createApplicationRecord("com.example.android.beam")
        });
        return msg;
    }

    @Override
    public void onResume() {
        super.onResume();
        // Check to see that the Activity started due to an Android Beam
        if (NfcAdapter.ACTION_NDEF_DISCOVERED.equals(getIntent().getAction())) {
            processIntent(getIntent());
        }
    }

    @Override
    public void onNewIntent(Intent intent) {
        // onResume gets called after this to handle the intent
        setIntent(intent);
    }

    /**
     * Parses the NDEF Message from the intent and prints to the TextView
     */
    void processIntent(Intent intent) {
        textView = (TextView) findViewById(R.id.textView);
        Parcelable[] rawMsgs = intent.getParcelableArrayExtra(
                NfcAdapter.EXTRA_NDEF_MESSAGES);
        // only one message sent during the beam
        NdefMessage msg = (NdefMessage) rawMsgs[0];
        // record 0 contains the MIME type, record 1 is the AAR, if present
        textView.setText(new String(msg.getRecords()[0].getPayload()));
    }
}

تجدر الإشارة إلى أنّ هذا الرمز يعلِّق على AAR، والذي يمكنك إزالته. في حال تفعيل ميزة AAR، سيتلقّى التطبيق المحدد في هذه الميزة رسالة Android Beam دائمًا. في حال عدم توفّر التطبيق، يبدأ Google Play في تنزيل التطبيق. وبالتالي، فإن فلتر الأهداف التالي ليس ضروريًا من الناحية الفنية لأجهزة Android 4.0 أو الإصدارات الأحدث في حال استخدام الاقتراحات المطبّقة تلقائيًا:

<intent-filter>
  <action android:name="android.nfc.action.NDEF_DISCOVERED"/>
  <category android:name="android.intent.category.DEFAULT"/>
  <data android:mimeType="application/vnd.com.example.android.beam"/>
</intent-filter>

باستخدام فلتر الأهداف هذا، يمكن الآن تشغيل تطبيق com.example.android.beam عندما يفحص علامة NFC أو يتلقى شعاع Android به نوع AAR من النوع com.example.android.beam أو عندما تحتوي رسالة بتنسيق NDEF على سجل MIME من النوع application/vnd.com.example.android.beam.

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