如何禁用 QTextEdit 的中间按钮功能?
Posted
技术标签:
【中文标题】如何禁用 QTextEdit 的中间按钮功能?【英文标题】:How to disable middle button functionality of QTextEdit? 【发布时间】:2013-07-23 13:40:11 【问题描述】:我不希望鼠标中键在我的 QTextEdit 中粘贴文本。此代码不起作用。 TextEdit
继承 QTextEdit
。鼠标中键粘贴后,它会粘贴复制的文本。
void TextEdit::mousePressEvent ( QMouseEvent * e )
if (e->button() == Qt::MidButton)
e->accept();
return;
;
QTextEdit::mousePressEvent(e);
【问题讨论】:
我无法复制此内容,中键不会为我粘贴任何文本。 还有,平台是Linux吗? @Merlin069 根据QTextControlPrivate::mouseReleaseEvent
的源代码,其他平台好像也可以中键粘贴。
是的,我正在 Linux 下编码
@alexisdm - 这很有趣,我以前从未注意到这一点。我问的是 Linux,因为它通常是默认的操作系统行为,不像 OSX 和 Windows。
【参考方案1】:
由于鼠标点击通常在按钮释放时注册,您应该重新定义mouseReleaseEvent
函数。
您甚至不需要重新定义mousePressEvent
,因为该函数根本不处理中间按钮。
【讨论】:
【参考方案2】:我假设您在这里使用的是 Linux;在您处理鼠标事件之前,在窗口中单击鼠标右键可能会触发插入 mime 数据,这就是它仍在粘贴文本的原因。
因此,根据 Qt docs for paste:-“要修改 QTextEdit 可以粘贴的内容以及粘贴方式,请重新实现虚拟 canInsertFromMimeData() 和 insertFromMimeData() 函数。”
【讨论】:
重新定义insertFromMimeData
也会改变拖放的工作方式,而不仅仅是改变中间按钮的行为。
@alexisdm 重新定义它并检查是否按下了鼠标中键,否则调用基类函数将提供所需的行为。
我并不是说它不起作用,我只是说应该避免在与鼠标无关的函数中添加鼠标处理代码。
它并不是真正处理鼠标,而是对其状态做出反应,这发生在 GUI 应用程序的整个代码中。
@Merlin069 我试过你说的,但是当insertFromMimeData()
被调用时,鼠标中键已经被释放,所以我不知道它是否是从中键单击中调用的【参考方案3】:
我也遇到过同样的情况,也就是说:我的CustomQTextEdit
的某些部分必须不可编辑。
因为我真的很喜欢鼠标中键粘贴功能,所以我不想禁用它。所以,这是我使用的(或多或少快速和肮脏的编码)解决方法:
void QTextEditHighlighter::mouseReleaseEvent(QMouseEvent *e)
QString prev_text;
if (e->button() == Qt::MidButton)
// Backup the text as it is before middle button click
prev_text = this->toPlainText();
// And let the paste operation occure...
// e->accept();
// return;
// !!!!
QTextEdit::mouseReleaseEvent(e);
// !!!!
if (e->button() == Qt::MidButton)
/*
* Keep track of the editbale ranges (up to you).
* My way is a single one range inbetween the unique
* tags "//# BEGIN_EDIT" and "//# END_EDIT"...
*/
QRegExp begin_regexp = QRegExp("(^|\n)(\\s)*//# BEGIN_EDIT[^\n]*(?=\n|$)");
QRegExp end_regexp = QRegExp("(^|\n)(\\s)*//# END_EDIT[^\n]*(?=\n|$)");
QTextCursor from = QTextCursor(this->document());
from.movePosition(QTextCursor::Start);
QTextCursor cursor_begin = this->document()->find(begin_regexp, from);
QTextCursor cursor_end = this->document()->find(end_regexp, from);
cursor_begin.movePosition(QTextCursor::EndOfBlock);
cursor_end.movePosition(QTextCursor::StartOfBlock);
int begin_pos = cursor_begin.position();
int end_pos = cursor_end.position();
if (!(cursor_begin.isNull() || cursor_end.isNull()))
// Deduce the insertion index by finding the position
// of the first character that changed between previous
// text and the current "after-paste" text
int insert_pos; //, end_insert_pos;
std::string s_cur = this->toPlainText().toStdString();
std::string s_prev = prev_text.toStdString();
int i_max = std::min(s_cur.length(), s_prev.length());
for (insert_pos=0; insert_pos < i_max; insert_pos++)
if (s_cur[insert_pos] != s_prev[insert_pos])
break;
// If the insertion point is not in my editable area: just restore the
// text as it was before the paste occured
if (insert_pos < begin_pos+1 || insert_pos > end_pos)
// Restore text (ghostly)
((MainWindow *)this->topLevelWidget())->disconnect(this, SIGNAL(textChanged()), ((MainWindow *)this->topLevelWidget()), SLOT(on_textEdit_CustomMacro_textChanged()));
this->setText(prev_text);
((MainWindow *)this->topLevelWidget())->connect(this, SIGNAL(textChanged()), ((MainWindow *)this->topLevelWidget()), SLOT(on_textEdit_CustomMacro_textChanged()));
【讨论】:
以上是关于如何禁用 QTextEdit 的中间按钮功能?的主要内容,如果未能解决你的问题,请参考以下文章
在推送 QPushButton 时将文本从 QTextEdit 发送到 QListWidget - Qt
Qt中通过点击一个QPushButton来实现QTextEdit的PageUp/PageDown功能
Qt:如何在 QVBoxLayout 中交替对齐 QTextEdit?