Warning: file_get_contents(/data/phpspider/zhask/data//catemap/7/image/5.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C++ 如何在QPixmap图像中绘制点?_C++_Image_Qt_User Interface_Qtgui - Fatal编程技术网

C++ 如何在QPixmap图像中绘制点?

C++ 如何在QPixmap图像中绘制点?,c++,image,qt,user-interface,qtgui,C++,Image,Qt,User Interface,Qtgui,我有一个项目,我想画一个点到一个QPixmap内的图像。在QLabel上单击鼠标即可绘制点。我创建了一个与鼠标单击相对应的eventFilter()。当我用鼠标单击时,会调用这些eventFilter并在图像中绘制一个点,但我的代码不起作用。我尝试了许多其他选项,比如子类化QLabel,但也没有成功 有时我的编译器会显示以下错误消息: QPainter::begin: Paint device returned engine == 0, type: 2 QPainter::setPen: Pai

我有一个项目,我想画一个点到一个QPixmap内的图像。在QLabel上单击鼠标即可绘制点。我创建了一个与鼠标单击相对应的
eventFilter()
。当我用鼠标单击时,会调用这些eventFilter并在图像中绘制一个点,但我的代码不起作用。我尝试了许多其他选项,比如子类化QLabel,但也没有成功

有时我的编译器会显示以下错误消息:

QPainter::begin: Paint device returned engine == 0, type: 2
QPainter::setPen: Painter not active
QPainter::drawPoints: Painter not active
QPainter::end: Painter not active, aborted
但我不明白,因为Qt文档说允许在paintEvent之外使用QPainter,而只使用QPixmap

下面是我的代码和启动QPaint的方法

bool mainwindow::eventFilter(QObject* watched, QEvent* event) {
if ( watched != ui->labelScreen )
    return false;
if ( event->type() != QEvent::MouseButtonPress )
    return false;
const QMouseEvent* const me = static_cast<const QMouseEvent*>( event );
//might want to check the buttons here
const QPoint p = me->pos(); //...or ->globalPos();

ui->label_Xget->setNum(this->xReal);
ui->label_Yget->setNum(this->yReal);

///////////////////////////////////

QPixmap pix;
pix.fromImage(QImage::fromData("C:/Users/Syn/Pictures/imagem137.jpg"));

QPainter *painter = new QPainter(&pix);

painter->setPen(Qt::red);
painter->drawPoint(p.x(), p.y());
ui->labelScreen->setPixmap(pix);
painter->end();

///////////////////////////////////


return false;
}
bool主窗口::事件过滤器(QObject*监视,QEvent*事件){
如果(观看!=ui->labelScreen)
返回false;
如果(事件->类型()!=QEvent::MouseButtonPress)
返回false;
const QMouseEvent*const me=静态_cast(事件);
//可能要检查这里的按钮
常量QPoint p=me->pos();/…或->globalPos();
ui->label\uxget->setNum(this->xReal);
ui->label_Yget->setNum(此->yReal);
///////////////////////////////////
QPixmap-pix;
fromImage(QImage::fromData(“C:/Users/Syn/Pictures/imagem137.jpg”);
QPainter*painter=新的QPainter(&pix);
画师->设置笔(Qt::红色);
油漆工->绘图点(p.x(),p.y());
ui->labelScreen->setPixmap(pix);
画师->结束();
///////////////////////////////////
返回false;
}

有人能帮我解决这个问题吗?谢谢。

错误消息不是来自您的编译器,它们发生在运行时,您无法确定上面引用的代码是否是它们的原因

有几个问题:

  • QPixmap::fromImage
    是一个返回pixmap的静态方法。您忽略了它的返回值。正确的使用方法是:

    // C++11
    auto pix = QPixmap::fromImage(QImage{"filename"});
    // C++98
    QPixmap pix(QPixmap::fromImage(QImage("filename")));
    
  • 您可以将文件名直接传递给
    QPixmap
    构造函数:

    // C++11
    QPixmap pix{"filename"};
    // C++98
    QPixmap pix("filename");
    
  • 你在泄露画家的实例。除非确实需要,否则应该避免任何动态内存分配。另外,按值存储
    ui
    ——这样更便宜

  • 在事件处理程序中执行任何阻塞I/O(如读取文件)都是一个非常糟糕的主意。将pixmap预加载并存储为
    main窗口
    类的成员

  • 因此(在C++11中):

    接口
    模板
    类主窗口:公共QMainWindow{
    QPixmap m_单击pixmap;
    Ui::主窗口Ui;
    布尔事件过滤器(QObject*,QEvent*)覆盖;
    公众:
    主窗口(QWidget*parent=nullptr);
    };
    
    实施
    void loadImage(常量QString&fileName,QObject*context,F&&functor){
    QtConcurrent::run([=]{
    QImage img{fileName};
    if(img.isNull())返回;
    QTimer::singleShot(0,上下文,函子,img);
    });
    }
    主窗口::主窗口(QWidget*父窗口):
    QMainWindow{parent}
    {
    loadImage(“C:/Users/Syn/Pictures/imagem137.jpg”,this,[this](const QImage&img){
    单击PixMap=QPixmap::fromImage(img);
    });
    ui.setupUi(这个);
    }
    bool主窗口::事件过滤器(QObject*监视,QEvent*事件){
    如果(监视!=ui.labelScreen)
    返回false;
    如果(事件->类型()!=QEvent::MouseButtonPress)
    返回false;
    自动常数me=静态施法(事件);
    自动常数p=me->pos();/…或->globalPos();
    ui.label_Xget->setNum(this->xReal);
    ui.label_Yget->setNum(this->yReal);
    自动pix{m_clickPixmap};
    QPainter painter(油漆工和pix);
    画师:设置笔(Qt::红色);
    绘制点(p.x(),p.y());
    painter.end();//可能不需要
    ui.labelScreen->setPixmap(pix);
    返回false;
    }
    
    错误消息不是来自您的编译器,它们发生在运行时,您无法确定上面引用的代码是否是它们的原因

    有几个问题:

  • QPixmap::fromImage
    是一个返回pixmap的静态方法。您忽略了它的返回值。正确的使用方法是:

    // C++11
    auto pix = QPixmap::fromImage(QImage{"filename"});
    // C++98
    QPixmap pix(QPixmap::fromImage(QImage("filename")));
    
  • 您可以将文件名直接传递给
    QPixmap
    构造函数:

    // C++11
    QPixmap pix{"filename"};
    // C++98
    QPixmap pix("filename");
    
  • 你在泄露画家的实例。除非确实需要,否则应该避免任何动态内存分配。另外,按值存储
    ui
    ——这样更便宜

  • 在事件处理程序中执行任何阻塞I/O(如读取文件)都是一个非常糟糕的主意。将pixmap预加载并存储为
    main窗口
    类的成员

  • 因此(在C++11中):

    接口
    模板
    类主窗口:公共QMainWindow{
    QPixmap m_单击pixmap;
    Ui::主窗口Ui;
    布尔事件过滤器(QObject*,QEvent*)覆盖;
    公众:
    主窗口(QWidget*parent=nullptr);
    };
    
    实施
    void loadImage(常量QString&fileName,QObject*context,F&&functor){
    QtConcurrent::run([=]{
    QImage img{fileName};
    if(img.isNull())返回;
    QTimer::singleShot(0,上下文,函子,img);
    });
    }
    主窗口::主窗口(QWidget*父窗口):
    QMainWindow{parent}
    {
    loadImage(“C:/Users/Syn/Pictures/imagem137.jpg”,this,[this](const QImage&img){
    单击PixMap=QPixmap::fromImage(img);
    });
    ui.setupUi(这个);
    }
    bool主窗口::事件过滤器(QObject*监视,QEvent*事件){
    如果(监视!=ui.labelScreen)
    返回false;
    如果(事件->类型()!=QEvent::MouseButtonPress)
    返回false;
    自动常数me=静态施法(事件);
    自动常数p=me->pos();/…或->globalPos();
    ui.label_Xget->setNum(this->xReal);
    ui.label_Yget->setNum(this->yReal);
    自动pix{m_clickPixmap};
    QPainter painter(油漆工和pix);
    画师:设置笔(Qt::红色);
    绘制点(p.x(),p.y());
    painter.end();//可能不需要
    ui.labelScreen->setPixmap(pix);
    返回false;
    }
    
    谢谢您的回答。我尝试了你的建议,但仍然显示相同的错误消息。在labelScreen中,设置了一个空的pixmap,但标签上没有显示任何内容:/您确定此代码会导致任何问题吗?禁用代码并查看是否仍然存在问题。这个代码应该可以正常工作。你呢