Flutter实战-自定义键盘(一)
用了两年的flutter,有了一些心得,从今天开始陆续更新一些案例,不虚头巴脑,只求实战有用,以供学习或使用flutter的小伙伴参考,学习尚浅,如有不正确的地方还望各路大神指正,以免误人子弟,在此拜谢~(原创不易,转发请标注来源和作者)
注意:无特殊说明,flutter版本为3.0+
此文大部分代码内容来自 GitHub - Im-Kevin/cool_ui: 用flutter实现一些我认为好看的UI控件,有Popover,仿Weui的Toast,自定义键盘,感谢大神指路,喜欢的可以去看源码,当然也有区别于原作者的实现,敬请关注。
为什么需要自定义键盘?自定义键盘可以说在客户端原生开发中有很多地方需要用到,比如做一个数字键盘支持支付业务,特殊内容的输入,或者响应其他特殊需求。作者在开发中也遇到自定义键盘的需求,当时是初学,在github和pub.flutter-io.cn中查了大量的插件,觉得cool_ui中的自定义键盘能满足,再次感谢作者。此文从cool_ui的自定义键盘出发,细说一下解决思路,希望给初学者在自定组件和理解Flutter运行原理提供帮助。
自定义键盘一定是一个Widget组件,那么它至少要实现类似系统键盘的以下功能:
- 当TextField 聚焦时候弹出键盘组件,将主视图推到键盘上,不至于遮挡
- 实现内容发送到TextField,也要有“搜索”,“确定”,“下一个”,“收起键盘”等常用键盘指令
一。KeyboardRootWidget
1.定义一个StatefulWidget,里面有两个参数的基础设置
class KeyboardRootWidget extends StatefulWidget {
final Widget child;
final TextDirection textDirection; //文字输入的方向,有从右到左,也有从左到右...
2.键盘初始化KeyboardMediaQuery,下一个章节具体解释
@override
Widget build(BuildContext context) {
// TODO: implement build
return KeyboardMediaQuery(child: Builder(builder: (context) {
CoolKeyboard.init(this, context);List<Widget> children = [widget.child];
if (_keyboardBuilder != null) {
children.add(Builder(
builder: _keyboardBuilder!,
));
}...
}
3.设置键盘和清除键盘的方法
setKeyboard 和clearKeyboard ,这两个方法用来设置和清除WidgetBuilder
完整代码如下:
class KeyboardRootState extends State<KeyboardRootWidget> {
WidgetBuilder? _keyboardBuilder;bool get hasKeyboard => _keyboardBuilder != null;
@override
void initState() {
super.initState();
}@override
Widget build(BuildContext context) {
// TODO: implement build
return KeyboardMediaQuery(child: Builder(builder: (context) {
CoolKeyboard.init(this, context);List<Widget> children = [widget.child];
if (_keyboardBuilder != null) {
children.add(Builder(
builder: _keyboardBuilder!,
));
}
return Directionality(
textDirection: widget.textDirection,
child: Stack(
children: children,
));
}));
}setKeyboard(WidgetBuilder _keyboardBuilder) {
_keyboardBuilder = _keyboardBuilder;
Future.delayed(const Duration(milliseconds: 50)).then((e) {
setState(() {});
});
}clearKeyboard() {
if (_keyboardBuilder != null) {
_keyboardBuilder = null;
setState(() {});
}
}
}
二。KeybordMediaQuery
我们再回顾一下什么是MediaQuery(如果需要详细了解,可以在我的专栏中搜索此文章),MediaQuery媒体查询会返回MediaQueryData,其中有个一重要数据就是viewInsets,这个是键盘遮挡UI的部分,那我们的思路很清晰,就是在我们自己的键盘弹出的时候更新当前视图的viewInsets值
1.定义一个键盘高度的监听
ValueNotifier<double> keyboardHeightNotifier = CoolKeyboard.getKeyboardHeightNotifier();
@override
void initState(){
super.initState();
CoolKeyboard.getKeyboardHeightNotifier().addListener(onUpdateHeight);
}
2.当键盘高度设置时候,覆盖系统的viewInsets值,就实现了类似系统键盘的弹出功能了。
var data = MediaQuery.maybeOf(context);
data ??= MediaQueryData.fromWindow(WidgetsBinding.instance.window);
var bottom = CoolKeyboard.getKeyboardHeightNotifier().value != 0 ? CoolKeyboard.getKeyboardHeightNotifier().value : data.viewInsets.bottom;
return MediaQuery(
child: widget.child,
data:data.copyWith(
viewInsets: data.viewInsets.copyWith(
;bottom: bottom
)
)
);
完整代码如下
class KeyboardMediaQuery extends StatefulWidget{
final Widget child;KeyboardMediaQuery({required this.child});
@override
State<StatefulWidget> createState() =>KeyboardMediaQueryState();}
class KeyboardMediaQueryState extends State<KeyboardMediaQuery >{
double keyboardHeight = 0;
ValueNotifier<double> keyboardHeightNotifier = CoolKeyboard.getKeyboardHeightNotifier();@override
void initState(){
super.initState();
CoolKeyboard.getKeyboardHeightNotifier().addListener(onUpdateHeight);
}@override
Widget build(BuildContext context) {// TODO: implement build
var data = MediaQuery.maybeOf(context);
data ??= MediaQueryData.fromWindow(WidgetsBinding.instance.window);
var bottom = CoolKeyboard.getKeyboardHeightNotifier().value != 0 ? CoolKeyboard.getKeyboardHeightNotifier().value : data.viewInsets.bottom;
// TODO: implement build
return MediaQuery(
child: widget.child,
data:data.copyWith(
viewInsets: data.viewInsets.copyWith(
bottom: bottom
)
)
);
}onUpdateHeight(){
try{
setState(()=>{});
}catch(_){
WidgetsBinding.instance.addPostFrameCallback((_){
setState(()=>{});
});
}
}@override
void dispose(){
super.dispose();
CoolKeyboard.getKeyboardHeightNotifier().removeListener(onUpdateHeight);
}
}
Flutter实战-自定义键盘(一)相关推荐
- Flutter实战-自定义键盘(二)
用了两年的flutter,有了一些心得,从今天开始陆续更新一些案例,不虚头巴脑,只求实战有用,以供学习或使用flutter的小伙伴参考,学习尚浅,如有不正确的地方还望各路大神指正,以免误人子弟,在此拜 ...
- Flutter仿微信,支付宝密码输入框+自定义键盘
大家好,我又来了. 刚用Flutter做完一个金融项目,当中使用到了类似于微信,和支付宝的那种密码输入框,然后为了安全一点也自己实现了自定义的键盘,今天跟大家分享一波 效果如下图所示: Flutter ...
- flutter -各类自定义弹窗(图片预览,输入框,键盘)以及如何阻止事件冒泡
开局废话:由于公司app后期需要做混合开发,又担心h5的性能问题.于是迫不得已,只能两端齐搞,验证一些性能优化的问题.打开了一年前flutter正式发布时,蹭热度创建的现已布满藤蔓的仓库,微微颤抖的双 ...
- Flutter实战 | 从 0 搭建「网易云音乐」APP(五、播放功能逻辑)
本系列可能会伴随大家很长时间,这里我会从0开始搭建一个「网易云音乐」的APP出来. 下面是该APP 功能的思维导图: 前期回顾: 1.Flutter实战 | 从 0 搭建「网易云音乐」APP(一.创建 ...
- Flutter 组件之 Flutter高级自定义TabBar(教程含源码)
实战需求 Flutter 组件之 Flutter高级自定义TabBar(教程含源码) 本文价值与收获 看完本文后,您将能够作出下面的界面 实战代码 import 'package:flutter/ma ...
- Android的自定义键盘颜色,android自定义键盘(解决弹出提示的字体颜色问题)
最近准备要做一个项目,需要用到自定义小键盘来确保安全,而且还需要精确获得用户点击键盘时的落点位置.力度.指尖接触屏幕的面积等参数. 在写自定义键盘的时 最近准备要做一个项目,需要用到自定义小键盘来确保 ...
- android键盘ui,android – 在自定义键盘中重新调整候选视图的UI
我正在使用自定义键盘.我在onCreateCandidatesView()中设置了setCandidatesViewShown(true)函数,问题是UI没有得到正确的重新调整. 任何帮助都会很棒.以 ...
- Flutter实战之(Clubhouse App)
flutter_ClubHouse 课程安排 每日一更, 最后达到的效果是1:1 项目简介 "Clubhouse"(俱乐部会馆)的音频聊天应用程序日前火了.这款社交软件的功能相对单 ...
- android自定义数字键盘和字母键盘,Android自定义键盘的实现(数字键盘和字母键盘)...
Android自定义键盘的实现(数字键盘和字母键盘) 发布时间:2020-09-04 03:18:48 来源:脚本之家 阅读:100 作者:浪淘沙xud 在项目中,产品对于输入方式会有特殊的要求,需要 ...
最新文章
- 无向图的连通分量的数量
- 树莓派与阿里云服务器之间的无线通信(非局域网)
- 如何删除windowsXP的计算器
- java 手写 jvm高性能缓存
- c语言第1次作业答案,C语言第五次上机作业参考答案
- JDBC和MySQL的实现原理
- kotlin 使用viewStub
- php storm 安装,PhpStorm安装教程
- 几道经典逻辑推理题,提高你的逻辑思考能力
- cc2530 按键中断实验——按键控制LED灯的亮灭
- 什么是ring0-ring3
- 智能语音:好玩的语音控制是怎么实现的?学习笔记01
- 搜狗校招笔试题编程之一
- 论EBS的并发请求(报表中心)的必要性
- 爬取某知名网站的数据
- HTML基于蔡徐坤的打飞机游戏源码
- 现代编程语言(1):Rust (铁锈,一文掌握钢铁是怎样生锈的)
- QPS、TPS、RT、并发用户数、吞吐量
- 手把手教你使用hexo搭建属于你的个人博客
- 宏杰文件夹加密V2878【永久免费的文件加密软件】