android开发获取手机麦克风设备信息

作者为测试蓝牙耳机麦克录音,发现三星、小米自带录音机不支持蓝牙录音,需特定APP。由此设想开发可选择录音源的APP,参考Android音频API介绍文章,询问ChatGPT指定麦克风录音方法但不可用。后续将分析指定录音源设备录音,还实现了设备管理及列表展示。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

之前为了测试蓝牙耳机的麦克,想从蓝牙耳机的麦克录音。尝试发现三星、小米自带的录音机并不能从蓝牙录音。看了网上一篇文章,提供了一个特定的录音APP,才支持开启蓝牙录音功能。

非常令人疑惑。想到现在的手机,有不只一个麦克风,是否能开发一个可选择录音源的录音APP呢?

看了这篇文章Android音频API介绍「转载」-CSDN博客,介绍了几种音频开发模式。

问了ChatGPT指定麦克风录音的方法

// 指定所需的音频输入设备
int audioSource = MediaRecorder.AudioSource.MIC; // 默认的内置麦克风
String desiredDeviceName = "Your_Desired_Device_Name"; // 设备名称

AudioManager audioManager = (AudioManager) getSystemService(Context.AUDIO_SERVICE);
AudioDeviceInfo[] inputDevices = audioManager.getDevices(AudioManager.GET_DEVICES_INPUTS);

// 遍历可用的音频输入设备,查找指定的设备
for (AudioDeviceInfo device : inputDevices) {
    if (device.getType() == AudioDeviceInfo.TYPE_USB_DEVICE && device.getProductName().equals(desiredDeviceName)) {
        // 找到了指定的设备
        audioSource = device.getId();
        break;
    }
}

// 使用指定的音频输入设备创建AudioRecord实例
int sampleRate = 44100; // 采样率,可以根据需要进行调整
int channelConfig = AudioFormat.CHANNEL_IN_MONO; // 单声道,可以根据需要进行调整
int audioFormat = AudioFormat.ENCODING_PCM_16BIT; // 16位PCM,可以根据需要进行调整

int bufferSize = AudioRecord.getMinBufferSize(sampleRate, channelConfig, audioFormat);
AudioRecord audioRecord = new AudioRecord(audioSource, sampleRate, channelConfig, audioFormat, bufferSize);

// 现在您可以使用audioRecord对象来录制音频

其实这段代码,并不可用。其中AudioRecord的原型是这样的

public AudioRecord (int audioSource, 
                int sampleRateInHz, 
                int channelConfig, 
                int audioFormat, 
                int bufferSizeInBytes)

从API手册上查到的audioSource,仅支持如下几项:

Constants

intCAMCORDER

Microphone audio source tuned for video recording, with the same orientation as the camera if available.

intDEFAULT

Default audio source *

intMIC

Microphone audio source

intREMOTE_SUBMIX

Audio source for a submix of audio streams to be presented remotely.

intUNPROCESSED

Microphone audio source tuned for unprocessed (raw) sound if available, behaves like DEFAULT otherwise.

intVOICE_CALL

Voice call uplink + downlink audio source

Capturing from VOICE_CALL source requires the Manifest.permission.CAPTURE_AUDIO_OUTPUT permission.

intVOICE_COMMUNICATION

Microphone audio source tuned for voice communications such as VoIP.

intVOICE_DOWNLINK

Voice call downlink (Rx) audio source.

intVOICE_PERFORMANCE

Source for capturing audio meant to be processed in real time and played back for live performance (e.g karaoke).

intVOICE_RECOGNITION

Microphone audio source tuned for voice recognition.

intVOICE_UPLINK

Voice call uplink (Tx) audio source.

ChatGPT有模有样的瞎编出来一种指定Microphone的方法,这就是它一向比较坑的地方。

也就是说,audioSource与实体设备无法关联,不能通过枚举的方法获得录音源,只能选择默认的几种。这种架构的设计,就是典型的隔离,用AudioRecord接口,不需要了解底层硬件(也无法设置和操作)。后面几篇文章会详细分析,介绍如何指定录音源设备录音。

虽然ChatGPT比较坑,但其中介绍了枚举录音源设备方法和代码,接下来先实现这些设备管理。下面代码是获取设备列表,生成名字后放入Recycler。

                if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M) {
                    AudioManager audioManager = (AudioManager) getSystemService(Context.AUDIO_SERVICE);

                    inputDevices = audioManager.getDevices(AudioManager.GET_DEVICES_INPUTS);

                    for (AudioDeviceInfo device : inputDevices) {
                        int type = device.getType();
                        // 这是麦克风
                        //if (type == AudioDeviceInfo.TYPE_BUILTIN_MIC || type == AudioDeviceInfo.TYPE_USB_DEVICE) {

                        String deviceInfo = "";
                        deviceInfo = "[" + device.getId() + "]" + DeviceTypeString.getDeviceTypeString(device.getType()) + "@";
                        if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.P) {
                            deviceInfo += device.getAddress().toString();
                        }
                        audioInfoList.add(deviceInfo);
                    }

                }

生成一个类型与String对应的Map,我手里的设备有如下几个种类:

        deviceTypeMap.put(AudioDeviceInfo.TYPE_WIRED_HEADPHONES, "有线耳机麦克风");
        deviceTypeMap.put(AudioDeviceInfo.TYPE_BLUETOOTH_SCO, "蓝牙麦克风");
        deviceTypeMap.put(AudioDeviceInfo.TYPE_TELEPHONY, "通话麦克风音频输入");
        deviceTypeMap.put(AudioDeviceInfo.TYPE_BUILTIN_MIC, "内置麦克风");
        deviceTypeMap.put(AudioDeviceInfo.TYPE_FM_TUNER, "FM收音机设备");
        deviceTypeMap.put(AudioDeviceInfo.TYPE_REMOTE_SUBMIX, "虚拟混音设备");

点击Recycler后,显示对应设备的详细信息:

    private void ShowMicrophoneDevice(int microphoneIndex){
        StringBuilder deviceInfo = new StringBuilder();
        AudioDeviceInfo inputDevice = inputDevices[microphoneIndex];
        if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M) {

            deviceInfo.append("产品名称:\t");
            deviceInfo.append(inputDevice.getProductName());

            deviceInfo.append("\n设备类型:\t");
            deviceInfo.append(DeviceTypeString.getDeviceTypeString(inputDevice.getType()));

            deviceInfo.append("\n设备ID:\t");
            deviceInfo.append(inputDevice.getId());

            if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.P) {
                deviceInfo.append("\n设备位置:\t");
                deviceInfo.append(inputDevice.getAddress());
            }

            deviceInfo.append("\n支持采样率:\t");
            deviceInfo.append(getSampleRateInfo(inputDevice.getSampleRates()));

            deviceInfo.append("\n支持Channel数量:\t");
            deviceInfo.append(getChannelCountInfo(inputDevice.getChannelCounts()));

            if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.R) {
                deviceInfo.append("\n支持metadata封装类型:\t");
                deviceInfo.append(getEncapsulationModeInfo(inputDevice.getEncapsulationModes()));
            }

            deviceInfo.append("\n支持Encoding类型:");
            deviceInfo.append(getEncodingInfo(inputDevice.getEncodings()));
        }
        textDeviceInfo.setText(deviceInfo);
    }

最终的效果如下,三星S7手机只有两个设备,我理解物理设备应该是有上下各有一个。通话设备应该是虚拟设备。

小米手机默认有5个设备,插入有线耳机和蓝牙耳机后,也可以列出增加的录音源设备:

评论 3
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值