FPGA 车牌识别与 Modelsim 仿真
本文介绍基于 Artix-7 开发板的车牌识别系统实现及 Modelsim 仿真验证,使用 Vivado 2019.2 开发环境。
一、硬件基础
本次选用的 FPGA 芯片为 XC7A35T。该芯片性能稳定,足以满足车牌识别这类复杂图像处理任务的需求。连接摄像头(OV5640)和 LCD 显示屏(800×480),即可开始车牌识别功能测试。
二、功能实现解析
1. 图像采集
图像采集部分主要负责从 OV5640 摄像头获取图像数据。在 Vivado 环境下,通过编写 Verilog 代码来实现与摄像头的通信协议,如配置摄像头的分辨率、帧率等参数。
module ov5640_interface (
input wire clk,
input wire rst,
// 摄像头相关信号
input wire vsync,
input wire href,
input wire pixel_clk,
input wire [7:0] data,
// 输出采集到的图像数据
output reg [23:0] img_data,
output reg img_valid
);
always @(posedge pixel_clk or posedge rst) begin
if (rst) begin
img_data <= 24'd0;
img_valid <= 1'b0;
end else if (vsync && href) begin
img_data <= {data, data, data};
img_valid <= 1'b1;
end else begin
img_valid <= 1'b0;
end
end
endmodule
在这段代码中,通过 pixel_clk 时钟信号来采样摄像头输出的像素数据 data,当 vsync(垂直同步信号)和 href(水平同步信号)有效时,将像素数据转换为 24 位的 RGB 格式并输出 img_data,同时拉高 img_valid 表示数据有效。
2. RGB 转 YCbCr
为了后续更好地进行图像处理,常常需要将采集到的 RGB 图像数据转换为 YCbCr 格式。
module rgb_to_ycbcr (
input wire [23:0] rgb,
output reg [7:0] y,
output reg [7:0] cb,
output reg [7:0] cr
);
always @(*) begin
y = (8'd65 * rgb[23:16] + 8'd129 * rgb[15:8] + 8'd25 * rgb[7:0] + 8'd128) >> 8;
cb = (8'd - 38 * rgb[23:16] - 8'd74 * rgb[15:8] + 8'd112 * rgb[7:0] + 8'd128) >> 8;
cr = (8'd112 * rgb[23:16] - 8'd94 * rgb[15:8] - 8'd18 * rgb[7:0] + 8'd128) >> 8;
end
endmodule
这里依据 RGB 到 YCbCr 的转换公式,通过简单的乘法、加法和移位操作实现了格式转换。这种转换在 FPGA 上实现效率较高,为后续的图像处理提供了合适的数据格式。
3. Sobel 边缘检测
Sobel 边缘检测是车牌识别中提取车牌轮廓的重要步骤。它通过与特定的卷积模板进行运算,增强图像中的边缘信息。
module sobel_edge_detection (
input wire [7:0] img_in,
input wire clk,
input wire rst,
output reg [7:0] edge_out
);
reg [7:0] gx[0:2][0:2];
reg [7:0] gy[0:2][0:2];
integer i, j;
always @(posedge clk or posedge rst) begin
if (rst) begin
for (i = 0; i < 3; i = i + 1) begin
for (j = 0; j < 3; j = j + 1) begin
gx[i][j] <= 8'd0;
gy[i][j] <= 8'd0;
end
end
edge_out <= 8'd0;
end else begin
// 填充 gx 和 gy 模板数据(实际实现需结合图像存储方式调整)
// 简单计算边缘强度
edge_out = (gx[0][0] + 2 * gx[0][1] + gx[0][2] + gx[1][0] + 2 * gx[1][1] + gx[1][2] + gx[2][0] + 2 * gx[2][1] + gx[2][2]) +
(gy[0][0] + 2 * gy[0][1] + gy[0][2] + gy[1][0] + 2 * gy[1][1] + gy[1][2] + gy[2][0] + 2 * gy[2][1] + gy[2][2]);
end
end
endmodule





