React Native Make View “Hug” the Top of the Keyboard

后端 未结 5 1960
陌清茗
陌清茗 2021-02-13 03:48

Let\'s say I have a view that is positioned absolute at the bottom of the screen. This view contains a text input. When the text input is focused, I want the bottom of the view

相关标签:
5条回答
  • 2021-02-13 03:53

    @jazzdle example works great! Thank you for that! Just one addition - in keyboardWillShow method, one can add event.endCoordinates.height so paddingBottom is exact height as keyboard.

        keyboardWillShow = (event) => {
        Animated.timing(this.paddingInput, {
            duration: event.duration,
            toValue: event.endCoordinates.height,
        }).start();
    }
    
    0 讨论(0)
  • 2021-02-13 03:54

    You can use flexbox to bottom position the element. Here's simple example -

      render() {
        return (
          <View style={styles.container}>
            <View style={styles.top}/>
            <View style={styles.bottom}>
              <View style={styles.input}>
                <TextInput/>
              </View>
            </View>
          </View>
        );
      }
    
    const styles = StyleSheet.create({
      container: {
        flex: 1,
        justifyContent: 'center',
        alignItems: 'center',
        backgroundColor: '#F5FCFF',
      },
      top: {
        flex: .8,
      },
      bottom: {
        flex: .2,
      },
      input: {
        width: 200,
      },
    });
    
    0 讨论(0)
  • 2021-02-13 04:04

    Few days ago I have the same problem (although I have a complex view with TextInput as a child) and wanted not only the TextInput to be focused but the whole view to be "attached" to the keyboard. What's finally is working for me is the following code:

    constructor(props) {
        super(props);
        this.paddingInput = new Animated.Value(0);
    }
    
    componentWillMount() {
        this.keyboardWillShowSub = Keyboard.addListener('keyboardWillShow', this.keyboardWillShow);
        this.keyboardWillHideSub = Keyboard.addListener('keyboardWillHide', this.keyboardWillHide);
    }
    
    componentWillUnmount() {
        this.keyboardWillShowSub.remove();
        this.keyboardWillHideSub.remove();
    }
    
    keyboardWillShow = (event) => {
        Animated.timing(this.paddingInput, {
            duration: event.duration,
            toValue: 60,
        }).start();
    };
    
    keyboardWillHide = (event) => {
        Animated.timing(this.paddingInput, {
            duration: event.duration,
            toValue: 0,
        }).start();
    };
    
    render() {
            return (
                <KeyboardAvoidingView behavior='padding' style={{ flex: 1 }}>
                    [...]
                    <Animated.View style={{ marginBottom: this.paddingInput }}>
                        <TextTranslateInput />
                    </Animated.View>
                </KeyboardAvoidingView>
            );
        }
    

    where [..] you have other views.

    0 讨论(0)
  • 2021-02-13 04:09

    Using Functional Component. This works for both iOS and Android

    useEffect(() => {
    const keyboardVisibleListener = Keyboard.addListener(
      Platform.OS === "ios" ? "keyboardWillShow" : "keyboardDidShow",
      handleKeyboardVisible
    );
    const keyboardHiddenListener = Keyboard.addListener(
      Platform.OS === "ios" ? "keyboardWillHide" : "keyboardDidHide",
      handleKeyboardHidden
    );
    
    return () => {
      keyboardHiddenListener.remove();
      keyboardVisibleListener.remove();
    };}, []);
    
    
    const handleKeyboardVisible = (event) => {
    Animated.timing(paddingInput, {
      duration: event.duration,
      toValue: 60,
      useNativeDriver: false,
    });};
    
     const handleKeyboardHidden = (event: any) => {
    Animated.timing(paddingInput, {
      duration: event.duration,
      toValue: 0,
      useNativeDriver: false,
    });};
    
    0 讨论(0)
  • 2021-02-13 04:11

    Custom hook:

    import { useRef, useEffect } from 'react';
    import { Animated, Keyboard, KeyboardEvent } from 'react-native';
    
    export const useKeyboardHeight = () => {
      const keyboardHeight = useRef(new Animated.Value(0)).current;
    
      useEffect(() => {
        const keyboardWillShow = (e: KeyboardEvent) => {
          Animated.timing(keyboardHeight, {
            duration: e.duration,
            toValue: e.endCoordinates.height,
            useNativeDriver: true,
          }).start();
        };
    
        const keyboardWillHide = (e: KeyboardEvent) => {
          Animated.timing(keyboardHeight, {
            duration: e.duration,
            toValue: 0,
            useNativeDriver: true,
          }).start();
        };
    
        const keyboardWillShowSub = Keyboard.addListener(
          'keyboardWillShow',
          keyboardWillShow
        );
        const keyboardWillHideSub = Keyboard.addListener(
          'keyboardWillHide',
          keyboardWillHide
        );
    
        return () => {
          keyboardWillHideSub.remove();
          keyboardWillShowSub.remove();
        };
      }, [keyboardHeight]);
    
      return keyboardHeight;
    };
    
    0 讨论(0)
提交回复
热议问题