Qt中QGraphicsView三種座標系統詳解

henry_gyr發表於2015-02-28

在QGraphicsView中支援三種不同的座標系統---視口座標、場景座標、項座標

場景座標就是系統視窗(QGraphicsScene)的座標,它(0,0)作為它的左上角座標.

視口座標相當於場景座標的數學變換,如當一個視窗座標為(0,0)至(100,100)那麼這個視窗就是實實在在的由100*100個畫素組成,此時把座標變換為(-50,50)(即場景座標(0,0))至(50,-50)(即場景座標為(100,100))那麼這個視口座標就是以(0,0)為中心了.當放大縮小item時可以改變視口座標的大小(如放大1倍)視口座標可以變為(0,0)至(50,50).

而項座標則為item本身的座標,它不隨場景座標、視口座標變化並且以(0,0)為中心.

在c++ GUI Qt程式設計(第二版) Cityscape中有段這樣的程式:

QRectF Annotation::boundingRect()const
{
    QFontMetrics metrics(font);
    QRectF rect=metrics.boundingRect(str);//計算文字外接矩形
    rect.translate(-rect.center());
    rect.adjust(-4,0,+4,0);
    return rect;
}

一開始我看到這段程式時總是不理解rect的座標是怎麼來的,它是用str計算外接矩形,但是外接矩形哪裡有座標呢?後來仔細想想在這程式之前在圖表應用程式中也有這樣的程式碼,書上是這樣說的:"由字型規格函式返回的外接矩形總是把(0,0)作為其左上角".現在理解這句話的意思為:rect的座標是項座標,它把項的中心作為其左上角的頂點(好像除了這種方法也無其它方法給它座標了,這種方法想想也很合理,不論外接矩形和項的尺寸有多大總是將外接矩形的左上角放在項的中間).

void Annotation::paint(QPainter *painter,
                       const QStyleOptionGraphicsItem *option,
                       QWidget *widget)
{
    if(option->levelOfDetail<=threshold)
        return;
    painter->setFont(font);
    QRectF rect=boundingRect();
    int alpha=int(30*std::log(option->levelOfDetail));
    if(alpha>=32){
        qDebug()<<"\ndraw white rect";

    } painter->fillRect(rect,QColor(100,255,255,80));
    painter->setPen(Qt::white);
    //建立陰影效果
    painter->drawText(rect.translated(+1,+1),str,
                      QTextOption(Qt::AlignCenter));
    painter->setPen(Qt::blue);
    painter->drawText(rect,str,QTextOption(Qt::AlignCenter));
}
在paint函式中painter直接用rect繪圖這是因為Annotation的父類中setPos()設定了Annotatio的場景座標.

void QPainter::​fillRect(const QRectF & rectangle, const QBrush & brush)
fillRect等函式形參座標為項座標,在函式內項座標與場景座標合成就能繪出指定位置的item了


相關文章