React-Native解决键盘遮挡问题(Keyboard遮挡问题)
来源:互联网 发布:阿里云服务云管家 编辑:程序博客网 时间:2024/04/29 08:36
参考:http://blog.csdn.net/pz789as/article/details/53079025
在开发中经常遇到需要输入的地方,RN给我们提过的TextInput虽然好用,可惜并没有处理遮挡问题。
很多时候键盘弹出来都会遮挡住编辑框,让人很头疼。
本来想在js.coach 库里面找一找第三方的插件,看到最好的一个就是react-native-keyboard-spacer了,然而我们还差一个东西,那就是获取键盘的高度。
这个我也查了半天并没有提供,获取没找到吧。于是只好自己写原生模块去获取键盘的高度了。
关于原生IOS获取键盘高度我就不多说了,网上一大堆,我直接贴上我的代码,自己根据RN写的原生模块:
//// KeyboardHeight.h// Jicheng6//// Created by guojicheng on 16/11/7.// Copyright © 2016年 Facebook. All rights reserved.//#import <UIKit/UIKit.h>#import "RCTEventEmitter.h"#import "RCTBridgeModule.h"@interface KeyboardHeight : RCTEventEmitter<RCTBridgeModule>-(void)heightChanged:(int)height;@property (nonatomic, assign)int kbHeight;@end
//// KeyboardHeight.m// Jicheng6//// Created by guojicheng on 16/11/7.// Copyright © 2016年 Facebook. All rights reserved.//#import "KeyboardHeight.h"@implementation KeyboardHeightRCT_EXPORT_MODULE();- (instancetype)init{ self = [super init]; if (self) { self.kbHeight = 0; [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(keyboardDidShow:) name:UIKeyboardDidShowNotification object:nil]; } return self;}-(void)keyboardDidShow:(NSNotification*) aNotification{ //获取键盘的高度 NSDictionary *userInfo = [aNotification userInfo]; NSValue *aValue = [userInfo objectForKey:UIKeyboardFrameEndUserInfoKey]; CGRect keyboardRect = [aValue CGRectValue]; if (_kbHeight != keyboardRect.size.height){ _kbHeight = keyboardRect.size.height; [self heightChanged:_kbHeight]; }}RCT_REMAP_METHOD(getKBHeight, resolver:(RCTPromiseResolveBlock)resolve rejecter:(RCTPromiseRejectBlock)reject){ resolve([[NSNumber alloc]initWithInt:_kbHeight]);}- (NSArray<NSString *> *)supportedEvents{ return @[@"heightChanged"];}-(void)heightChanged:(int)height{ [self sendEventWithName:@"heightChanged" body:[NSNumber numberWithUnsignedInt:height]];}@end
好了,原生模块封装好了,接下来看JS方面,这个也是老话题了,前面的博客都说了,直接贴代码:
import React, { Component } from 'react';import { AppRegistry, StyleSheet, Text, View, TouchableOpacity, Alert, TextInput, PixelRatio, Linking, Keyboard, NativeEventEmitter,} from 'react-native';var Dimensions = require('Dimensions');var ScreenWidth = Dimensions.get('window').width;var ScreenHeight = Dimensions.get('window').height;var kbHeight = require('NativeModules').KeyboardHeight;const kbHeightEvt = new NativeEventEmitter(kbHeight);
componentWillMount() { this.heightChanged = kbHeightEvt.addListener('heightChanged', this._heightChanged.bind(this)); } componentDidMount() { } componentWillUnmount() { this.heightChanged.remove(); } _heightChanged(data){ // console.log(data); this.keyboardHeight = data; this.changeMarginTop();//这里我是处理高度的 }
这里已经拿到高度,接下来就好办了,就是加减问题。
我们需要拿到输入框在屏幕中的位置,然后和键盘的高度做比较,输入框的位置我们通过onLayout获取:
onLayoutParent(event){ if (this.orgLayoutParent == null){//获取的父组件的位置,因为要用到计算 this.orgLayoutParent = event.nativeEvent.layout; } console.log('parent layout: ', event.nativeEvent.layout); } onLayoutMail(event){//获取输入框的位置,这个位置是相对父组件的位置,所以上面需要获得父组件的 this.layoutMail = event.nativeEvent.layout; } onFocusMail(event){ this.focusName = 'mail';//定义一个标识,可以区分不同输入框 this.changeMarginTop();//统一处理高度的函数 } onSubmitMail(){ drawLayout.setKBMoveY(0);//当输入完毕时,重置回原来的状态 } changeMarginTop(){//计算移动的距离 var layout = null; if (this.focusName == 'mail'){ layout = this.layoutMail; } if (layout && this.orgLayoutParent.y + layout.y + layout.height > ScreenHeight - this.keyboardHeight){ drawLayout.setKBMoveY(-(this.orgLayoutParent.y + layout.y + layout.height - ScreenHeight + this.keyboardHeight)); }else{//不对的置零处理 drawLayout.setKBMoveY(0); } } render() { return ( <View style={[styles.container, this.props.style ? this.props.style : {}]} onLayout={this.onLayoutParent.bind(this)}> <View style={[styles.viewStyle, {marginTop: 10}]} onLayout={this.onLayoutMail.bind(this)}>//这里获取的是相对位置哦 <TextInput style={styles.textInputStyle} onChangeText={this.onTextChange.bind(this)} value={this.state.emailPath} placeholder={'请输入邮箱'} onFocus={this.onFocusMail.bind(this)}//当获取到焦点时触发 onSubmitEditing={this.onSubmitMail.bind(this)}/>//点击回车时的调用,这里可以根据需求去做 <TouchableOpacity onPress={this.onSubmitSend.bind(this)}> <View style={[styles.sendButtonView, {}]}> <Text style={styles.sendButtonText}> 发送 </Text> </View> </TouchableOpacity> </View> </View> ); }
距离我们也都算好了,接下来就是给drawLayout加一个动画,然后动起来不要那么突兀。
import React, { Component } from 'react';import { StyleSheet, Text, View, TouchableOpacity, Animated,} from 'react-native';import SendEmail from './SendEmail';export default class DrawLayout extends Component { constructor(props){ super(props); this.state={ kbShowY: new Animated.Value(0),//设置动画的初始值 }; global.drawLayout = this;//这里将自己保存到global里面,方便它的子组件调用 } setKBMoveY(y){ Animated.timing(//这里用的是timing均匀变化,具体的参数,可以参考RN的文档,写的很详细了,这里就不啰嗦了。 this.state.kbShowY,{ toValue: y,//变化到目的位置 delay: 250,//延时250毫秒 }, ).start();//开始 } componentWillUnmount() { global.drawLayout = null;//降这个值赋值为空 } render() { return ( <Animated.View style={[styles.container, {marginTop: this.state.kbShowY}]} >//使用Animated.View <SendEmail style={{marginTop: 10}}/> </Animated.View> ); }}
这就大功告成了。接着截图看看效果,虽然有动画,没法弄动态图
最新的发现,可以看我这里: 点击打开链接
0 1
- React-Native解决键盘遮挡问题(Keyboard遮挡问题)
- React-Native解决键盘遮挡问题(Keyboard遮挡问题)
- React Native 解决iOS上键盘遮挡TextInput问题
- React Native 解决ScrollView 上 TextInput 键盘遮挡问题
- React-native键盘遮挡输入框问题的解决
- React Native 解决 iOS 上键盘遮挡 TextInput 问题
- React-Native键盘遮挡问题进阶发现
- React Native学习之TabBarIOS用法 React Native 解决iOS上键盘遮挡TextInput问题
- 《React-Native系列》33、 键盘遮挡问题处理
- 《React-Native系列》33、 键盘遮挡问题处理
- React Native TextInput键盘遮挡输入款问题
- 解决键盘遮挡UITextField问题
- iOS解决键盘遮挡问题
- iOS 解决键盘遮挡问题
- IQKeyboardManager解决键盘遮挡问题
- iOS解决键盘遮挡问题
- React Native 键盘KeyBoard问题
- 如何解决Keyboard 遮挡 UITextField的问题?
- Android应用 手势密码的实现(四)
- mysql 安装失败解决方法
- Hadoop的压缩codec
- 三个c语言
- CSS 滤镜Filter亮度动画
- React-Native解决键盘遮挡问题(Keyboard遮挡问题)
- javascript:继 JavaScript 模块入门,再详解“模块捆绑”
- hive优化心得
- 李葆文教授出席第二届中国(东莞)智能制造发展论坛并做智能维护主题报告
- 第89篇 webrtc一对一IOS端研究(二)
- .net treeview使用方法以及树状结构的应用
- 计算机系统总线
- List转换DataTable
- shell基础