2015-12-15 57 views
22

我想使用Qt反射將enum轉換爲QString。如何將enum轉換爲QString?

這裏是代碼的一部分:

class ModelApple 
{ 
    Q_GADGET 
    Q_ENUMS(AppleType) 
public: 
    enum AppleType { 
     Big, 
     Small 
    } 
} 

,這裏是我想要做:

convertEnumToQString(ModelApple::Big) 

返回"Big"

這可能嗎? 如果您有關於convertEnumToQString任何想法,請分享

回答

31

您需要使用Q_ENUM宏, h使用元對象系統註冊一個枚舉類型。

enum AppleType { 
    Big, 
    Small 
}; 
Q_ENUM(AppleType) 

現在,您可以使用QMetaEnum類訪問關於枚舉器的元數據。

QMetaEnum metaEnum = QMetaEnum::fromType<ModelApple::AppleType>(); 
qDebug() << metaEnum.valueToKey(ModelApple::Big); 

這裏是這樣實用的通用模板:

template<typename QEnum> 
std::string QtEnumToString (const QEnum value) 
{ 
    return std::string(QMetaEnum::fromType<QEnum>().valueToKey(value)); 
} 
+5

'QMetaEnum :: fromType '可從Qt 5中獲得,它在Qt 4中不存在。您應該添加此註釋。順便說一下,我不推薦使用'QMetaEnum :: key',因爲它將'index'作爲參數,他怎麼會聲明'enum AppleType {Big = 2,Small}' – Danh

+3

從文檔看來,它看起來像這實際上僅在Qt 5.5中可用,因此我仍然需要在我給出的答案(即將更新我的代碼但現在必須使用Qt 5.4)中使用我的方法。 –

8

下面應該讓你去:

QString convertEnumToQString(ModelApple::AppleType type) { 
    const QMetaObject metaObject = ModelApple::staticMetaObject; 
    int enumIndex = metaObject.indexOfEnumerator("AppleType"); 
    if(enumIndex == -1) { 
     /* The enum does not contain the specified enum */ 
     return ""; 
    } 
    QMetaEnum en = metaObject.enumerator(enumIndex); 
    return QString(en.valueToKey(type)); 
} 
+0

你爲什麼不加入我們的聲明'enumString'和'enumString = en.valueToKey(type);'它只會調用1個構造函數,而不是1個構造函數和1個'operator ='。另外,我們可以用'-1'來消除這個檢查,因爲我們可以確定該枚舉存在。 – Danh

+0

所以我必須指定枚舉「AppleType」? – Jiu

+0

@Danh是的,你可以做到這一點。我的實際代碼是一個模板函數,它接受枚舉名和枚舉值來返回字符串。我修改它來回答這個問題。我的用法是'string = convertEnumToQString (「AppleType」,ModelApple :: Big);'所以我需要檢查一個有效的枚舉並斷言如果對於調試無效。此外,我在返回之前斷言,因此首先分配然後返回(純粹用於調試)的原因。 –

2

如何:

QString convertEnumToQString(ModelApple::AppleType type) 
{ 
    const QMetaObject &mo = ModelApple::staticMetaObject; 
    int index = mo.indexOfEnumerator("AppleType"); 
    QMetaEnum metaEnum = mo.enumerator(index); 
    return metaEnum.valueToKey(type); 
} 

更新: Qt的5.5,看到this answer

+0

編輯Qt 5 - > Qt 5.5,謝謝。 – Danh

1

我面臨同樣的問題,這是我如何解決它。這是專爲的Qt 4.8

QString string = enumToString(ModelApple::Big); 

QString ModelApple::enumToString(AppleType apple) 
{ 
    int index = metaObject()->indexOfEnumerator("AppleType"); 
    QMetaEnum metaEnum = metaObject()->enumerator(index); 
    return metaEnum.valueToKey(apple); 
} 
2

更優雅的方式發現(QT 5.9),只是一個單一的線,具有強大的QVariant的幫助。

變成枚舉轉換爲字符串:

QString theBig = QVariant::fromValue(ModelApple::Big).value<QString>(); 

也許你並不需要QMetaEnum了。

示例代碼在這裏:

ModelApple(無需要求Q_DECLARE_METATYE)

class ModelApple : public QObject 
{ 
    Q_OBJECT 
public: 
    enum AppleType { 
     Big, 
     Small 
    }; 
    Q_ENUM(AppleType) 
    explicit ModelApple(QObject *parent = nullptr); 
}; 

我創建窗件應用程序,調用QVaraint功能有:

#include "mainwindow.h" 
#include "ui_mainwindow.h" 
#include <modelapple.h> 
#include <QDebug> 

MainWindow::MainWindow(QWidget *parent) : 
    QMainWindow(parent), 
    ui(new Ui::MainWindow) 
{ 
    ui->setupUi(this); 

    QString s = QVariant::fromValue(ModelApple::Big).value<QString>(); 
    qDebug() << s; 

} 

MainWindow::~MainWindow() 
{ 
    delete ui; 
} 

你可以看到,我嘗試在控制檯上輸出字符串,這確實是: enter image description here

對於反向鑄造抱歉,我在某些項目中嘗試成功,但是這次我遇到了編譯錯誤。所以我決定從我的答案中刪除它。

+0

感謝您的回答,看起來像該方法需要添加'Q_DECLARE_METATYPE(ModelApple :: AppleType)',甚至添加使其編譯成功,結果是一個空字符串。你能不能發佈這個示例代碼? – Jiu

+0

@Jiu確定,請檢查我編輯的內容。 –

0

這裏是不使用Q_ENUM宏觀

#define Enum2QStr(x) (QString(#x).split(「::」).at(1)) 

臨道:你的枚舉並不需要是insde任何類(無Q_OBJECT成員或Q_ENUM要求)