Warning: file_get_contents(/data/phpspider/zhask/data//catemap/0/iphone/43.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Iphone 检测是否将耳机(非麦克风)插入iOS设备_Iphone_Ipad_Ios - Fatal编程技术网

Iphone 检测是否将耳机(非麦克风)插入iOS设备

Iphone 检测是否将耳机(非麦克风)插入iOS设备,iphone,ipad,ios,Iphone,Ipad,Ios,我需要根据是否插入耳机来更改音频。我知道kAudioSessionProperty_AudioInputAvailable,它会告诉我是否有麦克风,但我想测试任何耳机,而不仅仅是带有内置麦克风的耳机。这可能吗?这里有一个我自己的方法,它是在这个网站上找到的方法的一个稍加修改的版本: 我从上面jpsetung给出的代码开始,但在我的用例中有一些问题: 文档中没有所谓的kAudioSessionProperty\u AudioRoute的证据 泄漏路线 无音频会话检查 耳机的字符串检查,而不是类别

我需要根据是否插入耳机来更改音频。我知道kAudioSessionProperty_AudioInputAvailable,它会告诉我是否有麦克风,但我想测试任何耳机,而不仅仅是带有内置麦克风的耳机。这可能吗?

这里有一个我自己的方法,它是在这个网站上找到的方法的一个稍加修改的版本:


我从上面jpsetung给出的代码开始,但在我的用例中有一些问题:

  • 文档中没有所谓的
    kAudioSessionProperty\u AudioRoute
    的证据
  • 泄漏
    路线
  • 无音频会话检查
  • 耳机的字符串检查,而不是类别的逻辑感知
  • 我更感兴趣的是iPhone是否在使用扬声器,“耳机”的意思是“扬声器以外的任何东西”。我觉得忽略诸如“蓝牙”、“airplay”或“lineout”之类的选项是危险的
此实现扩展了检查范围,以允许任何类型的指定输出:

BOOL isAudioRouteAvailable(CFStringRef routeType)
{
    /*
    As of iOS 5:
    kAudioSessionOutputRoute_LineOut;
    kAudioSessionOutputRoute_Headphones;
    kAudioSessionOutputRoute_BluetoothHFP;
    kAudioSessionOutputRoute_BluetoothA2DP;
    kAudioSessionOutputRoute_BuiltInReceiver;
    kAudioSessionOutputRoute_BuiltInSpeaker;
    kAudioSessionOutputRoute_USBAudio;
    kAudioSessionOutputRoute_HDMI;
    kAudioSessionOutputRoute_AirPlay;
    */

    //Prep
    BOOL foundRoute = NO;
    CFDictionaryRef description = NULL;

    //Session
    static dispatch_once_t onceToken;
    dispatch_once(&onceToken, ^{
        AudioSessionInitialize(NULL, NULL, NULL, NULL);
    });

    //Property
    UInt32 propertySize;
    AudioSessionGetPropertySize(kAudioSessionProperty_AudioRouteDescription, &propertySize);
    OSStatus error = AudioSessionGetProperty(kAudioSessionProperty_AudioRouteDescription, &propertySize, &description);
    if ( !error && description ) {
        CFArrayRef outputs = CFDictionaryGetValue(description, kAudioSession_AudioRouteKey_Outputs);
        CFIndex count = CFArrayGetCount(outputs);
        if ( outputs && count ) {
            for (CFIndex i = 0; i < count; i++) {
                CFDictionaryRef route = CFArrayGetValueAtIndex(outputs, i);
                CFStringRef type = CFDictionaryGetValue(route, kAudioSession_AudioRouteKey_Type);
                NSLog(@"Got audio route %@", type);

                //Audio route type
                if ( CFStringCompare(type, routeType, 0) == kCFCompareEqualTo ) {
                    foundRoute = YES;
                    break;
                }
            }
        }
    } else if ( error ) {
        NSLog(@"Audio route error %ld", error);
    }

    //Cleanup
    if ( description ) {
        CFRelease(description);
    }

    //Done
    return foundRoute;  
}

只是为这篇文章的未来读者做个准备


随着iOS 7的发布,大多数AVToolbox方法已被弃用,因此音频监听器现在基本上是冗余的

以下是基于rob mayoff评论的解决方案:

- (BOOL)isHeadsetPluggedIn
{
    AVAudioSessionRouteDescription *route = [[AVAudioSession sharedInstance] currentRoute];

    BOOL headphonesLocated = NO;
    for( AVAudioSessionPortDescription *portDescription in route.outputs )
    {
        headphonesLocated |= ( [portDescription.portType isEqualToString:AVAudioSessionPortHeadphones] );
    }
    return headphonesLocated;
}

只需链接到AVFoundation框架。

@Brad Larson该问题的答案没有提供我需要的信息。我的问题是指耳机,而不是麦克风。我相信你链接的问题的公认答案描述了如何检测麦克风是否插入。是的,我猜你问的是一个更精细的问题,仅仅检测音频输入是不够的。也许周围的一些讨论也会有帮助。谢谢你向我指出这个问题。也许,近两年过去了,你应该接受答案…?这似乎不起作用:(想更新你的答案吗?什么不起作用?不编译?我在游戏中使用这段代码,它对我有效。无论我的耳机是否插入,都会返回否插入耳机时的“错误”和“路由”值是多少?这是正常的,它只在实际设备上起作用。请检查
-[AVAudioSession currentRoute]
对于从iOS 6.0开始的此信息的Objective-C接口,这绝对是一个好注意事项,但前提是您正在链接到AVFoundation(上面的代码用于AudioToolbox)太棒了!!!!工作完美。:)
if ( isAudioRouteAvailable(kAudioSessionOutputRoute_BuiltInSpeaker) ) {
    //Do great things...
}
- (BOOL)isHeadsetPluggedIn
{
    AVAudioSessionRouteDescription *route = [[AVAudioSession sharedInstance] currentRoute];

    BOOL headphonesLocated = NO;
    for( AVAudioSessionPortDescription *portDescription in route.outputs )
    {
        headphonesLocated |= ( [portDescription.portType isEqualToString:AVAudioSessionPortHeadphones] );
    }
    return headphonesLocated;
}