[英]QFileDialog: force file name
我想創建一個QFileDialog
設置為QFileDialog::AnyFile
,其中文件名是固定的(但位置可以更改)。
到目前為止,我發現了問題QFileDialog - Saving a file with specified file name ,沒有得到回答。
有直接選擇目錄的偽答案,這是我迄今為止在我的項目中所做的。 然而,通過人們測試該程序,發現這令人困惑,因此不是一個可接受的答案。
到目前為止,我嘗試的是派生QFileDialog
然后強制執行此操作,但我不知道該嘗試什么了。 當點擊不同的文件時,我設法通過對適當的信號做出反應來重置文件名:
FixedFileDialog::FixedFileDialog(QWidget* parent) : QFileDialog(parent)
{
connect(this, SIGNAL(currentUrlChanged(const QString&)), this, SLOT(current_changed(const QString&)));
}
void FixedFileDialog::current_changed(const QString&)
{
selectFile(_filename);
}
(以_filename
為開頭的成員集。)
到目前為止,這有效,但它不會阻止用戶在行編輯中輸入不同的名稱。 而且我還沒有發現在這種情況下發出的任何信號。
另一種嘗試是嘗試訪問QLineEdit
小部件本身以禁用它,但我不知道如何。 我試過了
QLineEdit* line_edit = dialog.d_func()->lineEdit();
( dialog
是派生的 class。)
這不起作用,因為d_func()
在QFileDialog
中是私有的。
有人有其他想法該怎么做嗎?
我必須承認,我想到的是一個骯臟的黑客。 另一方面,OP對我來說似乎有些絕望。 所以,我把它貼出來(帶着一些疑問)。
由於OP的聲明,我提出了我的想法:
QLineEdit* line_edit = dialog.d_func()->lineEdit();
(對話框是派生的 class。)
這不起作用,因為
d_func()
在QFileDialog
中是私有的。
雖然d_func()
是私有的,但 Qt 小部件提供了一種后門,因為它們的所有權管理可以被利用:
每個QObject
都提供一個其子對象的列表。 因此,對這個子樹的簡單遍歷應該在 quest 中傳遞QLineEdit
(這是我在 Qt 5.13 中QFileDialog
的當前實現中唯一的一個)。
這是我在示例中嘗試的:
/ Qt header:
#include <QtWidgets>
QLineEdit* findFirstQLineEdit(QWidget *pQWidget)
{
//qDebug() << "Inspect" << pQWidget;
const QObjectList pQObjs = pQWidget->children();
for (QObject *pQObj : pQObjs) {
if (QLineEdit *pQLineEdit = dynamic_cast<QLineEdit*>(pQObj)) {
qDebug() << "Found:" << pQLineEdit;
return pQLineEdit;
} else if (QWidget *pQWidget = dynamic_cast<QWidget*>(pQObj)) {
if (QLineEdit *pQLineEdit = findFirstQLineEdit(pQWidget)) {
return pQLineEdit;
}
}
}
return nullptr;
}
// main application
int main(int argc, char **argv)
{
qDebug() << "Qt Version:" << QT_VERSION_STR;
QApplication app(argc, argv);
// setup GUI
QFileDialog qFileDlg(nullptr,
QString::fromUtf8("Choose Dir. to Save File"),
QDir::currentPath());
qFileDlg.show();
// manipulate the file name input
qFileDlg.selectFile("CMakeLists.txt");
QLineEdit *const pQEdit = findFirstQLineEdit(&qFileDlg);
pQEdit->setReadOnly(true);
// runtime loop
return app.exec();
}
Output:
文件名行編輯器是只讀的。 不允許編輯或刪除,但仍可以從外部復制和更改內容。 (對於這種情況,OP 似乎已經找到了另一種解決方案。)
筆記:
我的第一個想法是在派生自QFileDialog
的 class 的構造函數中調用findFirstQLineEdit()
。 這沒有用! 調試 output 證明QFileDialog
構造后沒有任何子級。 我得出的結論是, QFileDialog
的子項是稍后創建的——但肯定必須在show()
之后創建。
要將這個 hack 嵌入到派生的 class 中,在QFileDialog::showEvent()
的覆蓋中進行操作可能就足夠了。 (我沒有測試它。)
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.