【Qt筆記】繪製設備

繪圖設備是繼承QPainterDevice的類。QPaintDevice就是可以進行繪製的類,也就是說,QPainter能夠在任何QPaintDevice的子類上進行繪製。如今,Qt 提供了若干這樣的類:數組

在 Qt5 中,QGLPixelBuffer已經被廢棄。本章咱們關注的是QPixmapQBitmapQImageQPicture這幾個類。另外的部分,QWidget就是全部組件的父類,咱們已經在前面的章節中使用過,這裏再也不贅述。QGLWidgetQGLFramebufferObject,顧名思義,就是關於 OpenGL 的相關類。在 Qt 中,咱們能夠方便地結合 OpenGL 進行繪製。因爲這部分須要牽扯到 OpenGL 的相關內容,如今也再也不深刻。在咱們選擇的幾個類中,大多與圖像密切相關。svg

QPixmap專門爲圖像在屏幕上的顯示作了優化;QBitmapQPixmap的一個子類,它的色深限定爲1,你可使用QPixmapisQBitmap()函數來肯定這個QPixmap是否是一個QBitmapQImage專門爲圖像的像素級訪問作了優化。QPicture則能夠記錄和重現QPainter的各條命令。下面咱們將分兩部分介紹這四種繪圖設備。函數

QPixmap繼承了QPaintDevice,所以,你可使用QPainter直接在上面繪製圖形。QPixmap也能夠接受一個字符串做爲一個文件的路徑來顯示這個文件,好比你想在程序之中打開 png、jpeg 之類的文件,就可使用QPixmap。使用QPainter::drawPixmap()函數能夠把這個文件繪製到一個QLabelQPushButton或者其餘的設備上面。正如前面所說的那樣,QPixmap是針對屏幕進行特殊優化的,所以,它與實際的底層顯示設備息息相關。注意,這裏說的顯示設備並非硬件,而是操做系統提供的原生的繪圖引擎。因此,在不一樣的操做系統平臺下,QPixmap的顯示可能會有所差異。性能

QPixmap提供了靜態的grabWidget()grabWindow()函數,用於將自身圖像繪製到目標上。同時,在使用QPixmap時,你能夠直接使用傳值的形式,不須要傳指針,由於QPixmap提供了「隱式數據共享」。關於這一點,咱們會在之後的章節中詳細描述。簡單來講,就是通常對於大型數據(圖像無疑就是這種「大型數據」),爲性能起見,一般會採用傳指針的方式,可是因爲QPixmap內置了隱式數據共享,因此只要知道傳遞QPixmap優化

前面說過,QBitmap繼承自QPixmap,所以具備QPixmap的全部特性。不一樣之處在於,QBitmap的色深始終爲 1。色深這個概念來自計算機圖形學,是指用於表現顏色的二進制的位數。咱們知道,計算機裏面的數據都是使用二進制表示的。爲了表示一種顏色,咱們也會使用二進制。好比咱們要表示 8 種顏色,須要用 3 個二進制位,這時咱們就說色深是 3。所以,所謂色深爲 1,也就是使用 1 個二進制位表示顏色。1 個位只有兩種狀態:0 和 1,所以它所表示的顏色就有兩種,黑和白。因此說,QBitmap其實是隻有黑白兩色的圖像數據。因爲QBitmap色深小,所以只佔用不多的存儲空間,因此適合作光標文件和筆刷。this

下面咱們來看同一個圖像文件在QPixmapQBitmap下的不一樣表現:操作系統

void paintEvent(QPaintEvent *)
{
    QPainter painter(this);
    QPixmap pixmap("qt-logo.png");
    QBitmap bitmap("qt-logo.png");
    painter.drawPixmap(10, 10, 250, 125, pixmap);
    painter.drawPixmap(270, 10, 250, 125, bitmap);
    QPixmap whitePixmap("qt-logo-white.png");
    QBitmap whiteBitmap("qt-logo-white.png");
    painter.drawPixmap(10, 140, 250, 125, whitePixmap);
    painter.drawPixmap(270, 140, 250, 125, whiteBitmap);
}

先來看一下運行結果:指針

這裏咱們給出了兩張 png 圖片。qt-logo.png 具備透明背景,qt-logo-white.png 具備白色背景。咱們分別使用QPixmapQBitmap來加載它們。注意看它們的區別:白色的背景在QBitmap中消失了,而透明色在QBitmap中轉換成了黑色(「黑色」,記住,QBitmap只有兩種顏色:黑色和白色);其餘顏色則是使用點的疏密程度來體現的。code

QPixmap使用底層平臺的繪製系統進行繪製,沒法提供像素級別的操做,而QImage則是使用獨立於硬件的繪製系統,其實是本身繪製本身,所以提供了像素級別的操做,而且可以在不一樣系統之上提供一個一致的顯示形式。orm

QImageQPixmap相比,最大的優點在於可以進行像素級別的操做。咱們經過上面的示意圖能夠看到,咱們聲明一個 3 x 3 像素的QImage對象,而後利用setPixel()函數進行顏色的設置。你能夠把QImage想象成一個 RGB 顏色的二維數組,記錄了每一像素的顏色。值得注意的是,在QImage上進行繪製時,不能使用QImage::Format_Indexed8這種格式。

最後一種QPicture是平臺無關的,所以它可使用在多種設備之上,好比 svg、pdf、ps、打印機或者屏幕。回憶下咱們曾經說的QPaintDevice,其實是說能夠由QPainter進行繪製的對象。QPicture使用系統分辨率,而且能夠調整QPainter來消除不一樣設備之間的顯示差別。若是咱們要記錄下QPainter的命令,首先要使用QPainter::begin()函數,將QPicture實例做爲參數傳遞進去,以便告訴系統開始記錄,記錄完畢後使用QPainter::end()命令終止。代碼示例以下:

QPicture picture;
QPainter painter;
painter.begin(&picture);             // 在 picture 進行繪製
painter.drawEllipse(10, 20, 80, 70); // 繪製一個橢圓
painter.end();                       // 繪製完成
picture.save("drawing.pic");         // 保存 picture

若是咱們要重現命令,首先要使用 QPicture::load() 函數進行裝載:

QPicture picture;
picture.load("drawing.pic");           // 加載 picture
QPainter painter;
painter.begin(&myImage);               // 在 myImage 上開始繪製
painter.drawPicture(0, 0, picture);    // 在 (0, 0) 點開始繪製 picture
painter.end();                         // 繪製完成

咱們也能夠直接使用QPicture::play()進行繪製。這個函數接受一個QPainter對象,也就是進行繪製的畫筆。

相關文章
相關標籤/搜索