如何找到iOS8上使用的当前键盘?

时间:2014-10-02 01:48:49

标签: ios keyboard ios8 nsuserdefaults

您可以使用以下命令获取iOS设备上安装的键盘列表:

NSUserDefaults *userDeafaults = [NSUserDefaults standardUserDefaults];
NSDictionary * userDefaultsDict = [userDeafaults dictionaryRepresentation];
NSLog(@"%@", userDefaultsDict);

这会在控制台中产生一些内容:

{
    ...
    AppleKeyboards =     (
        "en_US@hw=US;sw=QWERTY",
        "es_ES@hw=Spanish - ISO;sw=QWERTY-Spanish",
        "emoji@sw=Emoji",
        "com.swiftkey.SwiftKeyApp.Keyboard"
    );
    AppleKeyboardsExpanded = 1;
    ...
}

这告诉我该设备已安装了西班牙语,表情符号和SwiftKey键盘,但它没有告诉我键盘出现时将使用哪个键盘。

有办法告诉吗?

4 个答案:

答案 0 :(得分:15)

没有这方面的公共API,但我找到了一个解决方案,这需要非常少的灰色区域API" (我将API定义为"灰色区域"如果API通常不会公开,但可以隐藏,几乎没有工作)。

iOS有以下类:UITextInputMode

此类为您提供用户可以使用的所有输入方法。使用以下查询将为您提供当前使用的仅在键盘打开时

UITextInputMode* inputMode = [[[UITextInputMode activeInputModes] filteredArrayUsingPredicate:[NSPredicate predicateWithFormat:@"isDisplayed = YES"]] lastObject];

要获取扩展程序(或常规Apple键盘)的显示名称,请使用:

[inputMode valueForKey:@"displayName"]

[inputMode valueForKey:@"extendedDisplayName"]

仅在键盘可见时才有效。因此,您必须使用

自行监控输入模式
[[NSNotificationCenter defaultCenter] addObserverForName:UITextInputCurrentInputModeDidChangeNotification object:nil queue:[NSOperationQueue mainQueue] usingBlock:^(NSNotification *note)
 {
     dispatch_async(dispatch_get_main_queue(), ^{
         NSLog(@"%@", [[[[UITextInputMode activeInputModes] filteredArrayUsingPredicate:[NSPredicate predicateWithFormat:@"isDisplayed = YES"]] lastObject] valueForKey:@"extendedDisplayName"]);
     });
 }];

我们实际上需要延迟获取当前输入模式,因为在键盘内部实现使用新值更新系统之前发送通知。在下一个runloop上获得它很有效。

答案 1 :(得分:3)

Leo Natan的答案很棒,但我想补充一点。您实际上可以随时获取当前输入模式,而不仅仅是键盘打开时,如下所示:

UITextView *textView = [[UITextView alloc] init];
UITextInputMode *inputMode = textView.textInputMode;

请注意,出于某种原因,textView.textInputMode对于表情符号键盘来说是nil

此外,除了displayNameextendedDisplayName之外,您还可以检索其他键,例如identifiernormalizedIdentifier(iOS 8 +),{{1 },...在这里查看完整的API:

https://github.com/nst/iOS-Runtime-Headers/blob/master/Frameworks/UIKit.framework/UIKeyboardInputMode.h

现在我不确定使用其中任何一个比App Store批准的hardwareLayout风险更大......

答案 2 :(得分:0)

@Leo Natan的答案很酷但是当键盘没有显示时,它可能会返回nil

所以我在这里使用字符串来查找UIKeyboardInputMode的属性。

我可以告诉你,这可以找到当前的键盘,因为它来自Apple的私有API。

代码在这里:

+ (BOOL)isTheCustomKeyboard
{
    UITextInputMode* inputMode = [UITextInputMode currentInputMode];
    if ([inputMode respondsToSelector:NSSelectorFromString(@"identifier")])
    {
        NSString* indentifier = [inputMode performSelector:NSSelectorFromString(@"identifier")];
        if ([indentifier isEqualToString: YOUR_APP_ID])
        {
            return YES;
        }
    }
   return NO;
}

还有更多:

+ (BOOL)isContaintCustomKeyboard
{
    NSArray * inputModes = [UITextInputMode activeInputModes];
    for (id inputModel in inputModes)
    {
        if ([inputModel respondsToSelector:NSSelectorFromString(@"identifier")])
        {
            NSString* indentifier = [inputModel performSelector:NSSelectorFromString(@"identifier")];
            if ([indentifier isEqualToString: YOUR_APP_ID])
            {
                return YES;
            }
        }
    }
    return NO;
}

实际上,我们也可以使用displayNameidentifier以及更多。

答案 3 :(得分:0)

对我来说它适用于Swift 5.0

 NotificationCenter.default.addObserver(self, selector: #selector(keyBoardChanged(_:)), name:UITextInputMode.currentInputModeDidChangeNotification, object: nil)

  @objc func keyBoardChanged(_ notification: NSNotification){
    if let identifier = textField.textInputMode?.perform(NSSelectorFromString("identifier"))?.takeUnretainedValue() as? String{
        if identifier == "YOUR APP IDENTIFIER"{
            //Do Whatever you required :) 
        }
    }
 }