在设计模式下创建的视图上的 QGraphicsView fitInView 不起作用
QGraphicsView fitInView on view created in Design mode doesn't work
我一直在与 QGraphicsView
和 fitInView()
作斗争。
我创建了一个场景(非常大)和一个必须在加载时显示的矩形。但是当加载时,视图总是被缩小得很远。
所以我创建了一个小测试程序,fitInView
工作得很好!
经过一番努力,试图找出问题所在,我发现我的小测试和巨型程序之间的唯一区别是,巨型程序使用了创建的设计器 ui。
所以这是我重现它的尝试:
classes.h
#include <QGraphicsView>
#include <QGraphicsRectItem>
class MyView : public QGraphicsView
{
public:
MyView(QWidget *parent = 0) : QGraphicsView(parent) {
setBackgroundRole(QPalette::Highlight);
}
};
class MyScene : public QGraphicsScene
{
public:
MyScene(qreal sceneW, qreal sceneH, qreal canvasW, qreal canvasH, QObject* parent = 0)
: QGraphicsScene(parent) {
setSceneRect(0.5*(canvasW - sceneW), 0.5*(canvasH - sceneH), sceneW, sceneH);
m_background = new QGraphicsRectItem();
m_background->setBrush(Qt::white);
m_background->setPen(Qt::NoPen);
m_background->setRect(0, 0, canvasW, canvasH);
addItem(m_background);
}
private:
QGraphicsRectItem* m_background;
};
main.cpp
#define USING_UI
#include <QApplication>
#include "classes.h"
#ifdef USING_UI
#include <QMainWindow>
#include "ui_form.h"
namespace Ui {
class MainWindow;
}
class MainWindow : public QMainWindow {
public:
explicit MainWindow(QWidget *parent=0):QMainWindow(parent),ui(new Ui::MainWindow) {
ui->setupUi(this);
MyScene* s = new MyScene(2000, 1000, 500, 300);
ui->myGraphicsView->setScene(s);
ui->myGraphicsView->fitInView(0,0,500,300); // with Qt::KeepAspectRatio
// or ui->myGraphicsView->fitInView(s->items().at(0), Qt::KeepAspectRatio);
}
private:
Ui::MainWindow *ui;
};
int main(int argc, char *argv[])
{
QApplication app(argc, argv);
MainWindow w;
w.show();
return app.exec();
}
#else
int main(int argc, char *argv[])
{
QApplication app(argc, argv);
MyScene s(2000, 1000, 500, 300);
MyView view;
view.setScene(&s);
view.show();
view.fitInView(0,0,500,300); // with Qt::KeepAspectRatio for pretty
// or view.fitInView(s.items().at(0), Qt::KeepAspectRatio);
return app.exec();
}
#endif
并且 form.ui
包含一个 QGraphicsView
提升为 MyView
,没有别的。
结果非常不同 - 我不知道如何修复 ui 版本。
我该怎么做才能使在 ui(使用 Qt Designer)中创建的视图 "fit in view" 我在启动时建议的矩形或对象?
我觉得很奇怪
qDebug() << s->sceneRect();
qDebug() << ui->myGraphicsView->mapToScene(s->sceneRect().toRect()).boundingRect();
qDebug() << ui->myGraphicsView->mapFromScene(s->sceneRect()).boundingRect();
都显示相同的东西,
QTransform t = ui->myGraphicsView->viewportTransform();
是统一的。
也许我可以找到一种方法来手动设置此变换 - 基于视口的实际坐标 - 但我不知道如何 - 或者如果稍后表单更改大小会发生什么。
我在 answer.
中找到了问题的答案
将 fitInView
调用放入 class' showEvent
。
protected:
virtual void showEvent(QShowEvent *event) {
if(m_startUp)
{
ui->myGraphicsView->fitInView(s->items().at(0), Qt::KeepAspectRatio);
// or, either works fine:
// ui->myGraphicsView->fitInView(0,0,500,300, Qt::KeepAspectRatio);
m_startUp = false;
}
QMainWindow::showEvent(event);
}
我添加了 m_startUp
因为在缩放和最小化之后,恢复将执行 fitInView
...
我找到的唯一替代方法是根据 UI 几何形状,通过反复试验找到一些值用于 fitInView
...这似乎不是一个好的选择。
我一直在与 QGraphicsView
和 fitInView()
作斗争。
我创建了一个场景(非常大)和一个必须在加载时显示的矩形。但是当加载时,视图总是被缩小得很远。
所以我创建了一个小测试程序,fitInView
工作得很好!
经过一番努力,试图找出问题所在,我发现我的小测试和巨型程序之间的唯一区别是,巨型程序使用了创建的设计器 ui。
所以这是我重现它的尝试:
classes.h
#include <QGraphicsView>
#include <QGraphicsRectItem>
class MyView : public QGraphicsView
{
public:
MyView(QWidget *parent = 0) : QGraphicsView(parent) {
setBackgroundRole(QPalette::Highlight);
}
};
class MyScene : public QGraphicsScene
{
public:
MyScene(qreal sceneW, qreal sceneH, qreal canvasW, qreal canvasH, QObject* parent = 0)
: QGraphicsScene(parent) {
setSceneRect(0.5*(canvasW - sceneW), 0.5*(canvasH - sceneH), sceneW, sceneH);
m_background = new QGraphicsRectItem();
m_background->setBrush(Qt::white);
m_background->setPen(Qt::NoPen);
m_background->setRect(0, 0, canvasW, canvasH);
addItem(m_background);
}
private:
QGraphicsRectItem* m_background;
};
main.cpp
#define USING_UI
#include <QApplication>
#include "classes.h"
#ifdef USING_UI
#include <QMainWindow>
#include "ui_form.h"
namespace Ui {
class MainWindow;
}
class MainWindow : public QMainWindow {
public:
explicit MainWindow(QWidget *parent=0):QMainWindow(parent),ui(new Ui::MainWindow) {
ui->setupUi(this);
MyScene* s = new MyScene(2000, 1000, 500, 300);
ui->myGraphicsView->setScene(s);
ui->myGraphicsView->fitInView(0,0,500,300); // with Qt::KeepAspectRatio
// or ui->myGraphicsView->fitInView(s->items().at(0), Qt::KeepAspectRatio);
}
private:
Ui::MainWindow *ui;
};
int main(int argc, char *argv[])
{
QApplication app(argc, argv);
MainWindow w;
w.show();
return app.exec();
}
#else
int main(int argc, char *argv[])
{
QApplication app(argc, argv);
MyScene s(2000, 1000, 500, 300);
MyView view;
view.setScene(&s);
view.show();
view.fitInView(0,0,500,300); // with Qt::KeepAspectRatio for pretty
// or view.fitInView(s.items().at(0), Qt::KeepAspectRatio);
return app.exec();
}
#endif
并且 form.ui
包含一个 QGraphicsView
提升为 MyView
,没有别的。
结果非常不同 - 我不知道如何修复 ui 版本。
我该怎么做才能使在 ui(使用 Qt Designer)中创建的视图 "fit in view" 我在启动时建议的矩形或对象?
我觉得很奇怪
qDebug() << s->sceneRect();
qDebug() << ui->myGraphicsView->mapToScene(s->sceneRect().toRect()).boundingRect();
qDebug() << ui->myGraphicsView->mapFromScene(s->sceneRect()).boundingRect();
都显示相同的东西,
QTransform t = ui->myGraphicsView->viewportTransform();
是统一的。
也许我可以找到一种方法来手动设置此变换 - 基于视口的实际坐标 - 但我不知道如何 - 或者如果稍后表单更改大小会发生什么。
我在 answer.
中找到了问题的答案将 fitInView
调用放入 class' showEvent
。
protected:
virtual void showEvent(QShowEvent *event) {
if(m_startUp)
{
ui->myGraphicsView->fitInView(s->items().at(0), Qt::KeepAspectRatio);
// or, either works fine:
// ui->myGraphicsView->fitInView(0,0,500,300, Qt::KeepAspectRatio);
m_startUp = false;
}
QMainWindow::showEvent(event);
}
我添加了 m_startUp
因为在缩放和最小化之后,恢复将执行 fitInView
...
我找到的唯一替代方法是根据 UI 几何形状,通过反复试验找到一些值用于 fitInView
...这似乎不是一个好的选择。