1

Qtで次の基本的な画像ビューアを作成しましたが、期待どおりに動作せず、神聖なものへの愛のために、問題が何であるかを見つけることができません。基本的には、ムービーを jpeg/gif として設定し、サイズを変更して画面の中央に配置した QLabel です。問題は、起動時にサイズを変更したり、画面の中央に配置したりせず、代わりにウィンドウを埋めて画像を引き伸ばすことです。

例: http://i.imgur.com/6l9wA.jpg

QVBoxLayoutに入れても同じです。ただし、スケーリング/ズームを実行すると (keyRelease イベントで定義されているように「+」または「-」を押して)、画像が中央に配置され、完全にサイズ変更されます。

例: http://i.imgur.com/jGeUV.png

したがって、問題は画像をロードするときだけのようですが、どこにあるのかわかりません。私はそれが単純なものでなければならないことを知っていますが、Qtのドキュメント、グーグルを検索し、コメント行の組み合わせとさまざまな機能の追加を試みましたが、何も思いつきませんでした.

ところで、loadImage 関数の下部からの出力は正しいサイズと位置を出力しますが、それらを尊重していないようです。

#include <QtGui>
#include "imageviewer.h"

ImageViewer::ImageViewer(QString imagePath)
{
    setWindowTitle(imagePath + " - Simple Image Viewer");
    currentImageSize=new QSize(0,0);

    fillScreen();

    imageLabel = new QLabel;
    imageLabel->setBackgroundRole(QPalette::Base);
    imageLabel->setScaledContents(true);

    QVBoxLayout* layout=new QVBoxLayout();
    layout->addWidget(imageLabel);

    QFrame* frame=new QFrame();
    frame->setLayout(layout);
    //setCentralWidget(frame);

    setCentralWidget(imageLabel);

    loadImage(imagePath);
}

void ImageViewer::loadImage(QString imagePath){
    currentImagePath=imagePath;
    open(imagePath);
    fitImage();
    centerImage();
    QTextStream out(stdout) ;

    //for debugging:
    out << QString("size: %1 %2 pos: %3 %4")
              .arg(imageLabel->width())
              .arg(imageLabel->height())
              .arg(imageLabel->x())
              .arg(imageLabel->y());
}

void ImageViewer::open(QString imagePath){
      if (!imagePath.isEmpty()) {
        QImage image(imagePath);

        currentImageSize=new QSize(image.size().width(),image.size().height());

        if (image.isNull()) {
            QMessageBox::information(this, tr("Image Viewer"),
                                     tr("Cannot load %1.").arg(imagePath));
            return;
        }

        imageLabel->resize(currentImageSize->width(),
                           currentImageSize->height());
        QMovie* movie=new QMovie(imagePath);
        imageLabel->setMovie(movie);
        movie->start();

        scaleFactor = 1.0;

        imageLabel->adjustSize();
      }
}

void ImageViewer::fitImage(){
    int windowHeight, windowWidth;
    int imageHeight, imageWidth;

    windowHeight = this->height();
    windowWidth = this->width();
    imageHeight = currentImageSize->height();
    imageWidth = currentImageSize->width();

    if(imageHeight > windowHeight || imageWidth > windowWidth){
        imageLabel->resize((windowHeight-40)*imageWidth/imageHeight, 
                            windowHeight-40);
    }
}

void ImageViewer::centerImage(){
    int windowHeight, windowWidth;
    int imageHeight, imageWidth;

    windowHeight = this->height();
    windowWidth = this->width();
    imageHeight = imageLabel->height();
    imageWidth = imageLabel->width();

    int x,y;
    x=(windowWidth-imageWidth)/2;
    y=(windowHeight-imageHeight)/2;
    imageLabel->move(x,y);
}

void ImageViewer::fillScreen(){
    this->showMaximized();
}

void ImageViewer::scaleImage(double factor)
{
    double newScale = scaleFactor + factor;

    if(newScale>MAX_SCALE || newScale<MIN_SCALE){
        return;
    }
    else{
        scaleFactor=newScale;
    }

    QTextStream out(stdout);
    imageLabel->resize(scaleFactor * currentImageSize->width(), 
                       scaleFactor * currentImageSize->height());

    out<< scaleFactor << " " 
       << imageLabel->height() << "," 
       << imageLabel->width() <<endl;

    centerImage();
}


void ImageViewer::keyReleaseEvent(QKeyEvent *event){
    if(event->key()==Qt::Key_Plus){
        scaleImage(SCALE_STEP);
    }
    if(event->key()==Qt::Key_Minus){
        scaleImage(0-(SCALE_STEP));
    }
}

ヘッダーは次のとおりです。

#ifndef MAINWINDOW_H
#define MAINWINDOW_H

#include <QLabel>
#include <QMainWindow>

class ImageViewer : public QMainWindow
{
    Q_OBJECT

public:
    ImageViewer(QString imagePath);
    void open(QString imagePath);
    void loadImage(QString imagePath);
private:
    void fitImage();
    void centerImage();
    void fillScreen();
    void scaleImage(double);
    void adjustScrollBar(QScrollBar*,double);
    void keyReleaseEvent(QKeyEvent *);
private:
    QLabel* imageLabel;
    double scaleFactor;
    QSize* currentImageSize;
    QString currentImagePath;
    QString currentDir;
    QStringList neighbourImages;
    static const double MAX_SCALE=2.0;
    static const double MIN_SCALE=0.2;
    static const double SCALE_STEP=0.1;
};

#endif // MAINWINDOW_H

編集: これは、最初に読み込まれた後の QLabel と、一度ズームインした後の QLabel の違いです: diffchecker.com/1uDcb83

4

1 に答える 1

1

I believe the problem is that you are trying to calculate your sizes in the main window constructor. These sizes are not established at this point. You need to override QWidget::resizeEvent() (in ImageViewer) and do your sizing calculations there. That function is called after the geometry for the widget has been set.

于 2012-02-20T19:03:34.790 に答える