Keeping the aspect ratio of a sub-classed QWidget during resize

后端 未结 2 755
天命终不由人
天命终不由人 2021-01-11 11:36

I\'m creating a new widget, by subclassing the QWidget class. I\'d like to be able to set a ratio (for its height and its width) for this widget, which will always be mainta

2条回答
  •  佛祖请我去吃肉
    2021-01-11 11:51

    Create a parent widget (e.g., AspectRatioWidget) in which to place your widget. For the parent widget, subclass QWidget and give it a QBoxLayout. Put your widget into the center, and QSpacerItems on either side. Then in the parent widget's QWidget::resizeEvent adjust the direction and stretches as needed. I've provided an example below. To use, just create an instance of AspectRatioWidget and pass the constructor a pointer to your widget and the desired aspect ratio.

    // header
    class AspectRatioWidget : public QWidget
    {
    public:
        AspectRatioWidget(QWidget *widget, float width, float height, QWidget *parent = 0);
        void resizeEvent(QResizeEvent *event);
    
    private:
        QBoxLayout *layout;
        float arWidth; // aspect ratio width
        float arHeight; // aspect ratio height
    };
    
    // cpp
    AspectRatioWidget::AspectRatioWidget(QWidget *widget, float width, float height, QWidget *parent) :
        QWidget(parent), arWidth(width), arHeight(height)
    {
        layout = new QBoxLayout(QBoxLayout::LeftToRight, this);
    
        // add spacer, then your widget, then spacer
        layout->addItem(new QSpacerItem(0, 0));
        layout->addWidget(widget);
        layout->addItem(new QSpacerItem(0, 0));
    }
    
    void AspectRatioWidget::resizeEvent(QResizeEvent *event)
    {
        float thisAspectRatio = (float)event->size().width() / event->size().height();
        int widgetStretch, outerStretch;
    
        if (thisAspectRatio > (arWidth/arHeight)) // too wide
        {
            layout->setDirection(QBoxLayout::LeftToRight);
            widgetStretch = height() * (arWidth/arHeight); // i.e., my width
            outerStretch = (width() - widgetStretch) / 2 + 0.5;
        }
        else // too tall
        {
            layout->setDirection(QBoxLayout::TopToBottom);
            widgetStretch = width() * (arHeight/arWidth); // i.e., my height
            outerStretch = (height() - widgetStretch) / 2 + 0.5;
        }
    
        layout->setStretch(0, outerStretch);
        layout->setStretch(1, widgetStretch);
        layout->setStretch(2, outerStretch);
    }
    

提交回复
热议问题