diff --git a/README.md b/README.md
index ea3884e..efc1ca1 100644
--- a/README.md
+++ b/README.md
@@ -91,6 +91,28 @@ You can register to `ScrollViewResponder` events `onKeyboardWillShow` and `onKey
```
+## Android Support
+First, Android natively has this feature, you can easily enable it by setting `windowSoftInputMode` in `AndroidManifest.xml`. Check [here](https://developer.android.com/guide/topics/manifest/activity-element.html#wsoft).
+
+But if you want to use feature like `extraHeight`, you need to enable Android Support with the following steps:
+
+- Make sure you are using react-native `0.46` or above.
+- Set `windowSoftInputMode` to `adjustPan` in `AndroidManifest.xml`.
+- Set `enableOnAndroid` property to `true`.
+
+Android Suppor is not perfect, here is the support list:
+
+| **Prop** | **Android Support** |
+|----------|-----------------|
+| `viewIsInsideTabBar` | Yes |
+| `resetScrollToCoords` | Yes |
+| `enableAutoAutomaticScroll` | Yes |
+| `extraHeight` | Yes |
+| `extraScrollHeight` | Yes |
+| `enableResetScrollToCoords` | Yes |
+| `keyboardOpeningTime` | No |
+
+
## API
### Props
All the `ScrollView`/`ListView` props will be passed.
@@ -104,6 +126,7 @@ All the `ScrollView`/`ListView` props will be passed.
| `extraScrollHeight` | `number` | Adds an extra offset to the keyboard. Useful if you want to stick elements above the keyboard. |
| `enableResetScrollToCoords` | `boolean` | Lets the user enable or disable automatic resetScrollToCoords. |
| `keyboardOpeningTime` | `number` | Sets the delay time before scrolling to new position, default is 250 |
+| `enableOnAndroid` | `boolean` | Enable Android Support |
| **Method** | **Parameter** | **Description** |
|------------|---------------|-----------------|
diff --git a/lib/KeyboardAwareListView.js b/lib/KeyboardAwareListView.js
index 961d13c..ade8b5a 100644
--- a/lib/KeyboardAwareListView.js
+++ b/lib/KeyboardAwareListView.js
@@ -2,7 +2,7 @@
import React from 'react'
import createReactClass from 'create-react-class'
-import { ListView } from 'react-native'
+import { ListView, Platform } from 'react-native'
import PropTypes from 'prop-types'
import KeyboardAwareMixin from './KeyboardAwareMixin'
@@ -14,6 +14,7 @@ const KeyboardAwareListView = createReactClass({
y: PropTypes.number.isRequired,
}),
onScroll: PropTypes.func,
+ enableOnAndroid: PropTypes.bool,
},
mixins: [KeyboardAwareMixin],
@@ -30,15 +31,32 @@ const KeyboardAwareListView = createReactClass({
},
render: function () {
+ const {
+ enableOnAndroid,
+ contentContainerStyle,
+ } = this.props
+
+ const {
+ keyboardSpace,
+ } = this.state
+
+ let newContentContainerStyle
+
+ if (Platform.OS === 'android' && enableOnAndroid) {
+ newContentContainerStyle = Object.assign({}, contentContainerStyle)
+ newContentContainerStyle.paddingBottom = (newContentContainerStyle.paddingBottom || 0) + keyboardSpace
+ }
+
return (
)
diff --git a/lib/KeyboardAwareMixin.js b/lib/KeyboardAwareMixin.js
index a939196..467dc7c 100644
--- a/lib/KeyboardAwareMixin.js
+++ b/lib/KeyboardAwareMixin.js
@@ -1,7 +1,7 @@
/* @flow */
import PropTypes from 'prop-types'
-import ReactNative, { TextInput, Keyboard, UIManager } from 'react-native'
+import ReactNative, { TextInput, Keyboard, UIManager, Platform } from 'react-native'
import TimerMixin from 'react-timer-mixin'
const _KAM_DEFAULT_TAB_BAR_HEIGHT: number = 49
@@ -70,8 +70,28 @@ const KeyboardAwareMixin = {
if (isAncestor) {
// Check if the TextInput will be hidden by the keyboard
UIManager.measureInWindow(currentlyFocusedField, (x, y, width, height) => {
- if (y + height > frames.endCoordinates.screenY - this.props.extraScrollHeight - this.props.extraHeight) {
- this.scrollToFocusedInputWithNodeHandle(currentlyFocusedField)
+ const textInputBottomPosition = y + height
+ const keyboardPosition = frames.endCoordinates.screenY
+ const totalExtraHeight = this.props.extraScrollHeight + this.props.extraHeight
+
+ if (Platform.OS === 'ios') {
+ if (textInputBottomPosition > keyboardPosition - totalExtraHeight) {
+ this.scrollToFocusedInputWithNodeHandle(currentlyFocusedField)
+ }
+ } else {
+
+ // on android, the system would scroll the text input just above the keyboard
+ // so we just neet to scroll the extra height part
+ if (textInputBottomPosition > keyboardPosition) {
+ // since the system already scrolled the whole view up
+ // we should reduce that amount
+ keyboardSpace = keyboardSpace - (textInputBottomPosition - keyboardPosition)
+ this.setState({keyboardSpace})
+
+ this.scrollForExtraHeightOnAndroid(totalExtraHeight)
+ } else if (textInputBottomPosition > keyboardPosition - totalExtraHeight) {
+ this.scrollForExtraHeightOnAndroid(totalExtraHeight - (keyboardPosition - textInputBottomPosition))
+ }
}
})
}
@@ -106,8 +126,13 @@ const KeyboardAwareMixin = {
componentDidMount: function () {
// Keyboard events
- this.keyboardWillShowEvent = Keyboard.addListener('keyboardWillShow', this.updateKeyboardSpace)
- this.keyboardWillHideEvent = Keyboard.addListener('keyboardWillHide', this.resetKeyboardSpace)
+ if (Platform.OS === 'ios') {
+ this.keyboardWillShowEvent = Keyboard.addListener('keyboardWillShow', this.updateKeyboardSpace)
+ this.keyboardWillHideEvent = Keyboard.addListener('keyboardWillHide', this.resetKeyboardSpace)
+ } else if (Platform.OS === 'android' && this.props.enableOnAndroid) {
+ this.keyboardWillShowEvent = Keyboard.addListener('keyboardDidShow', this.updateKeyboardSpace)
+ this.keyboardWillHideEvent = Keyboard.addListener('keyboardDidHide', this.resetKeyboardSpace)
+ }
},
componentWillUnmount: function () {
@@ -129,6 +154,10 @@ const KeyboardAwareMixin = {
responder && responder.scrollResponderScrollToEnd({animated: animated})
},
+ scrollForExtraHeightOnAndroid(extraHeight: number) {
+ this.scrollToPosition(0, this.position.y + extraHeight, true)
+ },
+
/**
* @param keyboardOpeningTime: takes a different keyboardOpeningTime in consideration.
* @param extraHeight: takes an extra height in consideration.
diff --git a/lib/KeyboardAwareScrollView.js b/lib/KeyboardAwareScrollView.js
index c26c017..2897975 100644
--- a/lib/KeyboardAwareScrollView.js
+++ b/lib/KeyboardAwareScrollView.js
@@ -2,7 +2,7 @@
import React from 'react'
import createReactClass from 'create-react-class'
-import { ScrollView } from 'react-native'
+import { ScrollView, Platform } from 'react-native'
import PropTypes from 'prop-types'
import KeyboardAwareMixin from './KeyboardAwareMixin'
@@ -14,6 +14,7 @@ const KeyboardAwareScrollView = createReactClass({
x: PropTypes.number,
y: PropTypes.number,
}),
+ enableOnAndroid: PropTypes.bool,
},
mixins: [KeyboardAwareMixin],
@@ -23,15 +24,32 @@ const KeyboardAwareScrollView = createReactClass({
},
render: function () {
+ const {
+ enableOnAndroid,
+ contentContainerStyle,
+ } = this.props
+
+ const {
+ keyboardSpace,
+ } = this.state
+
+ let newContentContainerStyle
+
+ if (Platform.OS === 'android' && enableOnAndroid) {
+ newContentContainerStyle = Object.assign({}, contentContainerStyle)
+ newContentContainerStyle.paddingBottom = (newContentContainerStyle.paddingBottom || 0) + keyboardSpace
+ }
+
return (
{
this.handleOnScroll(e)
this.props.onScroll && this.props.onScroll(e)