How to display image in ratio as PreserveAspectFit in Qt Widgets - qt

In qml, I can simply do this
Image {
anchors.fill: parent
source: "/path/to/coo/image"
fillMode: Image.PreserveAspectFit
}
I don't want to use QML due to its ties with JavaScript. How can I do this with Widgets ?
I tried using QLabel but it has no option to set aspect ratio or fillMode. I think I can manually scale the pixmap and then set it to QLabel but that wont be reactive (resize image when window is resized) like QML. Isn't there any image specefic widget in Qt to do this ?

A possible solution is to use QGraphicsView, QGraphicsScene and QGraphicsPixmapItem:
#include <QApplication>
#include <QGraphicsPixmapItem>
#include <QGraphicsView>
#include <QPixmap>
class Viewer: public QGraphicsView{
public:
Viewer(QWidget *parent = nullptr): QGraphicsView(parent){
setScene(new QGraphicsScene(this));
m_pixmapItem = scene()->addPixmap(QPixmap());
setAlignment(Qt::AlignCenter);
}
QPixmap pixmap() const{
return m_pixmapItem->pixmap();
}
void setPixmap(const QPixmap &newPixmap){
m_pixmapItem->setPixmap(newPixmap);
fitInView(m_pixmapItem, Qt::KeepAspectRatio);
}
protected:
void resizeEvent(QResizeEvent *event){
QGraphicsView::resizeEvent(event);
fitInView(m_pixmapItem, Qt::KeepAspectRatio);
}
private:
QGraphicsPixmapItem *m_pixmapItem;
};
int main(int argc, char *argv[])
{
QApplication a(argc, argv);
QPixmap pixmap(100, 200);
pixmap.fill(Qt::green);
Viewer w;
w.resize(640, 480);
w.setPixmap(pixmap);
w.show();
return a.exec();
}
Python version:
from PyQt5.QtCore import Qt
from PyQt5.QtGui import QPixmap
from PyQt5.QtWidgets import QApplication, QGraphicsScene, QGraphicsView
class Viewer(QGraphicsView):
def __init__(self, parent=None):
super().__init__(parent)
self.setScene(QGraphicsScene(self))
self.m_pixmapItem = self.scene().addPixmap(QPixmap())
self.setAlignment(Qt.AlignCenter)
#property
def pixmap(self):
return self.m_pixmapItem.pixmap()
#pixmap.setter
def pixmap(self, newPixmap):
self.m_pixmapItem.setPixmap(newPixmap)
self.fitInView(self.m_pixmapItem, Qt.KeepAspectRatio)
def resizeEvent(self, event):
super().resizeEvent(event)
self.fitInView(self.m_pixmapItem, Qt.KeepAspectRatio)
def main():
import sys
app = QApplication(sys.argv)
pixmap = QPixmap(100, 200)
pixmap.fill(Qt.green)
w = Viewer()
w.resize(640, 480)
w.pixmap = pixmap
w.show()
sys.exit(app.exec_())
if __name__ == "__main__":
main()
``

you can simply do that:
QPixmap pixmap("background.png");
pixmap.scaled(pixmap.size(), Qt::KeepAspectRatio);
You can manipulate the size value as you wanna. If you wanna, you can catch the size of the QLabel that the pixmap is laying on.

Related

qml Camera save same image with different resolutions

I'm using QML's Camera component and Camera.imageCapture to save images.
I want to save multiple resolutions of the same image when user click "Capture" button.
The code I'm trying to run is simply like this:
// 160x120
camera.imageCapture.resolution = Qt.size(160,120)
camera.imageCapture.captureToLocation("/location/")
// 320x340
camera.imageCapture.resolution = Qt.size(320,240)
camera.imageCapture.captureToLocation("/anotherLocation/")
camera.imageCapture.resolution = Qt.size(-1,-1) // set to default again
Thanks.
If you'd save your camera input to a QImage you can save and resize and save again using QImage's image.save() and image.scaled() functions.
I've used these functions before for resizing images and it works perfect.
However I don't know how you can save the camera input to a QImage, but I'll look into that and report back.
I know it's not a full answer to your question, but it's a start. I hope that this was helpful.
Here is how I have solved:
Save the image with highest resolution available in Camera:
Component.onCompleted: {
camera.imageCapture.resolution = camera.imageCapture.supportedResolutions[camera.imageCapture.supportedResolutions.length-1]
}
Give the path of that file to the QImage's constructor.
Then scale & save:
Full Code:
imageresizer.cpp:
#include "imageresizer.h"
#include <QImage>
ImageResizer::ImageResizer(QObject *parent) : QObject(parent)
{}
void ImageResizer::resizeImage(int width, int height, QString file, QString savefile)
{
QImage img(file);
img = img.scaled(width, height);
img.save(savefile);
}
imageresizer.h:
#ifndef IMAGERESIZER_H
#define IMAGERESIZER_H
#include <QObject>
class ImageResizer : public QObject
{
Q_OBJECT
public:
explicit ImageResizer(QObject *parent = nullptr);
signals:
public slots:
void resizeImage(int width, int height, QString file, QString savefile);
};
#endif // IMAGERESIZER_H
Don't forget to make it available from QML:
int main(int argc, char *argv[])
{
qmlRegisterType<ImageResizer>("project.imageresizer", 1, 0, "ImageResizer"); // Here
QApplication app(argc, argv);
QQmlApplicationEngine engine;
engine.load(QUrl(QStringLiteral("qrc:/main.qml")));
if (engine.rootObjects().isEmpty())
return -1;
return app.exec();
}
main.qml:
import project.imageresizer 1.0
Window {
id: mainWindow
visible: true
width: 1024
height: 600
title: ""
ImageResizer {
id: imageResizer
}
// Use it like:
// imageResizer.resizeImage(100,100,imgPath,scaleImgPath)
}

Qt 5.8 QTextEdit Text Cursor Color Won't Change

I am trying to make the text cursor on a QTextEdit red (rgb(255,0,0)). Despite my best efforts, it continues to blink white.
From what I've found, the Style Sheet "color" property is supposed to change the color of the cursor. Not sure what's wrong.
My Code:
textEntry = new QTextEdit();
textEntry->setFont(QFont("Electrolize", 9, 1));
textEntry->setMinimumHeight(25);
textEntry->setMaximumHeight(25);
textEntry->setLineWrapMode(QTextEdit::NoWrap);
textEntry->setHorizontalScrollBarPolicy(Qt::ScrollBarAlwaysOff);
textEntry->setStyleSheet("color: rgb(255, 0, 0);"
"border: 1px solid rgb(255, 0, 0);");
Edit:
I encourage a full read of Scheff's answer. It's awesome. I noticed that the cursor created with his solution didn't blink, though, so I wanted to share a blinking version derived from Scheff's code with my (inexperienced) addition.
TextEdit.h
#ifndef TEXTEDIT_H
#define TEXTEDIT_H
#include <QTextEdit>
#include <QTimer>
class TextEdit : public TextEdit
{
Q_OBJECT
public:
explicit TextEdit(QWidget *parent = nullptr);
private:
QTimer *timer;
QPainter *pPainter;
bool bCursorVisible;
protected:
virtual void paintEvent(QPaintEvent *pEvent) override;
signals:
sendUpdate();
public slots:
void timerSlot();
};
#endif // TEXTEDIT_H
TextEdit.cpp
#include "textedit.h"
#include <QPainter>
#include <QColor>
#include <QTimer>
TextEdit::TextEdit(QWidget *parent) : QTextEdit(parent) {
bCursorVisible = true;
timer = new QTimer(this);
timer->start(500);
connect(this, SIGNAL(sendUpdate()), this, SLOT(update()));
connect(timer, SIGNAL(timeout()), this, SLOT(timerSlot()));
}
void TextEdit::paintEvent(QPaintEvent *event)
{
// use paintEvent() of base class to do the main work
QTextEdit::paintEvent(event);
// draw cursor (if widget has focus)
if (hasFocus()) {
if(bCursorVisible) {
const QRect qRect = cursorRect(textCursor());
QPainter qPainter(viewport());
qPainter.fillRect(qRect, QColor(255, 0, 0, 255));
} else {
const QRect qRect = cursorRect(textCursor());
QPainter qPainter(viewport());
qPainter.fillRect(qRect, QColor(0, 0, 0, 255));
}
}
}
void TextEdit::timerSlot() {
if(bCursorVisible) {
bCursorVisible = false;
} else {
bCursorVisible = true;
}
emit sendUpdate();
}
There was some conversation with OP beforehand, as I had serious doubts whether the color property of the QTextEdit is responsible for the color of text cursor as well.
All I found in the Qt Style Sheets Reference:
The color used to render text.
This property is supported by all widgets that respect the QWidget::palette.
If this property is not set, the default is whatever is set for in the widget's palette for the QWidget::foregroundRole (typically black).
Out of curiosity, I fiddled a little bit with colors of QTextEdit.
I could reproduce what OP described:
Changing the text color of QTextEdit (e.g. with QTextEdit::setTextColor()) has an effect on inserted text typed afterwards but it didn't change the text cursor color (at least, on the platforms where I tested).
While fiddling I realized another fact that encouraged me to write this answer:
IMHO, the text cursor ignores any color setting. Instead, it inverts the pixels under the drawn text cursor bar.
Have a look at QPainter::RasterOp_NotSource to see what I mean.
My sample application testQTextEditCursorColor.cc:
#include <QtWidgets>
class ColorButton: public QPushButton {
private:
QColor _qColor;
public:
explicit ColorButton(
const QString &text, const QColor &qColor = Qt::black,
QWidget *pQParent = nullptr):
QPushButton(text, pQParent)
{
setColor(qColor);
}
virtual ~ColorButton() = default;
ColorButton(const ColorButton&) = delete;
ColorButton& operator=(const ColorButton&) = delete;
const QColor& color() const { return _qColor; }
void setColor(const QColor &qColor)
{
_qColor = qColor;
QFontMetrics qFontMetrics(font());
const int h = qFontMetrics.height();
QPixmap qPixmap(h, h);
qPixmap.fill(_qColor);
setIcon(qPixmap);
}
QColor chooseColor()
{
setColor(QColorDialog::getColor(_qColor, this, text()));
return _qColor;
}
};
int main(int argc, char **argv)
{
qDebug() << "Qt Version:" << QT_VERSION_STR;
QApplication app(argc, argv);
qDebug() << app.style();
// setup GUI
QMainWindow qWin;
qWin.resize(250, 100);
qWin.setWindowTitle("Test Set Cursor Color");
QTextEdit qTextEdit;
qWin.setCentralWidget(&qTextEdit);
QToolBar qToolBar;
ColorButton qBtnColor("Text Color", qTextEdit.palette().color(QPalette::Text));
qToolBar.addWidget(&qBtnColor);
ColorButton qBtnColorBg("Background", qTextEdit.palette().color(QPalette::Base));
qToolBar.addWidget(&qBtnColorBg);
qWin.addToolBar(&qToolBar);
qWin.show();
// install signal handlers
QObject::connect(&qBtnColor, &QPushButton::clicked,
[&]() { qTextEdit.setTextColor(qBtnColor.chooseColor()); });
QObject::connect(&qBtnColorBg, &QPushButton::clicked,
[&]() {
QPalette qPal = qTextEdit.palette();
qPal.setColor(QPalette::Base, qBtnColorBg.chooseColor());
qTextEdit.setPalette(qPal);
});
// runtime loop
return app.exec();
}
and the corresponding Qt project file testQTextEditCursorColor.pro:
SOURCES = testQTextEditCursorColor.cc
QT += widgets
Compiled and tested in cygwin64 on Windows 10:
$ qmake-qt5 testQTextEditCursorColor.pro
$ make && ./testQTextEditCursorColor
g++ -c -fno-keep-inline-dllexport -D_GNU_SOURCE -pipe -O2 -Wall -W -D_REENTRANT -DQT_NO_DEBUG -DQT_WIDGETS_LIB -DQT_GUI_LIB -DQT_CORE_LIB -I. -isystem /usr/include/qt5 -isystem /usr/include/qt5/QtWidgets -isystem /usr/include/qt5/QtGui -isystem /usr/include/qt5/QtCore -I. -I/usr/lib/qt5/mkspecs/cygwin-g++ -o testQTextEditCursorColor.o testQTextEditCursorColor.cc
g++ -o testQTextEditCursorColor.exe testQTextEditCursorColor.o -lQt5Widgets -lQt5Gui -lQt5Core -lGL -lpthread
Qt Version: 5.9.4
QFusionStyle(0x6000e10c0, name = "fusion")
So, black makes a white cursor, white makes a black cursor (independent of any color setting). Assuming my above statement is correct, cyan background (#00ffff) should make red cursor (#ff0000):
For a comparison, I wrote a CMake script CMakeLists.txt:
project(QTextEditCursorColor)
cmake_minimum_required(VERSION 3.10.0)
set_property(GLOBAL PROPERTY USE_FOLDERS ON)
set(CMAKE_CXX_STANDARD 17)
set(CMAKE_CXX_STANDARD_REQUIRED ON)
set(CMAKE_CXX_EXTENSIONS OFF)
find_package(Qt5Widgets CONFIG REQUIRED)
include_directories("${CMAKE_SOURCE_DIR}")
add_executable(testQTextEditCursorColor testQTextEditCursorColor.cc)
target_link_libraries(testQTextEditCursorColor Qt5::Widgets)
and compiled and tested in VS2017 again:
Qt Version: 5.11.2
QWindowsVistaStyle(0x1c1ed936690, name = "windowsvista")
(Please note, the different style engine.)
The rendering in the Windows GDI makes it obvious that glyph pixels are inverted as well (but I noticed the same in the X11 test above):
The above in mind, it becomes obvious that it's a bad idea to use middle gray as background color. The bitwise NOT of e.g. #808080 is #7f7f7f and there is little contrast between these two colors. (I don't provide a snapshot because I was not able to recognize the right time to hit the Print key for a snapshot with text cursor drawn.)
OP referred to another Q&A: SO: Qt 5.3 QPlainTextEdit Change the QTextCursor color. Though, this answer was accepted and upvoted, it didn't help to change the cursor color on my side in any other way as described above. These are the modifications, I tried on my sample:
replacing QTextEdit by QPlainTextEdit
changing text cursor width with qTextEdit.setCursorWidth()
used style sheets instead of modifying the colors in palette
including using the exposed code in linked answer "literally".
After some conversation with thuga (the author of the accepted answer to SO: Qt 5.3 QPlainTextEdit Change the QTextCursor color, it appeared that there is a bug report for Qt 5.8 concerning this:
Qt 5.8 no longer allows QPlainTextEdit's cursor color to be set
which is marked as Unresolved at the time of writing. (Currently, Qt5.12 is the most recent version.)
After having long explained why it cannot work out-of-the-box, finally a sample how OPs intention can be achieved with a custom-painted cursor:
#include <QtWidgets>
class TextEdit: public QTextEdit {
protected:
virtual void paintEvent(QPaintEvent *pEvent) override;
};
void TextEdit::paintEvent(QPaintEvent *pQEvent)
{
// use paintEvent() of base class to do the main work
QTextEdit::paintEvent(pQEvent);
// draw cursor (if widget has focus)
if (hasFocus()) {
const QRect qRect = cursorRect(textCursor());
QPainter qPainter(viewport());
qPainter.fillRect(qRect, textColor());
}
}
class ColorButton: public QPushButton {
private:
QColor _qColor;
public:
explicit ColorButton(
const QString &text, const QColor &qColor = Qt::black,
QWidget *pQParent = nullptr):
QPushButton(text, pQParent)
{
setColor(qColor);
}
virtual ~ColorButton() = default;
ColorButton(const ColorButton&) = delete;
ColorButton& operator=(const ColorButton&) = delete;
const QColor& color() const { return _qColor; }
void setColor(const QColor &qColor)
{
_qColor = qColor;
QFontMetrics qFontMetrics(font());
const int h = qFontMetrics.height();
QPixmap qPixmap(h, h);
qPixmap.fill(_qColor);
setIcon(qPixmap);
}
QColor chooseColor()
{
setColor(QColorDialog::getColor(_qColor, this, text()));
return _qColor;
}
};
int main(int argc, char **argv)
{
qDebug() << "Qt Version:" << QT_VERSION_STR;
QApplication app(argc, argv);
qDebug() << app.style();
// setup GUI
QMainWindow qWin;
qWin.resize(250, 100);
qWin.setWindowTitle("Test Set Cursor Color");
TextEdit qTextEdit;
qWin.setCentralWidget(&qTextEdit);
qTextEdit.setCursorWidth(QFontMetrics(qTextEdit.font()).averageCharWidth());
QToolBar qToolBar;
ColorButton qBtnColor("Text Color",
qTextEdit.palette().color(QPalette::Text));
qToolBar.addWidget(&qBtnColor);
ColorButton qBtnColorBg("Background",
qTextEdit.palette().color(QPalette::Base));
qToolBar.addWidget(&qBtnColorBg);
qWin.addToolBar(&qToolBar);
qWin.show();
// install signal handlers
QObject::connect(&qBtnColor, &QPushButton::clicked,
[&]() { qTextEdit.setTextColor(qBtnColor.chooseColor()); });
QObject::connect(&qBtnColorBg, &QPushButton::clicked,
[&]() {
QPalette qPal = qTextEdit.palette();
qPal.setColor(QPalette::Base, qBtnColorBg.chooseColor());
qTextEdit.setPalette(qPal);
});
// runtime loop
return app.exec();
}
The QTextEdit is replaced by the derived TextEdit with an overridden paintEvent().
The QTextEdit::paintEvent() is called in TextEdit::paintEvent() to do the main work. Afterwards the cursor is (re-)painted with a rectangle in the textColor. (This simply over-paints the already rendered built-in text cursor.)
Note:
A smalls trap is the usage of QPainter in TextEdit::paintEvent(). Because QTextEdit is derived from QAbstractScrollArea, QPainter qPainter(this); would be wrong. Instead, QPainter qPainter(viewport()); has to be used. This is mentioned in the Qt doc. for QAbstractScrollArea::paintEvent():
Note: If you open a painter, make sure to open it on the viewport().
Upon request, a Python3 / PyQt5 port of the sample program in my other answer:
#!/usr/bin/python3
import sys
from PyQt5.QtCore import QT_VERSION_STR, QRect
from PyQt5.QtWidgets import QApplication, QMainWindow, QToolBar
from PyQt5.QtGui import QPainter, QIcon, QPixmap, QFontMetrics, QPalette
from PyQt5.QtWidgets import QTextEdit
from PyQt5.QtWidgets import QPushButton, QColorDialog
class TextEdit(QTextEdit):
def __init__(self, parent=None):
QTextEdit.__init__(self, parent)
def paintEvent(self, event):
# use paintEvent() of base class to do the main work
QTextEdit.paintEvent(self, event)
# draw cursor (if widget has focus)
if self.hasFocus():
rect = self.cursorRect(self.textCursor())
painter = QPainter(self.viewport())
painter.fillRect(rect, self.textColor())
class ColorButton(QPushButton):
def __init__(self, text, custom_color, parent=None):
QPushButton.__init__(self, text, parent)
self.setColor(custom_color)
def color(self):
return self.custom_color
def setColor(self, custom_color):
self.custom_color = custom_color
font_metrics = QFontMetrics(self.font())
h = font_metrics.height()
pixmap = QPixmap(h, h)
pixmap.fill(self.custom_color)
self.setIcon(QIcon(pixmap))
def chooseColor(self):
self.setColor(QColorDialog().getColor(self.custom_color))
return self.custom_color
if __name__ == '__main__':
print("Qt Version: {}".format(QT_VERSION_STR))
app = QApplication(sys.argv)
print(app.style())
# build GUI
win = QMainWindow()
win.resize(250, 100)
win.setWindowTitle("Test Set Cursor Color")
text_edit = TextEdit()
text_edit.setCursorWidth(QFontMetrics(text_edit.font()).averageCharWidth())
win.setCentralWidget(text_edit)
tool_bar = QToolBar()
btn_color = ColorButton(
"Text Color", text_edit.palette().color(QPalette.Text))
tool_bar.addWidget(btn_color)
btn_color_bg = ColorButton(
"Background", text_edit.palette().color(QPalette.Base))
tool_bar.addWidget(btn_color_bg)
win.addToolBar(tool_bar)
win.show()
# install signal handlers
btn_color.clicked.connect(
lambda state: text_edit.setTextColor(btn_color.chooseColor()))
def on_click(state):
palette = text_edit.palette()
palette.setColor(QPalette.Base, btn_color_bg.chooseColor())
text_edit.setPalette(palette)
btn_color_bg.clicked.connect(on_click)
# runtime loop
sys.exit(app.exec_())
Output:
Qt Version: 5.9.3
<PyQt5.QtWidgets.QCommonStyle object at 0x6ffffd8dc18>

Paint/Draw on top of docked widgets in QDodckWidget

I have a class in Qt that inherits QDockWidget. And that class contains another widget.
Is there any possibility to define a function in my QDockWidget inherited class that draws stuff on top of the contained widget? Like the painting to be independent of the contained widget but to be linked to the inherited class.
Thank you
Sure it's possible. It is fairly simple to do, in fact. You need to place a child widget that sits on top of everything else in your QDockWidget. To do it so, it must be the last child widget you add to your dockwidget. That widget must not to draw its background, and it can then draw over any children of the dockwidget. The widget's size must track the size of the parent widget.
Below is a self-contained example.
// https://github.com/KubaO/stackoverflown/tree/master/questions/overlay-line-11034838
#include <QtGui>
#if QT_VERSION > QT_VERSION_CHECK(5,0,0)
#include <QtWidgets>
#endif
class Line : public QWidget {
protected:
void paintEvent(QPaintEvent *) override {
QPainter p(this);
p.setRenderHint(QPainter::Antialiasing);
p.drawLine(rect().topLeft(), rect().bottomRight());
}
public:
explicit Line(QWidget *parent = nullptr) : QWidget(parent) {
setAttribute(Qt::WA_TransparentForMouseEvents);
}
};
class Window : public QWidget {
QHBoxLayout layout{this};
QPushButton left{"Left"};
QLabel right{"Right"};
Line line{this};
protected:
void resizeEvent(QResizeEvent *) override {
line.resize(size());
}
public:
explicit Window(QWidget *parent = nullptr) : QWidget(parent) {
layout.addWidget(&left);
right.setFrameStyle(QFrame::Box | QFrame::Raised);
layout.addWidget(&right);
line.raise();
}
};
int main(int argc, char *argv[]) {
QApplication app(argc, argv);
Window w;
w.show();
return app.exec();
}
AFAIK: No.
Widgets are drawn in depth order, so whatever your QDockWidget derived class paints, will be drawn over by the contained widgets when they are updated (immediately afterwards no doubt, because paint updates are propagated to child widgets).
Python version for the accepted answer:
# Created by BaiJiFeiLong#gmail.com at 2022/1/15 10:22
from PySide2 import QtWidgets, QtGui, QtCore
app = QtWidgets.QApplication()
widget = QtWidgets.QWidget()
line = QtWidgets.QFrame(widget)
line.paintEvent = lambda _: QtGui.QPainter(line).drawLine(line.rect().topLeft(), line.rect().bottomRight())
line.setAttribute(QtCore.Qt.WidgetAttribute.WA_TransparentForMouseEvents)
widget.setLayout(QtWidgets.QGridLayout(widget))
widget.layout().addWidget(QtWidgets.QPushButton("CLICK ME", widget))
widget.resizeEvent = lambda event: line.resize(event.size())
line.raise_()
widget.show()
app.exec_()
Note that this will not work for QSplitter, in this condition, you should use QMainWindow as parent widget.

Qt: How to draw a dummy line edit control

I have a QPainter, and a rectangle.
i'd like to draw a QLineEdit control, empty. Just to draw it, not to have a live control. How do I do that? I have tried QStyle::drawPrimitive to no avail. nothing gets drawn.
QStyleOption option1;
option1.init(contactsView); // contactView is the parent QListView
option1.rect = option.rect; // option.rect is the rectangle to be drawn on.
contactsView->style()->drawPrimitive(QStyle::PE_FrameLineEdit, &option1, painter, contactsView);
Naturally, i'd like the drawn dummy to look native in Windows and OSX.
Your code is pretty close, but you would have to initialize the style from a fake QLineEdit. The following is based on QLineEdit::paintEvent and QLineEdit::initStyleOption.
#include <QtGui>
class FakeLineEditWidget : public QWidget {
public:
explicit FakeLineEditWidget(QWidget *parent = NULL) : QWidget(parent) {}
protected:
void paintEvent(QPaintEvent *) {
QPainter painter(this);
QLineEdit dummy;
QStyleOptionFrameV2 panel;
panel.initFrom(&dummy);
panel.rect = QRect(10, 10, 100, 30); // QFontMetric could provide height.
panel.lineWidth = style()->pixelMetric(QStyle::PM_DefaultFrameWidth,
&panel,
&dummy);
panel.midLineWidth = 0;
panel.state |= QStyle::State_Sunken;
panel.features = QStyleOptionFrameV2::None;
style()->drawPrimitive(QStyle::PE_PanelLineEdit, &panel, &painter, this);
}
};
int main(int argc, char **argv) {
QApplication app(argc, argv);
FakeLineEditWidget w;
w.setFixedSize(300, 100);
w.show();
return app.exec();
}

Single file Qt4 demo

Sometimes you need to create a very simple single file application in Qt4. However it's problematic since you are always doing the CPP/H separation, and then the main() is in another file...
Any ideas how to do this in a single file? As quick as dirty as possible.
This is an example that shows how to do this in a single file. Just throw this in a new directory, save it as "main.cpp" and then run qmake -project; qmake; make to compile.
#include <QtGui/QApplication>
#include <QtGui/QMainWindow>
#include <QtGui/QPushButton>
class MainWindow : public QMainWindow {
Q_OBJECT
public:
MainWindow(QWidget *parent = 0){
button = new QPushButton("Hello, world!", this);
}
private:
QPushButton *button;
};
int main(int argc, char *argv[])
{
QApplication a(argc, argv);
MainWindow w;
w.show();
return a.exec();
}
#include "main.moc"
Two tricks in this demo:
First is how to call "qmake -project" to create a *.pro file with the files in the current directory automagically. The target name by default is the name of the directory, so choose it wisely.
Second is to #include *.moc in the CPP file, to ask moc to preprocess the CPP files for QObject definitions.
If you need to build a quick prototype, using Python and PyQt4 is even more compact:
import sys
from PyQt4.QtGui import *
class MainWindow(QMainWindow):
def __init__(self, parent=None):
QMainWindow.__init__(self, parent)
self.button = QPushButton("Hello, world!", self)
if __name__ == '__main__':
app = QApplication(sys.argv)
w = MainWindow()
w.show()
sys.exit(app.exec_())
No need to call qmake or to bother with .moc files.

Resources