今晚整理下,实验室没开门,只好在一教将就一下了

关于蓝牙,看了好些天,但是看完后想想也没啥,都是谷歌做好了的东西,我们只要用用API就ok了,哎。

首先,如果是互相传递数据的,两部android设备各自都必须充当两种角色。

1、服务端 2、客户端。

其实也不难理解,毕竟通信是两者之间建立的,而且必须实现收发并用。所以理所当然了,客户端发送消息给服务端。

两部设备是通过使用相同的UUID建立起一个Rfcomm什么的通道,这个通道连接两台设备以供数据的传递。

当然要如何建立呢?(我也不知道)

我们先分析客户端,他是通过Socket的一个主动连接函数connect()来请求服务端的连接(服务端接收到请求..才会有数据传递 后面再说),那么这个socket是怎样来的呢?

是通过device.createRfcommSocketToServiceRecord(UUID);来的,这个device是由你相连服务端的地址得到的,通过蓝牙适配器mBluetoothAdapter.getRemoteDevice(address);来的。address又是怎么来的呢? 是通过扫描附近蓝牙,被广播接收器接收到的。

好的整理一下,就是通过广播接收器扫描到附近的蓝牙设备(当然机智的你肯定准备好了两台设备) 然后能通过扫描到的设备得到他们的地址。通过这个地址就能实例化出device

然后Socket也就出来了。最后通过Socket.getOutputStream() 得到输出流,想输出流内写入数据 即可完成客户端的任务。

//以下是客户端负责发送消息的代码(布局和manifest文件自己添加以下,很简单)

package com.example.single_bt1;import android.app.Activity;
import android.bluetooth.BluetoothAdapter;
import android.bluetooth.BluetoothDevice;
import android.bluetooth.BluetoothSocket;
import android.content.BroadcastReceiver;
import android.content.Context;
import android.content.Intent;
import android.content.IntentFilter;
import android.os.Bundle;
import android.util.Log;
import android.view.View;
import android.widget.AdapterView;
import android.widget.AdapterView.OnItemClickListener;
import android.widget.ArrayAdapter;
import android.widget.EditText;
import android.widget.ListView;
import android.widget.Toast;import java.io.OutputStream;
import java.util.ArrayList;
import java.util.List;
import java.util.Set;
import java.util.UUID;public class AsClient extends Activity implements OnItemClickListener {private static final String TAG = "MainActivity";// 本地蓝牙适配器private BluetoothAdapter mBluetoothAdapter;// 列表private ListView lvDevices;// 存储搜索到的蓝牙private List<String> bluetoothDevices = new ArrayList<String>();// listview的adapterprivate ArrayAdapter<String> arrayAdapter;// UUID.randomUUID()随机获取UUIDprivate final UUID MY_UUID = UUID.fromString("db764ac8-4b08-7f25-aafe-59d03c27bae3");// 连接对象的名称private final String NAME = "LGL";// 这里本身即是服务端也是客户端,需要如下类private BluetoothSocket clientSocket;private BluetoothDevice device;// 输出流_客户端需要往服务端输出private OutputStream os;private EditText et;@Overrideprotected void onCreate(Bundle savedInstanceState) {super.onCreate(savedInstanceState);setContentView(R.layout.activity_main);initView();}private void initView() {// 获取本地蓝牙适配器mBluetoothAdapter = BluetoothAdapter.getDefaultAdapter();// 判断手机是否支持蓝牙if (mBluetoothAdapter == null) {Toast.makeText(this, "设备不支持蓝牙", Toast.LENGTH_SHORT).show();finish();}// 判断是否打开蓝牙if (!mBluetoothAdapter.isEnabled()) {// 弹出对话框提示用户是后打开Intent intent = new Intent(BluetoothAdapter.ACTION_REQUEST_ENABLE);startActivityForResult(intent, 1);// 不做提示,强行打开
//             mBluetoothAdapter.enable();}et = (EditText) findViewById(R.id.edit_input2);// 初始化listviewlvDevices = (ListView) findViewById(R.id.lvDevices);lvDevices.setOnItemClickListener(this);// 获取已经配对的设备Set<BluetoothDevice> pairedDevices = mBluetoothAdapter.getBondedDevices();// 判断是否有配对过的设备if (pairedDevices.size() > 0) {for (BluetoothDevice device : pairedDevices) {// 遍历到列表中bluetoothDevices.add("已配对\n" + device.getName() + ":"+ device.getAddress());}}// adapterarrayAdapter = new ArrayAdapter<String>(this,android.R.layout.simple_list_item_1, android.R.id.text1,bluetoothDevices);lvDevices.setAdapter(arrayAdapter);//启动服务/*** 异步搜索蓝牙设备——广播接收*/// 找到设备的广播IntentFilter filter = new IntentFilter(BluetoothDevice.ACTION_FOUND);// 注册广播registerReceiver(receiver, filter);// 搜索完成的广播filter = new IntentFilter(BluetoothAdapter.ACTION_DISCOVERY_FINISHED);// 注册广播registerReceiver(receiver, filter);}@Overrideprotected void onDestroy() {super.onDestroy();unregisterReceiver(receiver);}// 广播接收器private final BroadcastReceiver receiver = new BroadcastReceiver() {@Overridepublic void onReceive(Context context, Intent intent) {// 收到的广播类型String action = intent.getAction();// 发现设备的广播if (BluetoothDevice.ACTION_FOUND.equals(action)) {// 从intent中获取设备BluetoothDevice device = intent.getParcelableExtra(BluetoothDevice.EXTRA_DEVICE);// 判断是否配对过if (device.getBondState() != BluetoothDevice.BOND_BONDED) {// 添加到列表bluetoothDevices.add("未配对\n" + device.getName() + ":"+ device.getAddress());arrayAdapter.notifyDataSetChanged();}// 搜索完成} else if (BluetoothAdapter.ACTION_DISCOVERY_FINISHED.equals(action)) {// 关闭进度条setProgressBarIndeterminateVisibility(true);setTitle("搜索完成!");}}};// 客户端@Overridepublic void onItemClick(AdapterView<?> parent, View view, int position,long id) {// 先获得蓝牙的地址和设备名String s = arrayAdapter.getItem(position);// 单独解析地址String address = s.substring(s.indexOf(":") + 1).trim();// 主动连接蓝牙try {// 判断是否在搜索,如果在搜索,就取消搜索if (mBluetoothAdapter.isDiscovering()) {mBluetoothAdapter.cancelDiscovery();}try {// 获得远程设备device = mBluetoothAdapter.getRemoteDevice(address);Log.e(TAG, "device:" + device);clientSocket = device.createRfcommSocketToServiceRecord(MY_UUID);// 连接clientSocket.connect();// 获得输出流os = clientSocket.getOutputStream();// 判断是否可以获得if (device == null) {// 获得远程设备device = mBluetoothAdapter.getRemoteDevice(address);Log.e(TAG, "device:" + device);}// 开始连接if (clientSocket == null) {clientSocket = device.createRfcommSocketToServiceRecord(MY_UUID);// 连接clientSocket.connect();// 获得输出流os = clientSocket.getOutputStream();}} catch (Exception e) {}// 如果成功获得输出流if (os != null) {
//                os.write("Hello Bluetooth!".getBytes());os.write(et.getText().toString().getBytes("GBK"));Log.e(TAG, "write");et.setText("");}} catch (Exception e) {}}}

接下来就是服务端了,服务端相比来说就稍微省事一点了,坐在那里等人来请求,所以他要一直在那里等,言下之意就是一个耗时操作,所以放在一个新的线程中是自然的事情。通过ServerScoket的accept()会产生一个socket负责与客户端的socket通信, 那么这个serversocket哪来的呢,直接上代码吧:

serverSocket = mBluetoothAdapter .listenUsingRfcommWithServiceRecord(NAME, MY_UUID); name是自己定义的,随便写就好(String类型)

然后就是通过serverSocket.getInputStream() 得到输入流,就能读出数据了。

package com.example.single_bt2_server;import android.app.Activity;
import android.bluetooth.BluetoothAdapter;
import android.bluetooth.BluetoothServerSocket;
import android.bluetooth.BluetoothSocket;
import android.content.Intent;
import android.os.Bundle;
import android.os.Handler;
import android.os.Message;
import android.util.Log;
import android.widget.ArrayAdapter;
import android.widget.ListView;
import android.widget.Toast;import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
import java.util.ArrayList;
import java.util.List;
import java.util.UUID;public class MainActivity extends Activity {private static final String TAG = "MainActivity";// 本地蓝牙适配器private BluetoothAdapter mBluetoothAdapter;// UUID.randomUUID()随机获取UUIDprivate final UUID MY_UUID = UUID.fromString("db764ac8-4b08-7f25-aafe-59d03c27bae3");// 连接对象的名称private final String NAME = "LGL";//线程类的实例private AcceptThread ac;//    private EditText edit_Get;private ListView list_Get;private List<String> content = new ArrayList<String>();private ArrayAdapter<String> adapter;@Overrideprotected void onCreate(Bundle savedInstanceState) {super.onCreate(savedInstanceState);setContentView(R.layout.received);
//        edit_Get = (EditText) findViewById(R.id.edit_get);initView();}private void initView() {list_Get = (ListView) findViewById(R.id.list_get);adapter = new ArrayAdapter<String>(MainActivity.this,android.R.layout.simple_list_item_1,content);list_Get.setAdapter(adapter);// 获取本地蓝牙适配器mBluetoothAdapter = BluetoothAdapter.getDefaultAdapter();// 判断手机是否支持蓝牙if (mBluetoothAdapter == null) {Toast.makeText(this, "设备不支持蓝牙", Toast.LENGTH_SHORT).show();finish();}// 判断是否打开蓝牙if (!mBluetoothAdapter.isEnabled()) {// 弹出对话框提示用户是后打开Intent intent = new Intent(BluetoothAdapter.ACTION_REQUEST_ENABLE);startActivityForResult(intent, 1);// 不做提示,强行打开
//             mBluetoothAdapter.enable();}ac = new AcceptThread();ac.start();}// 服务端,需要监听客户端的线程类private Handler handler = new Handler() {public void handleMessage(Message msg) {Toast.makeText(MainActivity.this, String.valueOf(msg.obj),Toast.LENGTH_SHORT).show();String result = String.valueOf(msg.obj);
//            edit_Get.setText(String.valueOf(msg.obj));content.add(result);adapter.notifyDataSetChanged();Log.e(TAG, msg.obj + ":服务端");super.handleMessage(msg);}};// 线程服务类private class AcceptThread extends Thread {private BluetoothServerSocket serverSocket;private BluetoothSocket socket;// 输入 输出流private OutputStream os;private InputStream is;public AcceptThread() {try {serverSocket = mBluetoothAdapter.listenUsingRfcommWithServiceRecord(NAME, MY_UUID);} catch (IOException e) {// TODO Auto-generated catch blocke.printStackTrace();}}@Overridepublic void run() {// 截获客户端的蓝牙消息try {socket = serverSocket.accept(); // 如果阻塞了,就会一直停留在这里is = socket.getInputStream();os = socket.getOutputStream();while (true) {synchronized (MainActivity.this) {byte[] tt = new byte[is.available()];if (tt.length > 0) {is.read(tt, 0, tt.length);Message msg = new Message();msg.obj = new String(tt, "GBK");Log.e(TAG, msg.obj + ":客户端");handler.sendMessage(msg);}}}} catch (Exception e) {e.printStackTrace();Log.e(TAG, e.getMessage());}}}}

至于两者都有的角色 让我放到文件中吧,是网上参考

Android手机蓝牙互联,并传递数据。相关推荐

  1. Android 手机蓝牙 (普通蓝牙篇)

    Android 手机蓝牙一 (普通蓝牙) hello,大家好有很久没有更新博客了.想写的东西很多,提起笔又觉得无从下笔.可能这就是菜鸟吧!好了废话不多说,进入正题. 本篇讲的是Android手机蓝牙分 ...

  2. react-native 原生Android界面向rn界面传递数据

    react-native 原生Android界面向rn界面传递数据 写在前面:本人因技术有限,写的都是一些自己会的或者是能查到的方法,可能会存在一些瑕疵.如果大家有什么更好的方法,欢迎一起讨论. 在r ...

  3. Android手机蓝牙连接笔记本电脑蓝牙

    1. 实验设备 1.1 笔记电脑 品牌:DELL 蓝牙模块:BCM43142(内置型带蓝牙的无线网卡) 蓝牙驱动:bluetooth_broadcom_6.5.1.6400_w7(通过360驱动大师下 ...

  4. STM32F103单片机温湿度等监测Android手机蓝牙APP显示控制设计

    这次给大家介绍的是一个温湿度,光照烟雾等监测设计,包含开关灯.基于STM32F103单片机(正点原子mini板).蓝牙模块.Android APP完成.软件是Android studio 2021.1 ...

  5. 美国部分Android手机竟将用户隐私数据回传至上海服务器!

    美国出售的Android手机,居然会将用户的个人数据传回到中国上海的服务器?今天美国大量安全媒体就报道了这样一件事,美国人民听来大概是非常惊悚的!Kryptowire安全公司的专家发现美国在售某些品牌 ...

  6. android fragment传递数据,Android 两个Fragment之间传递数据实例详解

    Android 两个Fragment之间如何传递数据 FragmentA启动FragmentB,做一些选择操作后,返回FragmentA,需要把FragmentB里面选择的数据传回来.有什么办法? F ...

  7. Android 开发中使用Intent传递数据的方法

    Activity之间通过Intent传递值,支持基本数据类型和String对象及它们的数组对象byte.byte[].char.char[].boolean.boolean[].short.short ...

  8. Android 手机获取加速度传感器加速度数据并自定义采样频率

    原文链接:http://blog.csdn.net/llp1992/article/details/41786865 因为项目需要利用到了Android手机中的加速度传感器来获取三个加速度轴的加速度大 ...

  9. android数据线接口定义,制作Android手机可连接普通键盘的数据转接线

    在上一篇" 现在市面上的Android手机和Android平板电脑基本上都支持USB OTG技术.这种技术将允许用户将手机或平板电脑通过usb2.0数据线连接到标准USB键盘和鼠标,甚至普通 ...

最新文章

  1. Android之加载外部dex
  2. c语言ut8,C语言使用utlist实现的双向链表
  3. 你可能不知道的switch
  4. 6.2.2 二叉树的创建
  5. STM32F1笔记(十二)DAC
  6. java使用properties_Java中使用Properties配置文件的简单方法
  7. sql慢查询问题排查
  8. 10分钟学会数据库压力测试
  9. svm loss function是什么
  10. “绿坝-花季护航”软件
  11. python numpy安装失败_【Python】pip安装numpy安装到一半失败解决办法
  12. c++ 写并查集算法模板
  13. 前端JQuery插件distpicker.js的部分操作使用
  14. cad2016批量修改相关字体,统一文字样式
  15. 金山毒霸推新产品金山卫士 正面狙击奇虎360
  16. 一句话道破X64和X86的区别
  17. 移动硬盘提示格式化解决办法,未正确删除导致不能读取文件提示格式化解决方案
  18. Vue简单快速上手 idea版
  19. 三轴加速度传感器BMA250解读
  20. FreeRTOS中的堆栈计算

热门文章

  1. 嵌入式系统linux开发流程,嵌入式系统的定义及嵌入式系统的开发流程
  2. Win8 RP微软原版光盘镜像下载大全(含中文版)
  3. Swift相关第三方资源整合
  4. PixHawk接口定义和Mission Planner安装及校准
  5. android的IPC机制
  6. 那些高阅读量文章的标题都是怎么取的?14种模板直接套用
  7. 实验7-1-5 选择法排序 (20分)
  8. MSN spaces Beta
  9. js获取当前时间戳;指定时间转换时间戳;时间戳转换时间
  10. 1564 把箱子放进仓库里 I