我正在尝试在QWidget上绘制一条线(以及其他一些原语)。 QWidget实际上是“在另一个小部件之上”,其中有一张图片。我想在图片上画线条和圆圈。
我知道如何绘制一条线。我可以用这段代码来做到这一点:
bool MySpecialWidget::eventFilter( QObject* watched, QEvent* event )
{
if (watched == this && event->type() == QEvent::Paint)
{
QPainter painter(this);
painter.translate(50, 50);
painter.setPen(QPen(Qt::blue, 12));
painter.setBrush(Qt::BrushStyle::SolidPattern);
painter.drawLine(0, 0, 200, 200);
}
return false;
}
但我真正想做的是定位一个小部件来保存图片,然后将小部件放在它上面以保持线条。像这样:
MySpecialWidget::MySpecialWidget(QWidget *parent) : QWidget(parent)
{
QRect position = QRect(30, 50, 600, 600);
pictureBox = new QLabel(parent);
pictureBox->setGeometry(position);
pictureBox->setPixmap(QPixmap(QString::fromUtf8(":/main/graphics/MyPicture.png")));
pictureBox->setScaledContents(true);
drawnElements = new QWidget(parent);
drawnElements->setGeometry(position);
drawnElements->raise();
this->installEventFilter(this);
}
然后绘制线条和图元,我想这样做:
bool MySpecialWidget::eventFilter( QObject* watched, QEvent* event )
{
if (watched == this && event->type() == QEvent::Paint)
{
QPainter painter(drawnElements);
painter.translate(50, 50);
painter.setPen(QPen(Qt::blue, 12));
painter.setBrush(Qt::BrushStyle::SolidPattern);
painter.drawLine(0, 0, 200, 200);
}
return false;
}
但这不起作用。什么都没画。空白。
问题是读取QPainter painter(drawnElements);
如果我说QPainter painter(this);
,它会绘制一些内容,但它不在子窗口小部件上,而是在父窗口小部件上。
答案 0 :(得分:1)
关于这个主题的文件很清楚:
每个小部件都在其中执行所有绘制操作 paintEvent()函数。只要小部件需要,就会调用此方法 重新绘制,或者由于某些外部更改或在请求时重新绘制 通过申请。
您应该只从其绘制事件中绘制一个小部件,并且您应该只绘制该特定小部件。
答案 1 :(得分:0)
问题是读取
的行QPainter painter(drawnElements);
当然。您需要改为观看目标小部件并捕获其绘制事件。要控制绘图顺序,您还应该将事件明确地传递给目标。
bool MySpecialWidget::eventFilter( QObject* watched, QEvent* event )
{
// *** vvvvvvvvvvvvv *** (A)
if (watched == drawnElements && event->type() == QEvent::Paint)
{
// Let the target draw itself first.
watched->event(event);
// Then overlay our content on it.
// *** vvvvvvvvvvvvv *** (B) - must match (A)!
QPainter painter(drawnElements);
painter.translate(50, 50);
painter.setPen(QPen(Qt::blue, 12));
painter.setBrush(Qt::BrushStyle::SolidPattern);
painter.drawLine(0, 0, 200, 200);
return true; // The event is already handled.
}
return false;
}
MySpecialWidget::MySpecialWidget(QWidget *parent) : QWidget(parent)
{
//...
drawnElements->installEventFilter(this);
}
您也可以考虑使用overlay widget。