flutter开发实战-自定义长按TextField输入框剪切、复制、选择全部菜单AdaptiveTextSelectionToolba样式UI效果

flutter开发实战-自定义长按TextField输入框剪切、复制、选择全部菜单样式UI效果

在开发过程中,需要长按TextField输入框cut、copy设置为中文“复制、粘贴”,我首先查看了TextField中的源码,看到了ToolbarOptions、AdaptiveTextSelectionToolbar,这时候我们可以在剪切、复制、选择全部菜单样式UI效果上显示icon的按钮了。

在这里插入图片描述

一、TextField源码中的代码contextMenuBuilder

我这里在中TextField中的源码,看到了ToolbarOptions、AdaptiveTextSelectionToolbar,可以继承AdaptiveTextSelectionToolbar来实现更改剪切、复制、选择全部菜单样式效果

将自定义的AdaptiveTextSelectionToolbar,设置到contextMenuBuilder即可。

TextField源码一段

  /// {@macro flutter.widgets.EditableText.contextMenuBuilder}////// If not provided, will build a default menu based on the platform.////// See also://////  * [AdaptiveTextSelectionToolbar], which is built by default.final EditableTextContextMenuBuilder? contextMenuBuilder;static Widget _defaultContextMenuBuilder(BuildContext context, EditableTextState editableTextState) {return AdaptiveTextSelectionToolbar.editableText(editableTextState: editableTextState,);}

二、自定义AdaptiveTextSelectionToolbar

继承AdaptiveTextSelectionToolbar实现自定义的toolbar样式CustomTextSelectionToolbar

自定义后需要实现按钮列表

List<Widget> resultChildren = <Widget>[];
for (int i = 0; i < buttonItems!.length; i++) {final ContextMenuButtonItem buttonItem = buttonItems![i];resultChildren.add(SelectionToolBarButton(width: 100,height: 50,icon: (i == 0)?Icon(Icons.cut,color: Colors.white,size: 14,):Icon(Icons.copy,color: Colors.white,size: 16,),title: getButtonLabelString(context, buttonItem),onPressed: buttonItem.onPressed,));
}

自定义按钮SelectionToolBarButton,设置icon+title的按钮样式

class SelectionToolBarButton extends StatelessWidget {const SelectionToolBarButton({super.key,required this.width,required this.height,required this.icon,required this.title,required this.onPressed,});final double width;final double height;final Icon icon;final String title;final VoidCallback onPressed;Widget build(BuildContext context) {return GestureDetector(onTap: () {onPressed();},child: Container(color: Colors.black87,width: width,height: height,alignment: Alignment.center,child: Row(mainAxisAlignment: MainAxisAlignment.center,crossAxisAlignment: CrossAxisAlignment.center,children: [icon,SizedBox(width: 5,),Text(title,style: TextStyle(fontSize: 15,color: Colors.white,),),],),),);}
}

CustomTextSelectionToolbar完整代码如下

import 'package:flutter/cupertino.dart';
import 'package:flutter/material.dart';class CustomTextSelectionToolbar extends AdaptiveTextSelectionToolbar {const CustomTextSelectionToolbar({super.key, required super.children, required super.anchors});CustomTextSelectionToolbar.editableText({super.key,required EditableTextState editableTextState,}) : super.editableText(editableTextState: editableTextState);Widget build(BuildContext context) {// If there aren't any buttons to build, build an empty toolbar.if ((children != null && children!.isEmpty) ||(buttonItems != null && buttonItems!.isEmpty)) {return const SizedBox.shrink();}List<Widget> resultChildren = <Widget>[];for (int i = 0; i < buttonItems!.length; i++) {final ContextMenuButtonItem buttonItem = buttonItems![i];resultChildren.add(SelectionToolBarButton(width: 100,height: 50,icon: (i == 0)?Icon(Icons.cut,color: Colors.white,size: 14,):Icon(Icons.copy,color: Colors.white,size: 16,),title: getButtonLabelString(context, buttonItem),onPressed: buttonItem.onPressed,));}switch (Theme.of(context).platform) {case TargetPlatform.iOS:return CupertinoTextSelectionToolbar(anchorAbove: anchors.primaryAnchor,anchorBelow: anchors.secondaryAnchor == null? anchors.primaryAnchor: anchors.secondaryAnchor!,children: resultChildren,);case TargetPlatform.android:return TextSelectionToolbar(anchorAbove: anchors.primaryAnchor,anchorBelow: anchors.secondaryAnchor == null? anchors.primaryAnchor: anchors.secondaryAnchor!,children: resultChildren,);case TargetPlatform.fuchsia:case TargetPlatform.linux:case TargetPlatform.windows:return DesktopTextSelectionToolbar(anchor: anchors.primaryAnchor,children: resultChildren,);case TargetPlatform.macOS:return CupertinoDesktopTextSelectionToolbar(anchor: anchors.primaryAnchor,children: resultChildren,);}}/// Returns the default button label String for the button of the given/// [ContextMenuButtonType] on any platform.static String getButtonLabelString(BuildContext context, ContextMenuButtonItem buttonItem) {if (buttonItem.label != null) {return buttonItem.label!;}switch (Theme.of(context).platform) {case TargetPlatform.iOS:case TargetPlatform.macOS:case TargetPlatform.android:case TargetPlatform.fuchsia:case TargetPlatform.linux:case TargetPlatform.windows:assert(debugCheckHasMaterialLocalizations(context));switch (buttonItem.type) {case ContextMenuButtonType.cut:return "剪切";case ContextMenuButtonType.copy:return "复制";case ContextMenuButtonType.paste:return "粘贴";case ContextMenuButtonType.selectAll:return "选择全部";case ContextMenuButtonType.custom:return '';}}}
}class SelectionToolBarButton extends StatelessWidget {const SelectionToolBarButton({super.key,required this.width,required this.height,required this.icon,required this.title,required this.onPressed,});final double width;final double height;final Icon icon;final String title;final VoidCallback onPressed;Widget build(BuildContext context) {return GestureDetector(onTap: () {onPressed();},child: Container(color: Colors.black87,width: width,height: height,alignment: Alignment.center,child: Row(mainAxisAlignment: MainAxisAlignment.center,crossAxisAlignment: CrossAxisAlignment.center,children: [icon,SizedBox(width: 5,),Text(title,style: TextStyle(fontSize: 15,color: Colors.white,),),],),),);}
}

三、TextField中使用CustomTextSelectionToolbar

在TextField输入框中设置contextMenuBuilder

static Widget _textFieldContextMenuBuilder(BuildContext context, EditableTextState editableTextState) {return CustomTextSelectionToolbar.editableText(editableTextState: editableTextState,);}

最后在TextField输入框中设置contextMenuBuilder

TextField(contextMenuBuilder: _textFieldContextMenuBuilder,minLines: 1,maxLines: null,keyboardType: TextInputType.multiline,textAlignVertical: TextAlignVertical.center,autofocus: widget.autofocus,focusNode: editFocusNode,controller: widget.textEditingController,textInputAction: TextInputAction.send,
)

至此可以自定义长按TextField输入框剪切、复制、选择全部菜单样式UI效果
在这里插入图片描述
在这里插入图片描述
使用系统全局剪切、复制、选择全部设置为中文,可以查看:https://blog.csdn.net/gloryFlow/article/details/132966717

四、小结

flutter开发实战-自定义长按TextField输入框剪切、复制、选择全部菜单样式UI效果。自定义AdaptiveTextSelectionToolbar,在TextField输入框中设置contextMenuBuilder,实现功能。
内容较多,描述可能不准确,请见谅。

本文地址:https://blog.csdn.net/gloryFlow/article/details/132970840

学习记录,每天不停进步。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/82033.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

深度学习中安装了包但是依然导入(import)失败这一问题,例如pytorch环境下已经安装了scikit-learn但是import不了

在跑深度学习模型的时候我们要先搭建pytorch环境&#xff0c;这个环境跟windows环境是不同的&#xff0c;我们默认在windows中安装的包在当前的虚拟环境中读取不到&#xff0c;所以导致我们明明安装了包但是依然在实际的导入中(import)报错。解决办法就是我们去虚拟环境中安装包…

linux驱动开发day6--(epoll实现IO多路复用、信号驱动IO、设备树以及节点和属性解析相关API使用)

一、IO多路复用--epoll实现 1.核心&#xff1a; 红黑树、一张表以及三个接口、 2.实现过程及API 1&#xff09;创建epoll句柄/创建红黑树根节点 int epfdepoll_create(int size--无意义&#xff0c;>0即可)----------成功&#xff1a;返回根节点对应文件描述符&#xff…

ubuntu:vi 编辑器修改文件的基本操作指令

Vi 编辑器是一个强大的命令行文本编辑器&#xff0c;它有着丰富的功能&#xff0c;但也可能对新用户来说有一些陡峭的学习曲线。下面是一些 Vi 编辑器中的基本操作指令&#xff1a; 1.打开文件 打开 Vi 并打开文件的命令是&#xff1a; vi filename其中 filename 是你要编辑…

构建无缝的服务网格体验:分享在生产环境中构建和管理服务网格的最佳实践

&#x1f337;&#x1f341; 博主猫头虎 带您 Go to New World.✨&#x1f341; &#x1f984; 博客首页——猫头虎的博客&#x1f390; &#x1f433;《面试题大全专栏》 文章图文并茂&#x1f995;生动形象&#x1f996;简单易学&#xff01;欢迎大家来踩踩~&#x1f33a; &a…

笙默考试管理系统-MyExamTest----codemirror(21)

笙默考试管理系统-MyExamTest----codemirror&#xff08;21&#xff09; 目录 一、 笙默考试管理系统-MyExamTest 二、 笙默考试管理系统-MyExamTest 三、 笙默考试管理系统-MyExamTest 四、 笙默考试管理系统-MyExamTest 五、 笙默考试管理系统-MyExamTest 笙默考试…

linux安装配置 kafka并简单使用

目录 一 解压安装包 二 修改配置 三 启动kafka 四 简单使用 kafka 一 解压安装包 这里提供了网盘资源 链接: https://pan.baidu.com/s/1wUxEQuiPB1wRsjJ-FPPu7Q?pwd9rm7 提取码: 9rm7 这里安装包上传至/opt/insatll目录 解压至/opt/soft目录 tar -zxf /opt/install/ka…

容器的数据卷

容器的数据卷 操作数据卷 # 基本格式 docker volume [common] # 创建一个volume docker volume create # 显示一个或多个volume docker volume inspect # 列出所以的volume docker volume ls # 删除未使用的volume docker volume prune # 删除一个或多个volume docker volume…

双节履带机械臂小车实现蓝牙遥控功能

1.功能描述 本文示例所实现的功能为&#xff1a;采用蓝牙远程遥控双节履带机械臂小车进行运动。 2.结构说明 双节履带机械臂小车&#xff0c;采用履带底盘&#xff0c;可适用于任何复杂地形。 前节履带抬起高度不低于10cm&#xff0c;可用于履带车进行爬楼行进。 底盘上装有一…

mybatis学习记录(三)-----关于SQL Mapper的namespace

关于SQL Mapper的namespace 视频总结笔记&#xff1a; 在SQL Mapper配置文件中<mapper>标签的namespace属性可以翻译为命名空间&#xff0c;这个命名空间主要是为了防止SQL id 冲突的。 创建CarMapper2.xml文件&#xff0c;代码如下&#xff1a; CarMapper2.xml: <?…

uni-app混合开发 navigateTo、reLaunch、redirectTo、switchTab区别

1.navigateTo 保留当前页面&#xff0c;跳转到应用内的某个页面&#xff0c;使用uni.navigateBack可以返回到原页面。 要注意的是navigateTo只能跳转的应用内非 tabBar 的页面的路径 , 路径后可以带参数&#xff1b;如果跳转url参数为tabBar的路径则无法进行跳转 2.redir…

用Python判断是否为闰年并计算生肖年

1 问题 润平年以及生肖是新的一年到来我们应该了解的信息。那么如何利用python程序计算快速计算该年为什么年&#xff1f; 2 方法 利用if条件判断语句实现。 代码清单 1 year eval(input(请输入咨询的年份:))if (year % 4 0 and year %100 ! 0) or year % 400 0: print(…

java版工程管理系统Spring Cloud+Spring Boot+Mybatis实现工程管理系统源码

工程项目管理软件&#xff08;工程项目管理系统&#xff09;对建设工程项目管理组织建设、项目策划决策、规划设计、施工建设到竣工交付、总结评估、运维运营&#xff0c;全过程、全方位的对项目进行综合管理 工程项目各模块及其功能点清单 一、系统管理 1、数据字典&am…

RocketMQ快速实战以及集群架构详解

⼀、 MQ 简介 MQ &#xff1a; MessageQueue &#xff0c;消息队列。是在互联⽹中使⽤⾮常⼴泛的⼀系列服务中间件。 这个词可以分两个部分来看&#xff0c;⼀是Message &#xff1a;消息。消息是在不同进程之间传递的数据。这些进程可以部署在同⼀台机器上&#xff0c;也可以…

Python 循环缓冲区

循环缓冲区是环形缓冲区的另一个名称。 缓冲区是一种数据结构&#xff0c;它使用单个固定大小的缓冲区&#xff0c;就好像它是端到端连接的一样。 这种结构有助于管理数据流&#xff0c;其中可以在一端不断添加新数据&#xff0c;而可以从另一端删除旧数据。 当缓冲区已满时&a…

17. 电话号码的字母组合

题目链接&#xff1a; 力扣&#xff08;LeetCode&#xff09;官网 - 全球极客挚爱的技术成长平台 思路&#xff1a; 数字对应字母用map(这里不好用&#xff09;&#xff0c;还是用数组映射&#xff0c;因为这里的映射表是个静态的 组合的思想。比如2,3就是需要选两个字母即搜…

TCP详解之流量控制

TCP详解之流量控制 发送方不能无脑的发数据给接收方&#xff0c;要考虑接收方处理能力。 如果一直无脑的发数据给对方&#xff0c;但对方处理不过来&#xff0c;那么就会导致触发重发机制&#xff0c;从而导致网络流量的无端的浪费。 为了解决这种现象发生&#xff0c;TCP 提…

java 启动参数 springboot idea

一、idea里配置&#xff1a; 在启动application处&#xff0c;选edit Configuration。进入启动配置框。 有VM options&#xff08;jvm参数&#xff09;&#xff0c;有Program arguments&#xff08;程序参数&#xff09;等。 1、VM options 需要以 -D 或 -X 或 -XX 开头&…

一个方法用js生成随机双色球、大乐透

代码如下&#xff1a; <!DOCTYPE html> <html lang"en"><head><meta charset"UTF-8"><meta name"viewport" content"widthdevice-width, initial-scale1.0"><title>Document</title><s…

【cpp】std::optional

原文地址 Intro float divide(float a, float b) {if (b 0){return ?;}return a / b; }这里以一个除法函数为例&#xff0c;当 b 为 0 的时候&#xff0c;明显是除法的异常&#xff0c;但是怎样把这个状态返回给调用方呢&#xff1f; 常见的方法有如下几种 抛异常&#x…

网络安全深入学习第六课——热门框架漏洞(RCE— Weblogic反序列化漏洞)

文章目录 一、Weblogic介绍二、Weblogic反序列化漏洞历史三、Weblogic框架特征1、404界面2、登录界面 四、weblogic常用弱口令账号密码五、Weblogic漏洞介绍六、Weblogic漏洞手工复现1、获取账号密码&#xff0c;这是一个任意文件读取的漏洞1&#xff09;读取SerializedSystemI…