文章目录

  • 一.前言
  • 二.效果预览
    • 1.实时识别
    • 2.ROI
    • 3.数据导出
  • 三.相关技术与实现
    • 1.目标识别与检测
    • 2.可视化展示
    • 3.如何设置推流环境
    • 4.如何实现的车牌和颜色识别
    • 5.项目结构
  • 四.总结


本系统支持黄牌、蓝牌、绿牌、黑牌、白牌,支持双层车牌,欢迎了解!

请添加图片描述

PyQt5车牌识别可视化系统

一.前言

这是我使用PyQt5开发的车牌识别系统,主要采用了深度学习对车牌以及车牌颜色进行识别
系统采用分析RTMP视频流的方式对视频内画面进行分析,提取出车牌以及车牌颜色
模型采用通用数据集进行的训练,模型文件拓展名为.pth
识别车牌类型包括:黄牌、蓝牌、绿牌、黑牌、白牌,支持双层车牌、警牌、民航、学牌…
采用多种方案对数据进行可视化展示:折线图、饼图、条形图、热力图、表格
支持ROI区域设置:矩形、圆形、多边形,另外支持清除ROI
支持拉流控制:开始识别、停止识别、设置视频流
支持识别结果详细数据导出、支持CSV、Excel、TXT

二.效果预览

软件启动后进入主界面主界面包括三个区域分别是:
左侧信息区域:展示了CPU内存利用率折线图、车牌颜色分布饼图、我们的系统支持黄牌、蓝牌、绿牌、黑牌、白牌,最底部是置信度分布条形图,对于颜色、识别置信度使用条形图展示各个区间的数据
中间区域:上面是实时画面显示,画面是数据处理过的,已经标注车牌以及颜色,使用红色四角框标注车牌区域,使用红色白底文字展示车牌号以及颜色,底部是当前识别到目标的详细数据,具体包括:颜色、识别置信度、车牌号、车牌颜色、车牌图片、车牌类别、车牌所在区域矩形、以及区域高度,
右侧区域:顶部是识别能力热力图,此热力图展示了识别置信度与区域高度的热力图,用于评估当前的识别能力,中间是车牌首字符分布条形图,我们采用不同颜色的条形展示具体车牌的数量分布,底部为实时日志,实时日志展示了日志的输出时间以及识别到的车牌数量还有具体车牌、颜色数据。

1.实时识别

软件启动后会自动拉取目标视频画面,对画面中的内容进行实时逐帧分析,最后将分析后的结果展示到主屏中间区域,我们采用了多进程的方式提升了识别+处理数据效率,采用队列的方式处理不同进程中的数据。
请添加图片描述

2.ROI

本系统支持设置ROI(感兴趣区域),用户可以在画面上右击鼠标后展示菜单,菜单中选择ROI的类型,具体的类型支持:矩形、圆形、多边形,多边形灵活度高,另外可以对标注的ROI进行清除操作,ROI的操作大大增加了用户与本系统的交互。
请添加图片描述

3.数据导出

用户可以在界面(非画面区域)右击鼠标,选择导出数据的类型:CSV、Excel、TXT都是支持的,具体数据我下面截图展示。
用户选了对应的文件类型之后,系统会让用户选择导出文件位置、设置导出文件名,软件会自动选择桌面为默认位置,缩短了用户操作路径,用户可以选择导出或者取消,如果选择了导出,系统会在指定位置创建数据文件,并且询问用户“是否打开文件”,用户选择打开后,会调用系统打开方式打开文件,展示文件内容。

请添加图片描述

在这里插入图片描述

三.相关技术与实现

1.目标识别与检测

本系统使用YOLOv8对目标进行识别与检测

YOLOv8是Ultralytics公司推出的最新一代实时目标检测算法,基于YOLO(You Only Look Once)系列架构改进,具有更高的检测精度和更快的推理速度。它支持目标检测、实例分割和图像分类任务,采用灵活的Backbone和Neck设计,并优化了训练策略与损失函数,兼容多种部署环境(如ONNX、TensorRT等),适合工业级应用。YOLOv8提供多种预训练模型(从轻量级YOLOv8n到高性能YOLOv8x),平衡速度与精度,是计算机视觉领域的先进工具之一。

在这里插入图片描述
本次使用YOLOv8版本对车辆和行人进行识别,车辆的类型包括:小汽车、摩托车、自行车、卡车,行人就是马路上行走的人,系统采用队列对读取到的视频流帧进行处理,标注分析好之后使用信号的方式发射给PyQt5的前端,前端设置槽函数接收、处理、展示数据。

2.可视化展示

本系统使用pyecharts对上游数据进行可视化展示

Pyecharts 是基于 Python 的数据可视化库,依托强大的 ECharts(百度开源 JavaScript 图表库)构建,提供丰富的交互式图表类型(如折线图、柱状图、散点图、地图等)。它支持链式调用和简洁的 API 设计,可轻松生成动态、可缩放的可视化结果,并兼容 Jupyter Notebook、Web 页面及 Flask/Django 等框架。Pyecharts 支持多种数据格式(如 Pandas、NumPy),允许自定义样式和主题,适用于数据分析、商业报表和实时大屏展示,是 Python 生态中高效、美观的可视化工具之一。

图片取自网络,仅用于echarts图效果展示,不包含在本系统中。
在这里插入图片描述

我们采用了组件化的开发思想,每个图标组件都是能够单独调试运行的,下面是个热力图组件,
在这里插入图片描述
大家通过导入指定的包和库,就能执行起来此代码:


class HeatmapBridge(QObject):updateSignal = pyqtSignal(str)def __init__(self, get_option_callback):super().__init__()self._get_option = get_option_callback@pyqtSlot(result=str)def getOption(self):return json.dumps(self._get_option())class HeatmapWidget(QWidget):def __init__(self, p=None, mode='height_conf'):super().__init__(p)self.mode = mode  # 'height_conf' or 'province'self.data = []self.ui_init()def ui_init(self):self.heatmap_data = self.prepare_heatmap_data()profile = QWebEngineProfile(f"profile_{id(self)}", self)page = NoRightClickWebEnginePage(profile)self.view = NoContextMenuWebEngineView()self.view.setPage(page)self.view.setAttribute(Qt.WA_TranslucentBackground, True)self.view.setStyleSheet("background: transparent;")self.view.page().setBackgroundColor(Qt.transparent)layout = QVBoxLayout()layout.setContentsMargins(0, 0, 0, 0)layout.addWidget(self.view)self.setLayout(layout)self.bridge = HeatmapBridge(self.get_echarts_option)self.channel = QWebChannel()self.channel.registerObject("bridge", self.bridge)self.view.page().setWebChannel(self.channel)self.init_html()def prepare_heatmap_data(self):if self.mode == 'height_conf':return self.prepare_by_height_conf()elif self.mode == 'province':return self.prepare_by_province()else:return []def prepare_by_height_conf(self):height_bins = [(0, 10), (10, 20), (20, 30), (30, 40), (40, 50), (50, 60)]conf_bins = [(0.0, 0.2), (0.2, 0.4), (0.4, 0.6), (0.6, 0.8), (0.8, 1.0)]height_labels = [f"{lo}{hi}" for lo, hi in height_bins]conf_labels = [f"{lo:.1f}{hi:.1f}" for lo, hi in conf_bins]count_matrix = [[0 for _ in height_bins] for _ in conf_bins]for item in self.data:height = item.get('roi_height')conf = item.get('detect_conf')h_idx = next((i for i, (lo, hi) in enumerate(height_bins) if lo <= height < hi), None)c_idx = next((i for i, (lo, hi) in enumerate(conf_bins) if lo <= conf < hi), None)if h_idx is not None and c_idx is not None:count_matrix[c_idx][h_idx] += 1heatmap_data = []for i, conf_label in enumerate(conf_labels):for j, height_label in enumerate(height_labels):heatmap_data.append([height_label, conf_label, count_matrix[i][j]])self.x_labels = height_labelsself.y_labels = conf_labelsself.z_values = [v[2] for v in heatmap_data]return heatmap_datadef prepare_by_province(self):province_count = {}for item in self.data:plate_no = item.get('plate_no', '')if plate_no:province = plate_no[0]province_count[province] = province_count.get(province, 0) + 1self.x_labels = list(province_count.keys())self.y_labels = ["数量"]self.z_values = list(province_count.values())heatmap_data = [[prov, "数量", cnt] for prov, cnt in province_count.items()]return heatmap_datadef get_echarts_option(self):option = {"tooltip": {"position": "top"},"grid": {"height": "60%","top": "18%","left": "16%","right": "10%"},"xAxis": {"type": "category","data": self.x_labels,"axisLabel": {"color": "#00FFE3"},"axisLine": {"lineStyle": {"color": "#00FFE3"}},},"yAxis": {"type": "category","data": self.y_labels,"axisLabel": {"color": "#00FFE3"},"axisLine": {"lineStyle": {"color": "#00FFE3"}},},"visualMap": {"min": 0,"max": max(self.z_values) if self.z_values else 1,"calculable": True,"orient": "horizontal","left": "center","bottom": "2%","inRange": {"color": ["#001f3f", "#0074D9", "#00FFFF"]}},"series": [{"type": "heatmap","data": self.heatmap_data,"label": {"show": True, "color": "#fff"},"emphasis": {"itemStyle": {"shadowBlur": 10,"shadowColor": "rgba(0,0,0,0.5)"}}}]}return optiondef init_html(self):html = """<html><head><meta charset="UTF-8"><script src="https://cdn.jsdelivr.net/npm/echarts@5"></script><script src="qrc:///qtwebchannel/qwebchannel.js"></script><style>html, body, #container {margin: 0; padding: 0;width: 100%; height: 100%;background: transparent; overflow: hidden;}</style></head><body><div id="container"></div><script>var chart;new QWebChannel(qt.webChannelTransport, function(channel) {window.bridge = channel.objects.bridge;chart = echarts.init(document.getElementById('container'), null, {backgroundColor: 'transparent'});bridge.getOption().then(function(optionStr) {let option = JSON.parse(optionStr);chart.setOption(option);});bridge.updateSignal.connect(function(optionStr) {let option = JSON.parse(optionStr);chart.setOption(option, true);});window.addEventListener('resize', function () {if (chart) chart.resize();});});</script></body></html>"""self.view.setHtml(html)def update_data(self, new_data):self.data = new_dataself.heatmap_data = self.prepare_heatmap_data()new_option_json = json.dumps(self.get_echarts_option())self.bridge.updateSignal.emit(new_option_json)

3.如何设置推流环境

环境问题老生常谈了,直接参考我的这篇博客:
日常–OBS+mediamtx实现本地RTMP推流环境搭建(详细图文)

4.如何实现的车牌和颜色识别

集成了一个车牌检测、字符识别与图像可视化的完整车牌识别系统,基于 PyTorch 和 OpenCV 构建,支持使用 YOLO 系列模型进行车牌定位,并结合自定义字符识别模型完成车牌号码和颜色的精准识别。系统内置了图像预处理、非极大值抑制(NMS)、双层车牌分割与拼接、合法性校验等功能,能够有效识别各种类型的单行或双层车牌,并输出包括车牌号、颜色、类型、置信度、定位框坐标及 base64 编码图像在内的结构化结果。支持通过设置 ROI 区域提升识别效率,并提供可视化接口在原图上绘制检测结果,包含直角框、文字标签与中文字体渲染。

5.项目结构

粉丝私聊我,担心项目跑不起来,这里统一回答:一定能跑起来,代码没问题的,大家要配置好环境
我们的项目结构清晰,可拓展性强,使用包、类名做了区分,所有核心代码在src/目录下。
大家有任何疑问可以加我好友,博客最底部有二维码的~

在这里插入图片描述

四.总结

本次和大家分享了我使用PyQt5开发的车牌、车牌颜色识别可视化系统,能够准确的识别目标视频中的车牌和颜色,采用多种可视化方案对数据使用图表进行展示,支持导出为不同格式的数据到文件,特有的ROI区域让用户操作更加个性化!
在这里插入图片描述

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。
如若转载,请注明出处:http://www.pswp.cn/pingmian/83519.shtml
繁体地址,请注明出处:http://hk.pswp.cn/pingmian/83519.shtml
英文地址,请注明出处:http://en.pswp.cn/pingmian/83519.shtml

如若内容造成侵权/违法违规/事实不符,请联系英文站点网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

python做题日记(12)

第二十七题 LeetCode第27题要求原地移除数组中所有等于给定值val的元素&#xff0c;并返回移除后数组的新长度。不能使用额外的数组空间&#xff0c;必须在原数组上修改&#xff0c;且元素的顺序可以改变。对于这道题的解法在之前的题目中也使用过&#xff0c;可以使用双指针法…

2025年计算机科学与网络安全国际会议(CSNS 2025)

第二届计算机科学与网络安全国际会议&#xff08;CSNS 2025&#xff09;将在兰州举办&#xff0c;这是一场聚焦于计算机科学领域最新进展及网络安全前沿技术的国际性学术交流盛会。该会议旨在为来自全球各地的研究学者、工程师以及相关行业专业人士提供一个高水平的交流平台&am…

知识拓展卡————————关于Access、Trunk、Hybrid端口

目录 什么是Trunk List、VLAN ID、PVID&#xff1a; VLAN ID&#xff08;Virtual Local Area Network Identifier&#xff09;&#xff1a; Trunk List&#xff08;Trunk列表&#xff09;&#xff1a; PVID&#xff08;Prot VLAN ID&#xff09;: 关于Native VLAN &#x…

Cursor 工具项目构建指南: Web Vue-Element UI 环境下的 Prompt Rules 约束(new Vue 方式)

简简单单 Online zuozuo: 简简单单 Online zuozuo 简简单单 Online zuozuo 简简单单 Online zuozuo 简简单单 Online zuozuo :本心、输入输出、结果 简简单单 Online zuozuo : 文章目录 Cursor 工具项目构建指南: Web Vue-Element UI 环境下的 Prompt Rules 约束前言项目简…

hadoop集群启动没有datanode解决

问题 多次初始化会出现此问题&#xff0c;根本原因是ClusterID不一样 解决 首先停止集群 stop-all.sh然后到/hadoop/logs中找到hadoop-root-datanode-hadoopxxx.log文件 cat一下这个文件&#xff0c;找到ClusterID 复制 然后到 可能文件会不太一样&#xff0c;可能直接是…

ann算法的种类有哪些,之间的区别,各自的适用场景

ANN&#xff08;近似最近邻&#xff09;算法主要分为三类技术路线&#xff1a;基于树的方法、哈希方法和图方法&#xff0c;它们在原理、性能及适用场景上有显著差异&#xff1a; 1. 基于树的方法 核心原理&#xff1a;递归划分数据空间形成树状结构&#xff08;如二叉树或多叉…

云服务器部署Gin+gorm 项目 demo

更多个人笔记见&#xff1a; &#xff08;注意点击“继续”&#xff0c;而不是“发现新项目”&#xff09; github个人笔记仓库 https://github.com/ZHLOVEYY/IT_note gitee 个人笔记仓库 https://gitee.com/harryhack/it_note 个人学习&#xff0c;学习过程中还会不断补充&…

【学习笔记】TCP 与 UDP

TCP&#xff08;Transmission Control Protocol&#xff09;与UDP&#xff08;User Datagram Protocol&#xff09;是 网络通讯 中最基础也最常用的两种 传输层 协议。 文章目录 1. 简介2. OSI 与 TCP/IP 模型中的定位3. 协议原理与关键机制3.1 UDP3.2 TCP 5. 实践&#xff1a;…

HikariCP 可观测性最佳实践

HikariCP 介绍 HikariCP 是一个高性能、轻量级的 JDBC 连接池&#xff0c;由 Brett Wooldridge 开发。它以“光”命名&#xff0c;象征快速高效。它支持多种数据库&#xff0c;配置简单&#xff0c;通过字节码优化和智能管理&#xff0c;实现低延迟和高并发处理。它还具备自动…

Java SpringBoot 调用大模型 AI 构建智能应用实战指南

一、基础知识 &#xff08;一&#xff09;Java基础 Java是一种广泛使用的高级编程语言&#xff0c;具有简单、面向对象、分布式、解释型、健壮、安全、架构中立、可移植、高性能、多线程和动态等特点。在构建基于Spring Boot的AI应用之前&#xff0c;您需要具备扎实的Java基础…

电路图识图基础知识-降压启动(十五)

降压启动电动机控制电路 降压启动&#xff0c;是指启动时降低加在电动机定子绕组上的电压&#xff0c;待电动机启动起来后再将电压 恢复到额定值&#xff0c;使之运行在额定电压下。降压启动可以减小启动电流&#xff0c;从而减小线路电压降。 传统的降压启动包括定子串电阻或…

2025年大模型平台落地实践研究报告|附75页PDF文件下载

本报告旨在为各行业企业在建设落地大模型平台的过程中&#xff0c;提供有效的参考和指引&#xff0c;助力大模型更高效更有价值地规模化落地。本报告系统性梳理了大模型平台的发展背景、历程和现状&#xff0c;结合大模型平台的特点提出了具体的落地策略与路径&#xff0c;同时…

Docker慢慢学

1、Docker DeskTop 2、N8N下载 3、Kafka docker run -d --name kafka -p 9092:9092 -e KAFKA_BROKER_ID1 -e KAFKA_ZOOKEEPER_CONNECTzookeeper:2181 -e KAFKA_ADVERTISED_LISTENERSPLAINTEXT://localhost:9092 -e KAFKA_OFFSETS_TOPIC_REPLICATION_FACTOR1 con…

Java 中创建线程主要有三种方式

在 Java 中&#xff0c;创建线程主要有三种方式&#xff0c;每种方式各有特点和适用场景。以下是详细说明和代码示例&#xff1a; 1. 继承 Thread 类 原理&#xff1a;自定义类继承 Thread 并重写 run() 方法&#xff0c;通过调用 start() 启动新线程。 特点&#xff1a;简单直…

ck-editor5的研究 (5):优化-页面离开时提醒保存,顺便了解一下 Editor的生命周期 和 6大编辑器类型

前言 经过前面的 4 篇内容&#xff0c;我们已经慢慢对 CKEditor5 熟悉起来了。这篇文章&#xff0c;我们就来做一个优化&#xff0c;顺便再补几个知识点&#xff1a; 当用户离开时页面时&#xff0c;提醒他保存数据了解一下 CKEditor5 的 六大编辑器类型了解一下 editor 实例对…

第42节:模型优化与部署:Web服务部署(Flask, FastAPI)

1. 引言 在现代人工智能和机器学习应用中,模型的开发只是整个流程的一部分。 将训练好的模型有效地部署为可访问的Web服务,使其能够处理实际请求并返回预测结果,是模型价值实现的关键环节。Python生态系统提供了多种轻量级Web框架,其中Flask和FastAPI是目前最受欢迎的选择…

LabVIEW超宽带紧凑场测量系统

采用 LabVIEW 开发超宽带紧凑场测量系统&#xff0c;实现天线方向图、目标雷达散射截面&#xff08;RCS&#xff09;及天线增益的自动化测量。通过品牌硬件设备&#xff0c;优化系统架构&#xff0c;解决传统测量系统在兼容性、数据处理效率及操作便捷性等方面的问题&#xff0…

vue2使用笔记、vue2和vue3的区别

文章目录 vue2和vue3的区别1. 实现数据响应式的原理不同2. 生命周期不同3. vue 2.0 采用了 option 选项式 API&#xff0c;vue 3.0 采用了 composition 组合式 API4. 新特性编译宏5. 父子组件间双向数据绑定 v-model 不同6. v-for 和 v-if 优先级不同7. 使用的 diff 算法不同8.…

CSS3美化页面元素

1. 字体 <span>标签 字体样式⭐ 字体类型&#xff08;font-family&#xff09; 字体大小&#xff08;font-size&#xff09; 字体风格&#xff08;font-style&#xff09; 字体粗细&#xff08;font-weight&#xff09; 字体属性&#xff08;font&#xff09; 2. 文本 文…

【笔记】Windows 下载并安装 ChromeDriver

以下是 在 Windows 上下载并安装 ChromeDriver 的笔记&#xff1a; ✅ Windows 下载并安装 ChromeDriver 1️⃣ 确认 Chrome 浏览器版本 打开 Chrome 浏览器 点击右上角 ︙ → 帮助 → 关于 Google Chrome 记下版本号&#xff0c;例如&#xff1a;114.0.5735.199 2️⃣ 下载…