如何禁用对Qt按钮标签上的&的特殊处理?

时间:2018-09-10 23:46:59

标签: qt keyboard-shortcuts acceleratorkey

我继承了一个虚拟的键盘系统,其中包含一系列按钮,每个按钮一个。每个按钮的标签是单个QChar。当显示“符号”键盘时,代码使用'&'QChar作为键标签,但是键显示为空白。我确定Qt会将'&'作为快捷键前缀处理。同样,输入的文本将显示在另一个较长的按钮标签上。该标签也将“&”字符用作加速器。输入“ ABC&DEF”显示为“ ABCDEF”,带下划线“ D”。

我尝试使用#QT_NO_SHORTCUT进行构建,但这没什么区别。

有人知道禁用这种对'&'的特殊处理的简单方法吗?

1 个答案:

答案 0 :(得分:1)

答案可在Qt文档中找到。 QAbstractButton::text

  

如果文本包含“&”字符,则会自动为其创建快捷方式。 “&”后面的字符将用作快捷键。如果文本未定义任何快捷方式,则任何先前的快捷方式都将被覆盖或清除。有关详细信息,请参见QShortcut文档。 要显示实际的与号,请使用“ &&”

(请强调一下)

QPushButton源自QAbstractButton,继承了这种行为。

示例testQPushButtonAmp.cc

#include <QtWidgets>

int main(int argc, char **argv)
{
  qDebug() << "Qt Version:" << QT_VERSION_STR;
  QApplication app(argc, argv);
  QPushButton qBtn("Text with &&");
  qBtn.show();
  return app.exec();
}

testQPushButtonAmp.pro

SOURCES = testQPushButtonAmp.cc

QT = widgets

已在Windows 10的cygwin64上进行了编译和测试:

$ qmake-qt5 testQPushButtonAmp.pro

$ make

$ ./testQPushButtonAmp
Qt Version: 5.9.4

snapshot of testQPushButtonAmp


关于如何禁用此默认行为

我看了woboq.org QAbstractButton::setText()

void QAbstractButton::setText(const QString &text)
{
    Q_D(QAbstractButton);
    if (d->text == text)
        return;
    d->text = text;
#ifndef QT_NO_SHORTCUT
    QKeySequence newMnemonic = QKeySequence::mnemonic(text);
    setShortcut(newMnemonic);
#endif
    d->sizeHint = QSize();
    update();
    updateGeometry();
#ifndef QT_NO_ACCESSIBILITY
    QAccessibleEvent event(this, QAccessible::NameChanged);
    QAccessible::updateAccessibility(&event);
#endif
}

因此,QT_NO_SHORTCUT禁止从文本中检索快捷方式,但必须在从源代码构建Qt库时定义它。实际上,恐怕即使禁用了快捷键,单个&仍将在输出中不可见。

我在woboq.org中进行了更深入的挖掘,发现了一些有希望的候选人,例如:

qt_set_sequence_auto_menmonic()

  

指定是否应遵守菜单项,标签等的助记符。在Windows和X11上,此功能默认情况下处于启用状态。在macOS上,它已关闭。关闭此功能时(即b为false时),QKeySequence::mnemonic()始终返回空字符串。

     

注意:此功能未在任何Qt头文件中声明。要在您的应用程序中使用它,请在调用它之前声明函数原型。

QProxyStyle

中的示例
#include "textedit.h"
#include <QApplication>
#include <QProxyStyle>

class MyProxyStyle : public QProxyStyle
{
  public:
    int styleHint(StyleHint hint, const QStyleOption *option = 0,
                  const QWidget *widget = 0, QStyleHintReturn *returnData = 0) const override
    {
        if (hint == QStyle::SH_UnderlineShortcut)
            return 0;
        return QProxyStyle::styleHint(hint, option, widget, returnData);
    }
};

int main(int argc, char **argv)
{
    Q_INIT_RESOURCE(textedit);

    QApplication a(argc, argv);
    a.setStyle(new MyProxyStyle);
    TextEdit mw;
    mw.resize(700, 800);
    mw.show();
    //...
}

我在示例中尝试过。

最后,它们中没有一个达到预期的效果,即只有"&&"被渲染为&,而"&"却没有。

__