QGraphicsViewおよびQGraphicsItem:ビューの四角形を拡大縮小するときに項目を拡大縮小しない
-
10-07-2019 - |
質問
Qtの QGraphicsView
-および QGraphicsItem
-サブクラスを使用しています。
ビューの四角形が変更されたときに、ビュー内のアイテムのグラフィカル表現をスケーリングしない方法があります。ズームインするときのデフォルトの動作は、アイテムがビューの四角形に合わせて拡大縮小することです。
ビューを拡大するときに拡大縮小しない薄い長方形で表される2dポイントを視覚化したい。頂点ポイントが常に同じサイズで表示されるリファレンスについては、典型的な3Dモデリングソフトウェアを参照してください。
ありがとう!
解決
QGraphicItem
のフラグ QGraphicsItem :: ItemIgnoresTransformations
をtrueに設定しても機能しませんか?
他のヒント
同じ問題に遭遇し、それを理解するのに時間がかかりました。これが私がそれを解決した方法です。
QGraphicsItemクラスを拡張し、paint()をオーバーライドします。 paint()内で、変換のスケーリング係数を1(m11およびm22)にリセットし、リセット前にm11(xスケーリング係数)およびm22(yスケーリング係数)を保存します。 次に、通常のように描画しますが、xにm11を、yにm22を掛けます。これにより、デフォルトの変換を使用した描画が回避されますが、シーンの変換に従って位置が明示的に計算されます。
void MyItem::paint(QPainter *painter, const QStyleOptionGraphicsItem *item, QWidget *widget)
{
QTransform t = painter->transform();
qreal m11 = t.m11(), m22 = t.m22();
painter->save(); // save painter state
painter->setTransform(QTransform(m11, t.m12(), t.m13(),
t.m21(), 1, t.m23(), t.m31(),
t.m32(), t.m33()));
int x = 0, y = 0; // item's coordinates
painter->drawText(x*m11, y*m22, "Text"); // the text itself will not be scaled, but when the scene is transformed, this text will still anchor correctly
painter->restore(); // restore painter state
}
次のコードブロックはデフォルトの変換で描画しています
void MyItem::paint(QPainter *painter, const QStyleOptionGraphicsItem *item, QWidget *widget)
{
int x = 0, y = 0;
painter->drawText(x, y, "Text");
}
両方を試して、違いを確認できます。お役に立てれば。
これについてはどうですか:
#include <QtGui/QApplication>
#include <QtGui/QGraphicsScene>
#include <QtGui/QGraphicsView>
#include <QtGui/QGraphicsRectItem>
int main(int argc, char* argv[]) {
QApplication app(argc, argv);
QGraphicsScene scene;
scene.addText("Hello, world!");
QRect rect(50, 50, 100, 100);
QGraphicsRectItem* recti = scene.addRect(rect);
QGraphicsView view(&scene);
// Set scale for the view
view.scale(10.0, 5.0);
// Set the inverse transformation for the item
recti->setTransform(view.transform().inverted());
view.show();
return app.exec();
}
ご覧のとおり、テキストは拡大されていますが、長方形は拡大されていません。これは、長方形のスケーリングだけでなく、その他の変換も防ぐことに注意してください。
新しいクラスを派生させ、ペイント機能を再実装すると、できることを見つけました
void MyDerivedQGraphicsItem::paint(QPainter *painter,
const QStyleOptionGraphicsItem *option,
QWidget *widget)
{
double scaleValue = scale();
double scaleX = painter->transform().m11();
setScale(scaleValue / scaleX);
QGraphicsSvgItem::paint(painter,option,widget);
}
これは私がこれまでに見つけた最善の方法ですが、まだいじくり回しています。
次の解決策は私にとって完璧に機能しました:
void MyDerivedQGraphicsItem::paint(QPainter *painter, const StyleOptionGraphicsItem *option, QWidget *widget)
{
double scaleValue = scale()/painter->transform().m11();
painter->save();
painter->scale(scaleValue, scaleValue);
painter->drawText(...);
painter->restore();
...
}
scaleValueに、保存/復元環境外でサイズを一定に保ちたい他の測定値を掛けることもできます。
QPointF ref(500, 500);
QPointF vector = scaleValue * QPointF(100, 100);
painter->drawLine(ref+vector, ref-vector);