转载请注明出处:http://blog.csdn.net/vnanyesheshou/article/details/71713786

本文主要是Android做为Audio Source端,A2DP的基本操作:包括连接、断开连接、设置优先级、获取优先级、获取A2DP连接状态、获取A2DP连接的设备列表等功能。


##

1 简介 ##
A2DP全名是Advanced Audio Distribution Profile,高质量音频数据传输的协议,其定义里了传送单声道或立体声等高质量音频(区别于蓝牙SCO链路上传输的普通语音)信息的协议和过程。A2DP的典型应用是将音乐播放器的音频数据发送到耳机或音箱。
A2DP定义了两种角色:

Audio Source(音频源) 音频的输入端对音频数据进行编码,发送到Sink端。
Audio Sink(音频接收器) 接收到音频数据后,进行解码操作还原出音频。


##

2 A2DP profile ##
要想操作A2DP相关,首先要获取A2DP代理对象,获取代理对象的方法比较简单,如下:

mBtAdapter = BluetoothAdapter.getDefaultAdapter();if(!mBtAdapter.isEnabled()){//弹出对话框提示用户是后打开  Intent enabler = new Intent(BluetoothAdapter.ACTION_REQUEST_ENABLE);  startActivityForResult(enabler, 1);}//获取A2DP代理对象mBtAdapter.getProfileProxy(mContext, mListener, BluetoothProfile.A2DP);

getProfileProxy并不会直接返回A2DP代理对象,而是通过mListener中回调获取。

private ServiceListener mListener = new ServiceListener() {@Overridepublic void onServiceDisconnected(int profile) {if(profile == BluetoothProfile.A2DP){mA2dp = null;}}@Overridepublic void onServiceConnected(int profile, BluetoothProfile proxy) {if(profile == BluetoothProfile.A2DP){mA2dp = (BluetoothA2dp) proxy; //转换}}};

成功会回调mListener中的onServiceConnected函数,判断proflie是否为BluetoothProfile.A2DP,转换为BluetoothA2dp对象。通过代理对象即可进行A2DP的相关操作了。


##

3 A2DP操作 ##
A2DP连接首先需要与蓝牙耳机进行配对,如何配对这里就不细说了。
我这里是连接到之前配对过的一个设备。设备名称为:

private final String BT_NAME = "QCY-QY7";

获取该设备,首先获取配对的蓝牙设备,然后遍历这些蓝牙设备,找出蓝牙名称符合条件的设备,就是要操作的设备,

//获取配对的蓝牙设备Set bondDevice = mBtAdapter.getBondedDevices();for(BluetoothDevice device:bondDevice){//获取指定名称的设备if(BT_NAME.equals(device.getName())){mConnectDevice = device;}}

mConnectDevice为要操作的设备。
1 A2DP连接

private void connectA2dp(BluetoothDevice device){setPriority(mConnectDevice, 100); //设置prioritytry {//通过反射获取BluetoothA2dp中connect方法(hide的),进行连接。Method connectMethod =BluetoothA2dp.class.getMethod("connect",BluetoothDevice.class);connectMethod.invoke(mA2dp, device);} catch (Exception e) {e.printStackTrace();} }

BluetoothA2dp中的connect方法是hide的,不能直接访问,需要通过反射的机制获取该方法进行连接。连接成功后手机可以播放音乐,声音就会从蓝牙耳机出来。
2 断开连接

private void disConnectA2dp(BluetoothDevice device){setPriority(mConnectDevice, 0);try {//通过反射获取BluetoothA2dp中connect方法(hide的),断开连接。Method connectMethod =BluetoothA2dp.class.getMethod("disconnect",BluetoothDevice.class);connectMethod.invoke(mA2dp, device);} catch (Exception e) {e.printStackTrace();}}

BluetoothA2dp中的disconnect方法也是hide的,与connect类似。
3 设置优先级

变量
PRIORITY_OFF 0
PRIORITY_ON 100
PRIORITY_AUTO_CONNECT 1000
PRIORITY_UNDEFINED -1

设置优先级是必要的,否则可能导致连接或断开连接失败等问题。

public void setPriority(BluetoothDevice device, int priority) {    if (mA2dp == null) return;    try {//通过反射获取BluetoothA2dp中setPriority方法(hide的),设置优先级    Method connectMethod =BluetoothA2dp.class.getMethod("setPriority",     BluetoothDevice.class,int.class);    connectMethod.invoke(mA2dp, device, priority);    } catch (Exception e) {e.printStackTrace();}}

4 获取优先级

public int getPriority(BluetoothDevice device) {int priority = 0;    if (mA2dp == null) return priority;    try {//通过反射获取BluetoothA2dp中getPriority方法(hide的),获取优先级    Method connectMethod =BluetoothA2dp.class.getMethod("getPriority",     BluetoothDevice.class);    priority = (Integer) connectMethod.invoke(mA2dp, device);    } catch (Exception e) {e.printStackTrace();}    return priority;}

5 获取与某设备A2DP连接状态

mA2dp.getConnectionState(device);

6 获取连接设备列表

//返回值类型ListmA2dp.getConnectedDevices();

7 A2DP是否正在发送音频流

//返回值类型boolean,表示设备是否在通过A2DP发送音频流。mA2dp.isA2dpPlaying(device);

##

4 状态监听 ##
通过广播接收者监听A2DP连接状态的改变,A2DP播放状态的改变。

private void initReceiver(){//注册广播接收者监听状态改变IntentFilter filter = new IntentFilter(BluetoothA2dp.ACTION_CONNECTION_STATE_CHANGED);filter.addAction(BluetoothA2dp.ACTION_PLAYING_STATE_CHANGED);registerReceiver(mReceiver, filter);}

广播接收者,通过intent获取状态值。

private BroadcastReceiver mReceiver = new BroadcastReceiver() {@Overridepublic void onReceive(Context context, Intent intent) {String action = intent.getAction();Log.i(TAG,"onReceive action="+action);//A2DP连接状态改变if(action.equals(BluetoothA2dp.ACTION_CONNECTION_STATE_CHANGED)){int state = intent.getIntExtra(BluetoothA2dp.EXTRA_STATE, BluetoothA2dp.STATE_DISCONNECTED);Log.i(TAG,"connect state="+state);}else if(action.equals(BluetoothA2dp.ACTION_PLAYING_STATE_CHANGED)){//A2DP播放状态改变int state = intent.getIntExtra(BluetoothA2dp.EXTRA_STATE, BluetoothA2dp.STATE_NOT_PLAYING);Log.i(TAG,"play state="+state);}}};

有问题欢迎交流指正。
连接小demo:http://www.demodashi.com/demo/14624.html

欢迎扫一扫关注我的微信公众号,定期推送优质技术文章:

更多相关文章

  1. android 项目中规范使用SharedPreferences
  2. Android(安卓)定位当前位置可能出现的问题
  3. Android学习笔记_12_网络通信之从web获取资源数据到Android
  4. Android(安卓)SSH BusyBox
  5. android 2.3 wifi (二)
  6. ADT在线安装连接不上的解决办法
  7. android 点击分享内容中的连接地址在应用中打开浏览
  8. android无线调试
  9. 命令获取 Eclipse Android(安卓)证书指纹 MD5、SHA1

随机推荐

  1. Android 使用shape来优化界面效果
  2. 【Android NDK 开发】Ubuntu 函数库交叉
  3. mac上的android apk安装器
  4. Android RelativeLayout
  5. Android中使用Context?这几点要注意
  6. Android中RelativeLayout各个属性,例如:and
  7. Android Studio 1.0 苹果电脑安装配置
  8. Android工具箱之组织你的代码文件
  9. Android 应用程序基础知识(1)
  10. AndroidDevTools收集整理Android开发所需