QT:在调整大小时强制主窗口的纵横比

时间:2014-12-16 20:18:19

标签: c++ qt resize aspect-ratio

我正在尝试在调整大小时保持主窗口的宽高比,不幸的是我在调整大小时会出现闪烁。

代码:

// maindialog.h

#ifndef MAINDIALOG_H
#define MAINDIALOG_H

#include <QDialog>
#include <QLabel>
#include <QSize>
#include <QImage>
#include <QPixmap>
#include <QSlider>
#include <QResizeEvent>

// aspect ratio
#define ASPECT_HEIGHT_9(width) ( ( width / 16 ) * 9 )
#define ASPECT_HEIGHT_10(width) ( ( width / 16 ) * 10 )

#define ASPECT_WIDTH_9(height) ( ( height / 9 ) * 16 )
#define ASPECT_WIDTH_10(height) ( ( height / 10 ) * 16 )

// padding
#define PADDING 5
#define X_2_PADDING 10

// main window
#define DEFAULT_WIDTH 1280
#define DIMENSIONS QSize( DEFAULT_WIDTH, ASPECT_HEIGHT_9(DEFAULT_WIDTH) )

// video
#define VIDEO_SCALE_FACTOR 0.8
#define VIDEO_WIDTH DEFAULT_WIDTH * VIDEO_SCALE_FACTOR
#define VIDEO_HEIGHT ASPECT_HEIGHT_10(VIDEO_WIDTH)

// seeker
#define VIDEO_SEEKER_HEIGHT 20

class MainDialog : public QDialog
{
    Q_OBJECT

public:
    MainDialog(QWidget *parent = 0);
    ~MainDialog();

signals:
    void resized(QSize size);

private slots:
    void on_seeker_valueChanged(int value);
    void on_resize(QSize size);

protected:
    void resizeEvent(QResizeEvent * event);

private:
    QLabel *video;
    QSlider *seeker;
};

#endif // MAINDIALOG_H

// maindialog.cpp

#include "maindialog.h"

MainDialog::MainDialog(QWidget *parent)
    : QDialog(parent),
      video(new QLabel(this)),
      seeker(new QSlider(Qt::Horizontal, this))
{
    connect(this, SIGNAL(resized(QSize)), this, SLOT(on_resize(QSize)));
    connect(seeker, SIGNAL(valueChanged(int)), this, SLOT(on_videoSeeker_valueChanged(int)));
    video->move(PADDING, PADDING);
    video->setScaledContents(true);
    emit resized(DIMENSIONS);
}

void MainDialog::on_resize(QSize size){
    resize(size);

    // Video
    int width = size.width() * VIDEO_SCALE_FACTOR;
    video->resize(width, ASPECT_HEIGHT_10(width));
    QImage image(video->size(), QImage::Format_RGB888);
    video->setPixmap(QPixmap::fromImage(image));

    // seeker
    seeker->move(video->x() + PADDING, video->y() + video->height() + PADDING);
    seeker->resize(video->width() - X_2_PADDING, VIDEO_SEEKER_HEIGHT);
}

void MainDialog::on_seeker_valueChanged(int value){
    // implement with opencv
}

void MainDialog::resizeEvent(QResizeEvent *event){
    QSize _old = event->oldSize();
    QSize _new = event->size();
    QSize updated;
    updated = _old.width() != _new.width() ?
              QSize( _new.width(), ASPECT_HEIGHT_9( _new.width() ) ) :
              QSize( ASPECT_WIDTH_9( _new.height() ), _new.height() );

    emit resized(updated);
}

MainDialog::~MainDialog() {
    delete video;
    delete seeker;
}

这种做法不可能是正确的!除了闪烁之外,resize内的resizeEvent(QResizeEvent *event)窗口似乎不是一个好主意。

问题:

当调整窗口大小时,如何(智能地)保持宽高比?

有没有办法完全覆盖调整大小操作?

0 个答案:

没有答案