当前位置: 首页 > article >正文

QT,opencv制作界面化图片操作

思路分析:

  1. main.py主要负责用户界面和事件处理。

    • 它首先导入许多所需的模块,然后定义一个MyWidget类来处理用户界面和信号。
    • MyWidget类的构造函数在载入用户界面后,设置一些初值和预置的图像处理选项,然后与按钮、滑块和下拉框的信号(如点击、值改变、选择改变等)连接对应的槽函数。
    • 槽函数主要调用Photo_Operate模块中的函数来处理图像,并更新用户界面上的图像显示。
  2. Photo_Operate.py 主要负责图像处理。

    • 它包含一系列的函数,每个函数对应一种特定的图像处理操作,如灰度化、旋转、亮度调整、对比度调整、模糊、边缘检测等。
    • 这些函数读取路径下的图像文件,进行相应的处理,然后将结果保存到预定的路径下。

mian.py

import sys
from opencv import Photo_Operate
from PyQt6 import uic
from PyQt6.QtGui import QPixmap
from PyQt6.QtWidgets import QWidget, QApplication, QLabel, QPushButton, QFileDialog, \
    QSlider, QComboBox


class MyWidget(QWidget):
    def __init__(self):
        super().__init__()
        ui = uic.loadUi('1.ui', self)
        self.photo_obj_sav = 'C:/Users/29610/new.jpg'
        self.photo_obj_sav_gray = 'C:/Users/29610/new_gray.jpg'
        self.photo_path_save = 'C:/Users/29610/save.jpg'
        self.photo_path_open = ''
        self.list = ['模糊', '锐化', '边缘检测']
        self.label: QLabel = self.label
        self.btn1: QPushButton = self.btn1
        self.btn2: QPushButton = self.btn2
        self.btn3: QPushButton = self.btn3
        self.btn4: QPushButton = self.btn4
        self.btn5: QPushButton = self.btn5
        self.btn6: QPushButton = self.btn6
        self.slider1: QSlider = self.slider1
        self.slider2: QSlider = self.slider2
        self.comboBox: QComboBox = self.comboBox
        self.comboBox.addItems(self.list)
        self.btn1.clicked.connect(self.btn1_slot)
        self.btn2.clicked.connect(self.btn2_slot)
        self.btn3.clicked.connect(self.btn3_slot)
        self.btn4.clicked.connect(self.btn4_slot)
        self.btn5.clicked.connect(self.btn5_slot)
        self.btn6.clicked.connect(self.btn6_slot)
        self.slider1.valueChanged.connect(self.slider1_slot)
        self.slider2.valueChanged.connect(self.slider2_slot)
        self.comboBox.activated.connect(self.getComboBox_slot)

    #灰度化
    def btn1_slot(self):
        path = Photo_Operate.grayscale(
            self.photo_obj_sav_gray,
            self.photo_obj_sav_gray)
        self.label.setPixmap(QPixmap(path))
        self.photo_path_save = rf'{path}'
        self.label.setScaledContents(True)

    #打开
    def btn2_slot(self):
        path, filetype = QFileDialog.getOpenFileName(
            window,
            "打开图片",
            "./",
            "mage(*.png *.jpg *ico)"
        )
        self.photo_path_open = rf'{path}'
        Photo_Operate.open_img(self.photo_path_open, self.photo_obj_sav_gray, self.photo_obj_sav)
        self.label.setPixmap(QPixmap(self.photo_path_open))
        self.label.setScaledContents(True)
        self.photo_path_save = rf'{path}'

    #保存
    def btn3_slot(self):
        self.photo_path_save = ''
        if not self.label.pixmap():
            print("No image to save")
            return
        path, filetype = QFileDialog.getSaveFileName(
            window,
            "保存图片",
            "./",
            "mage(*.png *.jpg *ico)"
        )
        self.photo_path_save = rf'{path}'
        if path:
            self.label.pixmap().save(self.photo_path_save)
        print(self.photo_path_save)

    #回复
    def btn4_slot(self):
        self.label.setPixmap(QPixmap(self.photo_obj_sav))
        self.label.setScaledContents(True)
        self.photo_path_save = self.photo_obj_sav
        pass

    #旋转
    def btn5_slot(self):
        path = Photo_Operate.warp(
            self.photo_obj_sav_gray,
            self.photo_obj_sav_gray, )
        path2 = Photo_Operate.warp(
            self.photo_obj_sav,
            self.photo_obj_sav, )
        if Photo_Operate.is_gray(self.photo_path_save):
            self.label.setPixmap(QPixmap(path))
            self.photo_path_save = path
        else:
            self.label.setPixmap(QPixmap(path2))
            self.photo_path_save = path2
        self.label.setScaledContents(True)
        pass

    #翻折
    def btn6_slot(self):
        path = Photo_Operate.flip(
            self.photo_obj_sav_gray,
            self.photo_obj_sav_gray,
            -1)
        path2 = Photo_Operate.flip(
            self.photo_obj_sav,
            self.photo_obj_sav,
            -1)
        if Photo_Operate.is_gray(self.photo_path_save):
            self.label.setPixmap(QPixmap(path))
            self.photo_path_save = path
        else:
            self.label.setPixmap(QPixmap(path2))
            self.photo_path_save = path2
        self.label.setScaledContents(True)
        pass

    #亮度
    def slider1_slot(self):
        path = Photo_Operate.change_brightness(
            self.photo_path_open,
            self.photo_obj_sav_gray,
            self.slider1.value())
        path2 = Photo_Operate.change_brightness(
            self.photo_path_open,
            self.photo_obj_sav,
            self.slider1.value())
        if Photo_Operate.is_gray(self.photo_path_save):
            self.label.setPixmap(QPixmap(path))
            self.photo_path_save = path
        else:
            self.label.setPixmap(QPixmap(path2))
            self.photo_path_save = path2
        self.label.setScaledContents(True)
        pass

    #对比度
    def slider2_slot(self):
        path = Photo_Operate.change_contrast(
            self.photo_path_open,
            self.photo_obj_sav_gray,
            self.slider2.value())
        path2 = Photo_Operate.change_contrast(
            self.photo_path_open,
            self.photo_obj_sav,
            self.slider2.value())
        if Photo_Operate.is_gray(self.photo_path_save):
            self.label.setPixmap(QPixmap(path))
            self.photo_path_save = path
        else:
            self.label.setPixmap(QPixmap(path2))
            self.photo_path_save = path2
        self.label.setScaledContents(True)
        pass

    #模糊,锐化,边缘检测
    def getComboBox_slot(self):
        if self.comboBox.currentText() == '模糊':
            path = Photo_Operate.blur(
                self.photo_obj_sav_gray,
                self.photo_obj_sav_gray, )
            path2 = Photo_Operate.blur(
                self.photo_obj_sav,
                self.photo_obj_sav, )
            if Photo_Operate.is_gray(self.photo_path_save):
                self.label.setPixmap(QPixmap(path))
                self.photo_path_save = path
            else:
                self.label.setPixmap(QPixmap(path2))
                self.photo_path_save = path2
            self.label.setScaledContents(True)
        elif self.comboBox.currentText() == '锐化':
            path = Photo_Operate.sobel(
                self.photo_obj_sav_gray,
                self.photo_obj_sav_gray, )
            path2 = Photo_Operate.sobel(
                self.photo_obj_sav,
                self.photo_obj_sav, )
            if Photo_Operate.is_gray(self.photo_path_save):
                self.label.setPixmap(QPixmap(path))
                self.photo_path_save = path
            else:
                self.label.setPixmap(QPixmap(path2))
                self.photo_path_save = path2
            self.label.setScaledContents(True)
        elif self.comboBox.currentText() == '边缘检测':
            path = Photo_Operate.canny(
                self.photo_obj_sav_gray,
                self.photo_obj_sav_gray, )
            path2 = Photo_Operate.canny(
                self.photo_obj_sav,
                self.photo_obj_sav, )
            if Photo_Operate.is_gray(self.photo_path_save):
                self.label.setPixmap(QPixmap(path))
                self.photo_path_save = path
            else:
                self.label.setPixmap(QPixmap(path2))
                self.photo_path_save = path2
            self.label.setScaledContents(True)


if __name__ == '__main__':
    app = QApplication(sys.argv)
    window = MyWidget()
    window.show()
    sys.exit(app.exec())
Photo_Operate.py
import cv2
import numpy as np


def is_gray(path: str):
    img = cv2.imdecode(np.fromfile(path, dtype=np.uint8), cv2.IMREAD_COLOR)  # 从指定路径读取图像
    if len(img.shape) == 2:
        return True
    elif len(img.shape) == 3:
        if img.shape[2] == 3:
            b, g, r = cv2.split(img)
            if (b == g).all() and (b == r).all():
                return True
    return False


def open_img(path: str, path_save1: str, path_save2: str):
    img = cv2.imdecode(np.fromfile(path, dtype=np.uint8), cv2.IMREAD_COLOR)  # 从指定路径读取图像
    img_new = img.copy()
    img_new2 = img.copy()
    cv2.imencode('.jpg', img_new)[1].tofile(path_save1)  # 将图像保存为 .jpg 格式文件
    cv2.imencode('.jpg', img_new2)[1].tofile(path_save2)


def grayscale(path: str, path_save: str):  # 该函数将图像转换为灰度图
    img = cv2.imdecode(np.fromfile(path, dtype=np.uint8), cv2.IMREAD_COLOR)  # 从指定路径读取图像
    img_gray = cv2.cvtColor(img, cv2.COLOR_BGR2GRAY)
    cv2.imencode('.jpg', img_gray)[1].tofile(path_save)  # 将图像保存为 .jpg 格式文件
    return path_save


def flip(path: str, path_save: str, num: int):
    img = cv2.imdecode(np.fromfile(path, dtype=np.uint8), cv2.IMREAD_COLOR)  # 从指定路径读取图像
    img_new = cv2.flip(img, num)
    cv2.imencode('.jpg', img_new)[1].tofile(path_save)  # 将图像保存为 .jpg 格式文件
    return path_save


def warp(path: str, path_save: str):
    img = cv2.imdecode(np.fromfile(path, dtype=np.uint8), cv2.IMREAD_COLOR)  # 从指定路径读取图像
    M = cv2.getRotationMatrix2D((img.shape[1] / 2, img.shape[0] / 2), 90, -1)
    img_rotate = cv2.warpAffine(img, M, (img.shape[1], img.shape[0]))
    cv2.imencode('.jpg', img_rotate)[1].tofile(path_save)  # 将图像保存为 .jpg 格式文件
    return path_save


def change_brightness(path: str, path_save: str, b):
    img = cv2.imdecode(np.fromfile(path, dtype=np.uint8), cv2.IMREAD_COLOR)  # 从指定路径读取图像
    img_copy = img.copy()
    img_copy = img_copy + b
    img_copy = np.clip(img_copy, 0, 255)
    img_copy = np.uint8(img_copy)
    cv2.imencode('.jpg', img_copy)[1].tofile(path_save)  # 将图像保存为 .jpg 格式文件
    return path_save


def change_contrast(path: str, path_save: str, a):
    img = cv2.imdecode(np.fromfile(path, dtype=np.uint8), cv2.IMREAD_COLOR)  # 从指定路径读取图像
    img_copy = img.copy()
    img_copy = (a + 100) / 100 * img_copy
    img_copy = np.clip(img_copy, 0, 255)
    img_copy = np.uint8(img_copy)
    cv2.imencode('.jpg', img_copy)[1].tofile(path_save)  # 将图像保存为 .jpg 格式文件
    return path_save


def blur(path: str, path_save: str):
    img = cv2.imdecode(np.fromfile(path, dtype=np.uint8), cv2.IMREAD_COLOR)  # 从指定路径读取图像
    img_blur = cv2.blur(img, (5, 5))
    cv2.imencode('.jpg', img_blur)[1].tofile(path_save)  # 将图像保存为 .jpg 格式文件
    return path_save


def sobel(path: str, path_save: str):
    img = cv2.imdecode(np.fromfile(path, dtype=np.uint8), cv2.IMREAD_COLOR)  # 从指定路径读取图像
    img_sobel = cv2.Sobel(img, -1, dx=0, dy=1, ksize=5)
    cv2.imencode('.jpg', img_sobel)[1].tofile(path_save)  # 将图像保存为 .jpg 格式文件
    return path_save


def canny(path: str, path_save: str):
    img = cv2.imdecode(np.fromfile(path, dtype=np.uint8), cv2.IMREAD_COLOR)  # 从指定路径读取图像
    img_gray = cv2.cvtColor(img, cv2.COLOR_BGR2GRAY)
    img_canny = cv2.Canny(img_gray,
                          30,  # 低阈值
                          70  # 高阈值
                          )
    _, img_th = cv2.threshold(img_canny, 127, 255, cv2.THRESH_BINARY+cv2.THRESH_OTSU)
    can, _ = cv2.findContours(img_th, cv2.RETR_LIST, cv2.CHAIN_APPROX_SIMPLE)
    img_draw = img.copy()
    cv2.drawContours(img_draw, can, -1, (0, 255, 255), 3)
    cv2.imencode('.jpg', img_draw)[1].tofile(path_save)  # 将图像保存为 .jpg 格式文件
    return path_save

效果实现:

读取图片:

灰度化及灰度化恢复:

旋转翻折:

对比度,亮度:

模糊处理:

锐化处理:

边缘检测:


http://www.kler.cn/a/455976.html

相关文章:

  • 从0入门自主空中机器人-2-2【无人机硬件选型-PX4篇】
  • 数据库原理及应用(MySQL版-李月军)-习题参考答案
  • Numpy指南:解锁Python多维数组与矩阵运算(下)
  • 复习打卡大数据篇——Hadoop MapReduce
  • 双柱渐变图背景图
  • No.29 笔记 | CTF 学习干货
  • Vue.js 入门与进阶:打造高效的前端开发体验
  • 机床数据采集网关在某机械制造企业的应用
  • Unity游戏环境交互系统
  • 回声函数 printf重定向 sht20温湿度传感器
  • 代码随想录38 322. 零钱兑换,279.完全平方数,本周小结动态规划,139.单词拆分,动态规划:关于多重背包,你该了解这些!背包问题总结篇。
  • 不修改内核镜像的情况下,使用内核模块实现“及时”的调度时间片超时事件上报
  • Redis-十大数据类型
  • 通过 `@Configuration` 和 `WebMvcConfigurer` 配置 Spring MVC 中的静态资源映射
  • 开源软件兼容性可信量化分析
  • Scrapy 自定义 Item 类 与 直接使用字典的区别详解
  • 【ArcGIS】土地利用/土地覆盖遥感解译与基于CLUE模型未来变化情景预测
  • uni-app开发收货地址管理
  • 二百八十二、ClickHouse——删除Linux中的ClickHouse
  • 设计模式的分类及作用
  • 对象字面量内定义属性和方法,传值(什么使用const等关键字,什么时候用键值对)
  • 项目42:简易语法检查器 --- 《跟着小王学Python·新手》
  • 企信唤起跳转小程序及分享API功能
  • C# OpenCV机器视觉:产品计数
  • springboot493基于java的美食信息推荐系统的设计与实现(论文+源码)_kaic
  • vuex - 第一天