• 14、NFC技术:使用Android Beam技术传输文本


    Android Beam的基本理念

         Android Beam的基本理念就是两部(只能是两部)NFC设备靠近时(一般是背靠背),通过触摸一部NFC设备的屏幕,将数据推向另外一部NFC设备。在传递数据的过程中,两部NFC设备不能离得太远,否则NFC连接将中断。

    Android Beam API

    Android SDK提供了如下两个用于传递消息的方法。

    NfcAdapter.setNdefPushMessage
    NfcAdapter.setNdefPushMessageCallback

    public void setNdefPushMessage(NdefMessage message, Activity activity, Activity ... activities);

    public void setNdefPushMessageCallback(CreateNdefMessageCallback callback, Activity activity, Activity ... activities);

    public NdefMessage createNdefMessage(NfcEvent event)

    Demo

              
      1 import java.nio.charset.Charset;
      2 import java.util.Locale;
      3 
      4 import android.app.Activity;
      5 import android.app.PendingIntent;
      6 import android.content.Intent;
      7 import android.nfc.NdefMessage;
      8 import android.nfc.NdefRecord;
      9 import android.nfc.NfcAdapter;
     10 import android.nfc.NfcAdapter.CreateNdefMessageCallback;
     11 import android.nfc.NfcAdapter.OnNdefPushCompleteCallback;
     12 import android.nfc.NfcEvent;
     13 import android.os.Bundle;
     14 import android.os.Parcelable;
     15 import android.util.Log;
     16 import android.widget.EditText;
     17 import android.widget.Toast;
     18 
     19 /**
     20  * 两部android手机,进行传入文本信息。
     21  * @author dr
     22  *
     23  */
     24 public class AndroidBeamMainActivity extends Activity implements
     25         CreateNdefMessageCallback, OnNdefPushCompleteCallback {
     26 
     27     private EditText mBeamText;
     28 
     29     private NfcAdapter mNfcAdapter;
     30     private PendingIntent mPendingIntent;
     31 
     32     @Override
     33     public void onCreate(Bundle savedInstanceState) {
     34         super.onCreate(savedInstanceState);
     35 
     36         setContentView(R.layout.activity_android_beam);
     37         mBeamText = (EditText) findViewById(R.id.edittext_beam_text);
     38         
     39         mNfcAdapter = mNfcAdapter.getDefaultAdapter(this);
     40         mPendingIntent = PendingIntent.getActivity(this, 0, new Intent(this,
     41                 getClass()), 0);
     42 
     43         mNfcAdapter.setNdefPushMessageCallback(this, this);
     44         mNfcAdapter.setOnNdefPushCompleteCallback(this, this);
     45     }
     46 
     47     @Override    /** 窗口处理完成 */
     48     public void onNdefPushComplete(NfcEvent event) {
     49         Log.d("message", "complete");
     50     }
     51 
     52     @Override  /** 如果另外一台手机,靠近当前这部手机 */
     53     public NdefMessage createNdefMessage(NfcEvent event) {
     54         String text = mBeamText.getText().toString().trim();
     55         if ("".equals(text))
     56             text = "默认文本";
     57         /*
     58          *  "com.android.calculator2"  官方原生计算器包。
     59          *  当另外一部手机靠近这部手机时,会启动计算器。
     60          *  
     61          * NdefMessage ndefMessage = new NdefMessage( new NdefRecord[] {
     62          * NdefRecord .createApplicationRecord("com.android.calculator2") });
     63          */
     64         NdefMessage ndefMessage = new NdefMessage(
     65                 new NdefRecord[] { createTextRecord(text) });
     66 
     67         return ndefMessage;
     68     }
     69 
     70     @Override
     71     public void onResume() {
     72         super.onResume();
     73         if (mNfcAdapter != null)
     74             mNfcAdapter.enableForegroundDispatch(this, mPendingIntent, null,
     75                     null);
     76     }
     77 
     78     @Override
     79     public void onPause() {
     80         super.onPause();
     81         if (mNfcAdapter != null)
     82             mNfcAdapter.disableForegroundDispatch(this);
     83     }
     84 
     85     @Override
     86     public void onNewIntent(Intent intent) {
     87         // 用于显示接收手机的信息。如果接收手机没有打开,会默认调用系统的黑界面。
     88         processIntent(intent);
     89     }
     90 
     91     /** 根据文本创建 NdefRecord 这个对象 */
     92     public NdefRecord createTextRecord(String text) {
     93         byte[] langBytes = Locale.CHINA.getLanguage().getBytes(
     94                 Charset.forName("US-ASCII"));
     95         Charset utfEncoding = Charset.forName("UTF-8");
     96         byte[] textBytes = text.getBytes(utfEncoding);
     97         int utfBit = 0;
     98         char status = (char) (utfBit + langBytes.length);
     99         byte[] data = new byte[1 + langBytes.length + textBytes.length];
    100         data[0] = (byte) status;
    101         System.arraycopy(langBytes, 0, data, 1, langBytes.length);
    102         System.arraycopy(textBytes, 0, data, 1 + langBytes.length,
    103                 textBytes.length);
    104         NdefRecord record = new NdefRecord(NdefRecord.TNF_WELL_KNOWN,
    105                 NdefRecord.RTD_TEXT, new byte[0], data);
    106 
    107         return record;
    108     }
    109 
    110     void processIntent(Intent intent) {
    111         Parcelable[] rawMsgs = intent
    112                 .getParcelableArrayExtra(NfcAdapter.EXTRA_NDEF_MESSAGES);
    113 
    114         NdefMessage msg = (NdefMessage) rawMsgs[0];
    115         String text = TextRecord.parse(msg.getRecords()[0]).getText();
    116         Toast.makeText(this, text, Toast.LENGTH_LONG).show();
    117     }
    118 }
     1 import java.io.UnsupportedEncodingException;
     2 import java.util.Arrays;
     3 import android.nfc.NdefRecord;
     4 
     5 public class TextRecord {
     6     private final String mText;
     7 
     8     private TextRecord(String text) {
     9         mText = text;
    10     }
    11 
    12     public String getText() {
    13         return mText;
    14     }
    15 
    16     // 将纯文本内容从NdefRecord对象中解析出来
    17     public static TextRecord parse(NdefRecord record) {
    18 
    19         if (record.getTnf() != NdefRecord.TNF_WELL_KNOWN)
    20             return null;
    21         if (!Arrays.equals(record.getType(), NdefRecord.RTD_TEXT))
    22             return null;
    23 
    24         try {
    25             byte[] payload = record.getPayload();
    26             /*
    27              * payload[0] contains the "Status Byte Encodings" field, per the
    28              * NFC Forum "Text Record Type Definition" section 3.2.1.
    29              * 
    30              * bit7 is the Text Encoding Field.
    31              * 
    32              * if (Bit_7 == 0): The text is encoded in UTF-8 if (Bit_7 == 1):
    33              * The text is encoded in UTF16
    34              * 
    35              * Bit_6 is reserved for future use and must be set to zero.
    36              * 
    37              * Bits 5 to 0 are the length of the IANA language code.
    38              */
    39             String textEncoding = ((payload[0] & 0x80) == 0) ? "UTF-8"
    40                     : "UTF-16";
    41             int languageCodeLength = payload[0] & 0x3f;
    42             String languageCode = new String(payload, 1, languageCodeLength,
    43                     "US-ASCII");
    44             String text = new String(payload, languageCodeLength + 1,
    45                     payload.length - languageCodeLength - 1, textEncoding);
    46             return new TextRecord(text);
    47         } catch (UnsupportedEncodingException e) {
    48             // should never happen unless we get a malformed tag.
    49             throw new IllegalArgumentException(e);
    50         }
    51     }
    52 
    53 }
     1 <?xml version="1.0" encoding="utf-8"?>
     2 <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
     3     android:layout_width="match_parent"
     4     android:layout_height="match_parent"
     5     android:orientation="vertical" >
     6 
     7     <EditText
     8         android:id="@+id/edittext_beam_text"
     9         android:layout_width="match_parent"
    10         android:layout_height="wrap_content"
    11         android:hint="请输入要传输的文本"/>
    12 
    13     <TextView
    14         android:layout_width="match_parent"
    15         android:layout_height="wrap_content"
    16         android:layout_marginBottom="5dp"
    17         android:text="请将当前设备靠近其他NFC设备,别忘了触摸屏幕哦!"
    18         android:textSize="16sp" />
    19 
    20     <ImageView
    21         android:layout_width="match_parent"
    22         android:layout_height="match_parent"
    23         android:layout_margin="10dp"
    24         android:src="@drawable/read_nfc_tag" />
    25 
    26 </LinearLayout>
     
  • 相关阅读:
    SpringBoot Rabbitmq接收消息
    SpringBoot Rabbitmq发送消息
    Rabbitmq 介绍
    Eureka 使用Spring cloud config 管理中心启动
    Spring Cloud Config 搭建Config 服务
    Eureka 向Server中注册服务
    Eureka 配置
    给定一些分割符,给定一个待分割的字符串,打印出分割之后最长的字符串
    给定N个整数,乱序,分行打印每个数字和其位置
    给定一个整数,求它的二进制表示中有多少个1
  • 原文地址:https://www.cnblogs.com/androidsj/p/3856440.html
Copyright © 2020-2023  润新知