このライブラリは次の問題に対処します。
windowSoftInputMode をadjustNothing
に設定すると、React Native Keyboard イベント、 keyboardDidHide
およびkeyboardDidShow
動作しなくなります (問題 #2852 を参照)。
キーボードが表示されると、アプリのコンテンツ全体が上に移動します(iOS および Android)。
チャット アプリケーションでは、キーボードを閉じてアクションを表示するときに、下部のテキスト入力を同じ位置に維持する必要があるため、切り替えがそれほどスムーズではありません。
$ yarn add react-native-keyboard-area
React Native > 0.60 を使用することをお勧めします。自動リンクにより、iOS および Android 用のこのライブラリ ネイティブRNKeyboard
モジュールがインストールされます。
iOS の場合: React Native はKeyboardAvoidingView
というコンポーネントを提供します。これでページをラップすると、キーボードが表示されたときにコンテンツが上に移動します。
Android の場合: AndroidManifest.xmlのデフォルトでは、 windowSoftInputModeがadjustResize
に設定されており、キーボードが表示されるとアプリのコンテンツ全体が上に移動するため、 KeyboardAvoidingView
コンポーネントは必要ありません。
どちらの方法でも、ページのコンテンツ全体が上下に移動し、キーボードが表示または非表示になります。
ただし、アプリ全体を上に移動する必要がない場合もあります。最も一般的な例はチャット アプリケーションで、キーボードが消えたときにカスタム ビューに切り替えたい場合があります。
このライブラリは、ラッパー コンポーネントKeyboardArea
作成することで問題を解決します。このコンポーネントは高さを調整し、キーボードが表示または非表示になります。
さらに、 isOpen
プロパティまたは公開されたopen()
およびclose()
メソッドを使用して状態を制御することもできます。
もう 1 つの利点は、メイン ビューのサイズが変わらないため、キーボードが表示されたときに ReactNaive がアプリ全体を再描画しないことです。
Before : ReactNative KeyboardAvoidingView とAdjustResizeを使用すると、結果はあまり良くなく、切り替え後にキーボードが消えるとページが「ジャンプ」します。 | 後: このライブラリを使用すると、ビュー全体は移動せず、入力の下のキーボード領域は切り替え中に同じ高さを維持します。 |
このライブラリには、キーボードの高さが変更されたときにKeyboardSizeChanges
という名前のイベントを通じてKeyboardArea
コンポーネントに通知する iOS および Android のネイティブ コードがいくつか含まれています。
iOS では、 UIResponder
keyboardWillShowNotification とkeyboardWillHideNotification を使用して、現在の高さでイベントを発行します。
Android では、キーボードがビュー全体の上に移動するのを避けるために、 windowSoftInputMode をadjustNothing
に設定する必要があります。その後、レイアウトの変更をリッスンしてキーボードの高さを測定するために、非表示のPopupWindow
を作成します。
ロジックのほとんどはKeyboardArea
コンポーネント内にあります。キーボードが消えたときに表示したいコンテンツをラップし、次の例のようにChatActionsInputコンポーネントを表示する必要があるときにisOpenプロパティを設定するだけです。
** これは上記のスクリーンショットの簡略版です **
import { KeyboardArea , KeyboardAreaRef } from 'react-native-keyboard-area' ;
/// ...
keyboardSpacerRef = createRef < KeyboardSpacerRef > ( ) ;
handleUserClick = ( ) => {
this . keyboardSpacerRef . current ?. close ( ) ;
}
handleChangeMode = ( ) => {
this . setState ( prev => ( {
inputMode :
prev . inputMode === ChatInputModes . Actions
? ChatInputModes . Text
: ChatInputModes . Actions ,
} ) ) ;
}
keyboardAreaHeightChanged = ( isOpen : boolean , currentHeight : number ) => {
// Your logic
} ;
render ( ) {
return (
< PageContent >
< ChatMessageList />
< ChatTextInput onChangeMode = { this . handleChangeMode } />
< KeyboardSpacer
ref = { this . keyboardSpacerRef }
isOpen = { inputMode === ChatInputModes . Actions }
onChange = { this . keyboardAreaHeightChanged }
>
< ChatActionsInput />
</ KeyboardSpacer >
</ PageContent >
) ;
}
Android では、他のページにAdjustResize を使用したい場合があるため、このライブラリsetWindowSoftInputMode
使用して、必要なページのみ SoftInput モードを動的に変更できます。次に例を示します。
import { RNKeyboard , SoftInputMode } from 'react-native-keyboard-area' ;
// Example with react-navigation page focus/blur events
componentDidMount ( ) {
navigation . addListener ( 'blur' , this . componentDidExit ) ;
navigation . addListener ( 'focus' , this . componentDidEnter ) ;
}
componentDidEnter = ( ) => {
if ( Platform . OS === 'android' ) {
RNKeyboard . setWindowSoftInputMode ( SoftInputMode . SOFT_INPUT_ADJUST_NOTHING , ) ;
}
} ;
componentDidExit = ( ) => {
if ( Platform . OS === 'android' ) {
RNKeyboard . setWindowSoftInputMode ( SoftInputMode . SOFT_INPUT_ADJUST_RESIZE ) ;
}
} ;
componentWillUnmount ( ) {
navigation . removeListener ( 'blur' , this . componentDidExit ) ;
navigation . removeListener ( 'focus' , this . componentDidEnter ) ;
}
Android の場合、 PopupWindow
アイデアの実装についてはすべて Cristian Holdunu と Siebe Brouwer に与えられ、キーボードの高さを計算するために、それを React Native モジュール システムに移植しました。