2012-05-25 3 views
9

私は、メッセージングを行うiPadのiMessageアプリに似たアプリを作成しています。したがって、キーボードが表示されているときは、メッセージビューの下部に入力ビューが固定され、アクセサリビューが入力されます。また、ドッキングまたはドッキング解除中にキーボードが表示されている場合は、メッセージビューのサイズを適切に変更する必要があります。iPad分割キーボード

問題は、UIKeyboardWillChangeFrameNotificationからの通知データが一貫していないことです。

まず、ユーザがキーボードのドッキングを解除することができ、3つの方法があります。

  1. は、長押し、次に右下のキーを押し続けると、
  2. をスライドさせ、右下のキーを、メニューがポップアップしたときに、ケース#1は、「スプリット」

を選択し、メニューがポップアップし、右下のキーを、押し続けると、

  • を「ドッキング解除」を選択し、UIKeyboardWillChangeFrameNotificationからの通知データがあります構成するent。

    userInfo = { 
        UIKeyboardFrameBeginUserInfoKey = "NSRect: {{0, 0}, {768, 304}}"; 
    } 
    

    ケース#2、#3のデータについては、私が受け取る何をここで、矛盾しているされています:ここにデータがある

    userInfo = { 
        UIKeyboardAnimationCurveUserInfoKey = 0; 
        UIKeyboardAnimationDurationUserInfoKey = "0.25"; 
        UIKeyboardBoundsUserInfoKey = "NSRect: {{0, 0}, {768, 304}}"; 
        UIKeyboardCenterBeginUserInfoKey = "NSPoint: {384, 872}"; 
        UIKeyboardCenterEndUserInfoKey = "NSPoint: {384, 1136}"; 
        UIKeyboardFrameBeginUserInfoKey = "NSRect: {{0, 0}, {768, 304}}"; 
        UIKeyboardFrameChangedByUserInteraction = 0; 
        UIKeyboardFrameEndUserInfoKey = "NSRect: {{0, -264}, {768, 304}}"; 
    } 
    

    何ここで奇数であることである私は、ケースの下UIKeyboardDidChangeFrameNotificationをリッスンするとき#2または#3の場合、データは期待どおりに表示されます。

    なぜ通知データが異なるのですか?誰かがスプリットキーボードイベントを検出する明確な方法を見つけましたか?

  • 答えて

    3

    明確な方法ではありません。

    私は、次の手順でこの悩みを解決:

    1. は、現在の向きを取得します。
    2. 向きが横の場合、UImacboardFrameEndUserInfoKeyのの高さがになります。それは216に等しくなければなりません。これは、キーボードが分割モードであることを意味します。
    3. 向きがポートレートの場合、UImacboardFrameEndUserInfoKeyのの高さがになります。それは216に等しくなければなりません。これは、キーボードが分割モードであることを意味します。

    私はgist for example.をconvertRectメソッドで更新します。

    +0

    これは、iPad Miniが導入されて以来、もっと難しくなるだろう。私はまだiOS 7に触れていない... –

    +2

    違いはありません。 216はピクセルではなく、解像度とは無関係な点のパルメータです。しかし、これはiPhone 4と5では機能しません。また、iPhoneにはキーボードが分割されていません。彼らはフォームファクタを変えます。 – Bimawa

    +0

    これは良い解決策ではありません。キーボードの高さは、ロケール、バージョン、デバイスによって異なります。 – capikaw

    1

    これは、キーボードが分割されているかどうかを判断するためのややハックですが、信頼できる方法です。これが機能するためには明らかに

    NSArray *classPath = @[ 
        @"KeyboardAutomatic", 
        @"KeyboardImpl", 
        @"KeyboardLayoutStar", 
        @"KBKeyplaneView", 
        @"KBSplitImageView" 
    ]; 
    UIView *splitView = textField.inputAccessoryView.superview; 
    for (NSString *className in classPath) { 
        for (UIView *subview in splitView.subviews) { 
        if ([NSStringFromClass([subview class]) rangeOfString:className].location != NSNotFound) { 
         splitView = subview; 
         break; 
        } 
        } 
    } 
    BOOL isSplit = [splitView.subviews count] > 1; 
    

    あなたは非nilのinputAccessoryViewとのUITextField/UITextViewを(あなたはちょうどそれのために空のビューを使用することができます)が必要です。

    注:textField.inputAccessoryView.superviewの行動はかなり凝り性で、通常superviewを呼び出す前に、一度表示されたキーボードに依存します。また、App Storeの提出プロセスに合格するために、プライベートクラスの名前から 'UI'プレフィックスを削除しました。それはAppleがあなたのアプリにフラグを立てることを保証するものではありませんが、このアプローチはこれまでに成功しています。

    私はiOS7でテストしましたが、他のバージョンのiOSでは動作しないのであれば、同様のアプローチを使用できます。

    +0

    これはうまくいくかもしれませんが、なぜサブビュー0 0 1 0にアクセスしますか? –

    +0

    これは、実際にキーボードをレンダリングするプライベートクラスを探しているビューの階層をたどるためです。私は[Reveal](http://revealapp.com)を使用して、キーボードビューの状態を確認しました。 [ここ](http://imgur.com/v8rFMKP)を参照してください。 – cagey

    +0

    この正確なコードを本番環境で使用することは明らかに悪い考えですが、その答えは依然として一部の人には役立つことを願っています。 – cagey

    関連する問題