Android蓝牙开发:如何连接蓝牙设备实现音频播放
安卓蓝牙音箱音频输出实现方案
你现有代码只完成了蓝牙开关、可发现性配置、已配对设备列表查询的基础逻辑,要实现音频输出到蓝牙音箱,核心是走A2DP蓝牙音频传输协议完成设备连接+音频路由配置,具体实现步骤如下:
一、前置配置补充
1. 清单文件权限补全
在AndroidManifest.xml中添加对应权限,按安卓版本做适配:
<!-- 安卓12及以上版本蓝牙权限 --> <uses-permission android:name="android.permission.BLUETOOTH_CONNECT" /> <uses-permission android:name="android.permission.BLUETOOTH_SCO" /> <!-- 安卓11及以下版本蓝牙权限 --> <uses-permission android:name="android.permission.BLUETOOTH" android:maxSdkVersion="30" /> <uses-permission android:name="android.permission.BLUETOOTH_ADMIN" android:maxSdkVersion="30" /> <!-- 音频设置修改权限 --> <uses-permission android:name="android.permission.MODIFY_AUDIO_SETTINGS" />
注意安卓6.0以上的危险权限、安卓12以上的新版蓝牙权限需要做动态申请,否则会触发权限拒绝报错。
2. 核心实现逻辑说明
蓝牙音频播放不依赖普通蓝牙Socket连接,系统已经封装了BluetoothA2dp代理类专门处理音频流传输,搭配AudioManager完成音频路由确认即可,不需要自己实现底层音频传输协议。
二、核心功能代码实现
1. 新增全局变量
在现有MainActivity的基础上补充以下全局变量:
private BluetoothA2dp mBluetoothA2dp; private AudioManager mAudioManager; private BluetoothDevice mTargetDevice; // A2DP服务连接状态监听 private BluetoothProfile.ServiceListener mProfileListener = new BluetoothProfile.ServiceListener() { @Override public void onServiceConnected(int profile, BluetoothProfile proxy) { if (profile == BluetoothProfile.A2DP) { mBluetoothA2dp = (BluetoothA2dp) proxy; // 代理绑定完成后发起目标设备连接 connectA2dpDevice(); } } @Override public void onServiceDisconnected(int profile) { if (profile == BluetoothProfile.A2DP) { mBluetoothA2dp = null; } } };
2. 初始化服务代理
在onCreate方法末尾补充初始化逻辑:
// 初始化音频管理器 mAudioManager = (AudioManager) getSystemService(Context.AUDIO_SERVICE); // 绑定A2DP代理服务 BA.getProfileProxy(this, mProfileListener, BluetoothProfile.A2DP); // 注册A2DP连接状态广播 IntentFilter filter = new IntentFilter(BluetoothA2dp.ACTION_CONNECTION_STATE_CHANGED); registerReceiver(mA2dpReceiver, filter);
3. 实现A2DP设备连接方法
新增连接方法,选中目标音箱设备后调用:
private void connectA2dpDevice() { if (mBluetoothA2dp == null || mTargetDevice == null) return; // 反射调用系统隐藏connect方法,普通第三方应用可正常调用,是蓝牙音频类应用的通用实现 try { Method connectMethod = mBluetoothA2dp.getClass().getMethod("connect", BluetoothDevice.class); connectMethod.invoke(mBluetoothA2dp, mTargetDevice); } catch (Exception e) { e.printStackTrace(); } }
注意:
BluetoothA2dp.connect()是系统隐藏API,不需要系统签名权限,反射即可正常调用。
4. 给已配对设备列表加点击触发逻辑
修改现有list方法,给ListView加item点击事件,点击对应设备时触发连接:
public void list(View v){ pairedDevices = BA.getBondedDevices(); ArrayList<String> list = new ArrayList<>(); // 同步存储设备对象,方便点击时获取对应BluetoothDevice实例 ArrayList<BluetoothDevice> deviceList = new ArrayList<>(); for(BluetoothDevice bt : pairedDevices) { list.add(bt.getName()); deviceList.add(bt); } Toast.makeText(getApplicationContext(), "Showing Paired Devices",Toast.LENGTH_SHORT).show(); final ArrayAdapter adapter = new ArrayAdapter(this,android.R.layout.simple_list_item_1, list); lv.setAdapter(adapter); // 新增item点击连接逻辑 lv.setOnItemClickListener((parent, view, position, id) -> { mTargetDevice = deviceList.get(position); if (mBluetoothA2dp != null) { connectA2dpDevice(); } }); }
5. 监听连接状态确认音频路由
定义广播接收器监听A2DP连接状态,连接成功后确认音频路由切到蓝牙:
private final BroadcastReceiver mA2dpReceiver = new BroadcastReceiver() { @Override public void onReceive(Context context, Intent intent) { String action = intent.getAction(); if (BluetoothA2dp.ACTION_CONNECTION_STATE_CHANGED.equals(action)) { int state = intent.getIntExtra(BluetoothProfile.EXTRA_STATE, BluetoothProfile.STATE_DISCONNECTED); if (state == BluetoothProfile.STATE_CONNECTED) { // A2DP连接成功后系统默认会切媒体音频到蓝牙,主动调用接口确认路由 mAudioManager.setMode(AudioManager.MODE_NORMAL); mAudioManager.setBluetoothA2dpOn(true); Toast.makeText(MainActivity.this, "蓝牙音箱连接成功,音频将从音箱输出", Toast.LENGTH_SHORT).show(); // 此时启动MediaPlayer播放音频即可正常从蓝牙音箱出声 } else if (state == BluetoothProfile.STATE_DISCONNECTED) { mAudioManager.setBluetoothA2dpOn(false); Toast.makeText(MainActivity.this, "蓝牙音箱已断开", Toast.LENGTH_SHORT).show(); } } } };
最后在onDestroy方法中补充资源释放逻辑:注销广播、关闭A2DP代理,避免内存泄漏。
三、常见踩坑点
- 配对不等于连接:已配对设备列表只代表设备曾经完成绑定,必须主动走A2DP连接流程才能传输音频
- 不要在A2DP未连接成功时启动音频播放,否则音频会默认从手机扬声器输出
- 如果需要实现蓝牙通话音频输出,额外处理HFP协议+SCO音频链路即可,媒体音频仅需A2DP协议就能正常工作
- 安卓不同版本的蓝牙权限差异较大,必须做版本适配,否则会出现功能正常但高版本系统无法使用的问题
内容的提问来源于stack exchange,提问作者Arron Lapta
相关产品推荐
相关产品推荐

