HarmonyOS鸿蒙Next中如何屏蔽或者重写TextInput的文本选择菜单的复制、粘贴功能?
HarmonyOS鸿蒙Next中如何屏蔽或者重写TextInput的文本选择菜单的复制、粘贴功能? 如上图,我想重写复制和粘贴的功能,如何实现呢?涉及的API文档具体是哪个?
更多关于HarmonyOS鸿蒙Next中如何屏蔽或者重写TextInput的文本选择菜单的复制、粘贴功能?的实战教程也可以访问 https://www.itying.com/category-93-b0.html
开发者您好,
TextInput
、TextArea等文本输入组件,在长按时会自动弹起系统文本选择菜单;
如果想要隐藏系统文本选择菜单,可以使用selectionMenuHidden
属性进行隐藏。
如果不想隐藏系统文本选择菜单,而是仅仅想禁止粘贴,有以下两种方法:
- 重写
onPaste
方法,在触发粘贴事件回调时不让文本粘贴。 - 使用
editMenuOptions
设置自定义菜单的扩展项,禁用editMenu
的粘贴项。
使用自定义菜单bindContextMenu
替代系统文本选择菜单,isShown
为false
时,隐藏菜单。弹出菜单项需要自定义。
推荐解决方案:
方案一:利用selectionMenuHidden
属性隐藏系统文本选择菜单,示例代码如下:
@Entry
@Component
struct Index {
@State message: string = '';
build() {
Column() {
Text(`输入的内容: ${this.message}`).margin({ top: 100, bottom: 30 })
TextInput({ placeholder: "请输入内容" })
.borderRadius(0)
.onChange((value: string) => {
this.message = value
})
.selectionMenuHidden(true)
}
.height('100%')
.width('100%')
}
}
方案二:在TextInput
的onPaste
回调事件中阻止文本的粘贴,示例代码如下:
@Entry
@Component
struct Index {
@State message: string = '';
build() {
Column() {
Text(`输入的内容: ${this.message}`).margin({ top: 100, bottom: 30 })
TextInput({ placeholder: "请输入内容" })
.borderRadius(0)
.onChange((value: string) => {
this.message = value
})
.onPaste((value: string, event: PasteEvent) => {
if (event !== undefined && event.preventDefault) {
console.info("禁止粘贴")
event.preventDefault()
}
})
}
.height('100%')
.width('100%')
}
}
方案三:禁用editMenu
的粘贴项。
- 定义
onCreateMenu
方法,使用filter
函数切除Array<TextMenuItem>
中的粘贴项。 - 在
editMenuOptions
属性中使用onCreateMenu
方法初始化editMenu
。
示例代码如下:
@Entry
@Component
struct TextAreaExample {
@State text: string = 'TextArea editMenuOptions'
onCreateMenu(menuItems: Array<TextMenuItem>) {
menuItems = menuItems.filter(item => item.content !== '粘贴');
return menuItems
}
build() {
Column() {
TextArea({ text: this.text })
.width('95%')
.height(56)
.editMenuOptions({
onCreateMenu: this.onCreateMenu, onMenuItemClick: (menuItem: TextMenuItem, textRange: TextRange) => {
return false;
}
})
.margin({ top: 100 })
}
.width("90%")
.margin("5%")
}
}
方案四:拦截整个默认菜单并使用自定义bindContextMenu
代替。
- 令
Array<TextMenuItem>
返回空数组,从而拦截整个editMenu
。 - 定义
bindContextMenu
,实际内容和功能需要自定义。
示例代码如下:
@Entry
@Component
struct Example {
@State start: number = 0
@State end: number = 0
@State text: string = '请选择此文字'
@State isShown: boolean = true
getContentLength() {
return this.text.length
}
setSelection(start: number, end: number) {
this.start = start
this.end = end
}
setAllSelect() {
this.setSelection(0, this.getContentLength())
}
build() {
Column() {
Column() {
TextArea({ text: this.text })
.fontSize(16)
.copyOption(CopyOptions.InApp)
.bindContextMenu(this.isShown, SelectionMenu,
{
onDisappear: () => {
this.isShown = false;
}
})
.editMenuOptions({
onCreateMenu: (menuItems: Array<TextMenuItem>) => {
console.log(`Text onCreateMenu ----------------------`)
this.isShown = true
return [] // 拦截默认菜单项,显示自定义contextmenu
}, onMenuItemClick: (menuItem: TextMenuItem, textRange: TextRange) => {
return true;
}
})
.onTextSelectionChange((start, end) => {
console.info('TextSelection' + start.toString() + '-' + end.toString())
if (start < 0 || end < 0) {
this.setSelection(0, 0)
this.isShown = false;
} else {
this.start = start
this.end = end
}
})
.parallelGesture(
LongPressGesture()
.onAction((event: GestureEvent) => {
this.setAllSelect()
})
)
}
.padding(50)
.justifyContent(FlexAlign.Center)
.backgroundColor(Color.Pink)
.parallelGesture(
LongPressGesture()
.onAction((event: GestureEvent) => {
this.setAllSelect()
})
)
}
.width("100%")
.height("100%")
.justifyContent(FlexAlign.Center)
}
}
@Builder
function SelectionMenu() {
Column() {
Text('CustomMenu')
}
}
更多关于HarmonyOS鸿蒙Next中如何屏蔽或者重写TextInput的文本选择菜单的复制、粘贴功能?的实战系列教程也可以访问 https://www.itying.com/category-93-b0.html
if (TextMenuItemId.of(‘自定义’).equals(menuItem.id)) { return true }
我用 == 号比较,它也没报错,定位了老半天
你好。这里是跨设备剪贴板开发文档:https://developer.huawei.com/consumer/cn/doc/harmonyos-guides/distributed-pasteboard-guide。希望可以帮助到你。
总的来说,HarmonyOS是一款非常优秀的操作系统,期待它能在未来带给我们更多惊喜!
有这么一个接口可以用,亲测有效
@Entry
@Component
struct Index {
@State message: string = 'Hello World';
build() {
Column() {
TextInput().width('100%').editMenuOptions({
onCreateMenu: (menuItems: Array<TextMenuItem>) => {
// 入参是包含了所有系统菜单的信息,可以修改这个数组,最终系统会根据这个列表添加选项
// 如你标题所示,如果你想屏蔽复制按钮可以这么写
menuItems.filter((item: TextMenuItem) => {
return item.id == TextMenuItemId.COPY
})
// 如果你要添加一个控制选项
menuItems.push({
id: TextMenuItemId.of('自定义'),
content: '自定义按钮'
})
return menuItems
},
onMenuItemClick: (menuItem: TextMenuItem, range: TextRange) => {
// 这个接口在每个按钮按下的时候会触发,看参数很好理解,如果你添加了一个自定义按钮,这里可以写你自己的业务逻辑
if (menuItem.id == TextMenuItemId.of('自定义')) {
return true
}
// 这个返回值true表示按钮逻辑处理完了,对于系统原有的菜单,这里返回true表示应用侧处理完了,不需要系统的默认处理逻辑了
// 所以,你要自己重写系统的粘贴功能,就可以在这里实现
if (menuItem.id == TextMenuItemId.PASTE) {
// 自己实现粘贴功能,所谓粘贴无非就是把剪切板里的数据拿出来,再通过状态变量塞回去,注意访问剪切需要申请权限的
// 实测系统自带的粘贴好像不要申请,感觉是加了白名单控制??
return true
}
return true
}
})
}
.width('100%').borderWidth(1)
}
}
在HarmonyOS鸿蒙Next中,可以通过重写TextInput
组件的onTextContextMenu
方法来屏蔽或自定义文本选择菜单的复制、粘贴功能。具体步骤如下:
- 创建一个自定义的
TextInput
组件。 - 在组件中重写
onTextContextMenu
方法。 - 在
onTextContextMenu
方法中,根据需求过滤掉“复制”和“粘贴”选项,或者自定义菜单项。
示例代码:
class CustomTextInput extends TextInput {
onTextContextMenu(event) {
const menuItems = event.menuItems.filter(item => item.label !== '复制' && item.label !== '粘贴');
event.menuItems = menuItems;
super.onTextContextMenu(event);
}
}
通过这种方式,你可以灵活控制文本选择菜单的行为。