You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何用PyQt5实现背景图绘图并仅导出画笔轨迹图像?

解决PyQt5中仅保存画笔轨迹的问题

你的核心问题是当前代码将画笔轨迹直接绘制在背景图上,导致无法单独导出轨迹。解决思路是将背景图与画笔轨迹分离存储:用一个独立的透明画布存储轨迹,界面显示时叠加背景和轨迹,保存时只导出轨迹画布。

以下是修改后的完整代码:

import sys
from PyQt5.QtCore import *
from PyQt5.QtGui import *
from PyQt5.QtWidgets import *


class Drawer(QWidget):
    def __init__(self, img_path, parent=None):
        QWidget.__init__(self, parent)
        self.setAttribute(Qt.WA_StaticContents)
        self.myPenWidth = 10
        self.myPenColor = Qt.white
        # 加载背景图
        self.bg_image = QPixmap(img_path)
        # 创建透明轨迹画布,尺寸与背景图一致
        self.trail_image = QPixmap(self.bg_image.size())
        self.trail_image.fill(Qt.transparent)
        self.drawing = False
        self.lastPoint = QPoint()

    def clearImage(self):
        # 重置轨迹画布为透明
        self.trail_image.fill(Qt.transparent)
        self.update()

    def saveImage(self, fileName, fileFormat):
        # 仅保存轨迹画布
        self.trail_image.save(fileName, fileFormat)

    def paintEvent(self, event):
        painter = QPainter(self)
        # 先画背景图
        painter.drawPixmap(self.rect(), self.bg_image)
        # 再画轨迹
        painter.drawPixmap(self.rect(), self.trail_image)

    def mousePressEvent(self, event):
        if event.button() == Qt.LeftButton:
            self.drawing = True
            self.lastPoint = event.pos()

    def mouseMoveEvent(self, event):
        if event.buttons() & Qt.LeftButton and self.drawing:
            # 在轨迹画布上绘制
            painter = QPainter(self.trail_image)
            pen = QPen(self.myPenColor, self.myPenWidth, Qt.SolidLine, Qt.RoundCap, Qt.RoundJoin)
            painter.setPen(pen)
            painter.drawLine(self.lastPoint, event.pos())
            self.lastPoint = event.pos()
            self.update()

    def mouseReleaseEvent(self, event):
        if event.button() == Qt.LeftButton:
            self.drawing = False

    def sizeHint(self):
        return self.bg_image.size()


if __name__ == '__main__':
    img_path = 'heatmap.png'

    app = QApplication(sys.argv)
    w = QWidget()
    btnSave = QPushButton("Save Trail")
    btnClear = QPushButton("Clear Trail")
    drawer = Drawer(img_path)

    w.setLayout(QVBoxLayout())
    w.layout().addWidget(btnSave)
    w.layout().addWidget(btnClear)
    w.layout().addWidget(drawer)

    btnSave.clicked.connect(lambda: drawer.saveImage("trail.png", "png"))
    btnClear.clicked.connect(drawer.clearImage)
    w.show()
    sys.exit(app.exec_())

关键修改说明:

  • 分离画布:新增self.bg_image存储背景图,self.trail_image作为透明画布专门存储画笔轨迹,两者尺寸保持一致
  • 重置逻辑:clearImage仅清空轨迹画布,不影响背景图
  • 绘制目标调整:鼠标移动时将轨迹绘制到self.trail_image,而非背景图,避免污染原始背景
  • 显示叠加:paintEvent先绘制背景,再叠加轨迹,保证界面显示效果不变
  • 保存目标修改:saveImage方法保存轨迹画布,导出的图像仅包含画笔轨迹(透明背景)

内容的提问来源于stack exchange,提问作者abhishekkuber

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.09 02:36:02