如何在 QGraphicsView 的中心显示 QDialog?
How to show a QDialog in center of a QGraphicsView?
我有一个 QGraphicsView 子类,我想在项目的上下文菜单上显示一个属性对话框。
我希望对话框在视图中居中...
我现在有,没有parent,显示在屏幕中央。
MyView::MyView(QWidget *parent) : QGraphicsView(parent) {}
void MyView::showProperties()
{
TabDialog *tabDialog = new TabDialog(); // shows in center of screen
// TabDialog *tabDialog = new TabDialog(this); // doesn't show at all
// TabDialog *tabDialog = new TabDialog((QWidget*)this->parent()); // doesn't show at all
tabDialog->setWindowFlags(Qt::WindowCloseButtonHint | Qt::WindowSystemMenuHint);
tabDialog->exec();
delete tabDialog;
}
视图放置在组框中...所以 parent 是组框...
如何使用 parent 调用对话框?
您必须将对话框设置为顶级 window,而不仅仅是将嵌入到您的视图中的子窗口小部件。您的 setWindowsFlags
调用会重置对话框中的相关标志。您需要手动保存它们。
您也不应该使用 exec()
重新进入事件循环,因为这需要您的许多其他代码也需要可重入。
一个最小的修复看起来像:
void MyView::showProperties()
{
auto dialog = new TabDialog(this);
dialog->setWindowFlags(Qt::Dialog |
Qt::WindowCloseButtonHint |
Qt::WindowSystemMenuHint);
dialog->setAttribute(Qt::WA_DeleteOnClose);
dialog->show();
}
也许您想缓存对话框:
class MyView : public ... {
QPointer<TabDialog> m_tabDialog; // nulls itself when the dialog perishes
QTimer m_tabDialogTimer;
...
};
MyView::MyView(...) {
m_tabDialogTimer->setSingleShot(true);
...
}
void MyView::showProperties() {
if (! m_tabDialog) {
m_tabDialog = new TabDialog(this);
m_tabDialog->setWindowFlags(Qt::Dialog |
Qt::WindowCloseButtonHint |
Qt::WindowSystemMenuHint);
QObject::connect(&m_tabDialogTimer, &QTimer::timeout,
m_tabDialog, &QObject::deleteLater);
QObject::connect(m_tabDialog, &QDialog::finished, [&this](int){
// the dialog gets deleted 120 seconds after last use
m_tabDialogTimer.start(120);
});
}
m_tabDialogTimer.stop(); // reset pending timeout, if any
m_tabDialog->show();
}
我有一个 QGraphicsView 子类,我想在项目的上下文菜单上显示一个属性对话框。
我希望对话框在视图中居中...
我现在有,没有parent,显示在屏幕中央。
MyView::MyView(QWidget *parent) : QGraphicsView(parent) {}
void MyView::showProperties()
{
TabDialog *tabDialog = new TabDialog(); // shows in center of screen
// TabDialog *tabDialog = new TabDialog(this); // doesn't show at all
// TabDialog *tabDialog = new TabDialog((QWidget*)this->parent()); // doesn't show at all
tabDialog->setWindowFlags(Qt::WindowCloseButtonHint | Qt::WindowSystemMenuHint);
tabDialog->exec();
delete tabDialog;
}
视图放置在组框中...所以 parent 是组框...
如何使用 parent 调用对话框?
您必须将对话框设置为顶级 window,而不仅仅是将嵌入到您的视图中的子窗口小部件。您的 setWindowsFlags
调用会重置对话框中的相关标志。您需要手动保存它们。
您也不应该使用 exec()
重新进入事件循环,因为这需要您的许多其他代码也需要可重入。
一个最小的修复看起来像:
void MyView::showProperties()
{
auto dialog = new TabDialog(this);
dialog->setWindowFlags(Qt::Dialog |
Qt::WindowCloseButtonHint |
Qt::WindowSystemMenuHint);
dialog->setAttribute(Qt::WA_DeleteOnClose);
dialog->show();
}
也许您想缓存对话框:
class MyView : public ... {
QPointer<TabDialog> m_tabDialog; // nulls itself when the dialog perishes
QTimer m_tabDialogTimer;
...
};
MyView::MyView(...) {
m_tabDialogTimer->setSingleShot(true);
...
}
void MyView::showProperties() {
if (! m_tabDialog) {
m_tabDialog = new TabDialog(this);
m_tabDialog->setWindowFlags(Qt::Dialog |
Qt::WindowCloseButtonHint |
Qt::WindowSystemMenuHint);
QObject::connect(&m_tabDialogTimer, &QTimer::timeout,
m_tabDialog, &QObject::deleteLater);
QObject::connect(m_tabDialog, &QDialog::finished, [&this](int){
// the dialog gets deleted 120 seconds after last use
m_tabDialogTimer.start(120);
});
}
m_tabDialogTimer.stop(); // reset pending timeout, if any
m_tabDialog->show();
}