日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 编程资源 > 编程问答 >内容正文

编程问答

Zedboard学习(七):VGA显示

發布時間:2025/3/21 编程问答 19 豆豆
生活随笔 收集整理的這篇文章主要介紹了 Zedboard学习(七):VGA显示 小編覺得挺不錯的,現在分享給大家,幫大家做個參考.

VGA硬件接口

到zedboard官方給出的原理圖中查看:

RGB信號,各四位;這里的設計是使用了電阻分壓模擬了DAC芯片實現了4X4X4的RGB信號,如果要更好的顯示效果還是建議使用專門的DAC。


上面給出了所有的引腳分配。

信號功能引腳分配
Red紅色視頻信號V20, U20, V19, V18
Green綠色視頻信號AB22, AA22, AB21, AA21
Blue藍色視頻信號Y21, Y20, AB20, AB19
Hsync行同步信號AA19
Vsync列同步信號Y19

VGA時序分析


如上圖所示,就是VGA時序的表示。按照這個時序圖,編寫程序。

Hsync是行同步信號,表示一行的開始和上一行的結束;
Vsync是列同步信號,表示一場的開始和上一場的結束;
行時序是以像素為單位的, 場時序是以行為單位的;
像素點從左到右算一行,行數從上到下算一場。

在圖上定義了很多區間,而根據這些區間我們可以看到整個時序圖被分為了三個矩形:中間的Adressable Video,其外面的Border,還有最外面的Blanking。
傳輸數據的時間就是中間的Adressable Video的這段時間,同步到每個像素即可。中間的那個矩形就對應顯示器顯示的范圍,其他的矩形可以看做是不可見的。

VGA的時序我只是簡單介紹了下,詳細的介紹可以查看:[筆記]VGA時序及其原理

列出幾個常用的時序:
640×480 @60HZ

800×600@60HZ

上面給出了幾個示例,圖中給出了時序參數的計算步驟以及最后結果,可以到這下載:VGA時序標準
現在我們只提取出最后要用到的時序參數:

(這個圖是我直接在網上截圖的,不保證全部正確,最好參考VGA時序標準確認一遍,以手冊為準)

編寫代碼

新建工程,添加Verilog代碼,這些步驟不再贅述。
直接上代碼了,代碼中添加了注釋。我選取的是800×600@60HZ。
程序的結構:

產生vga信號的代碼:
vga_data_gen.v

`timescale 1ns / 1ps // // Company: // Engineer: // // Create Date: 2017/07/27 23:15:37 // Design Name: // Module Name: vga_data_gen // Project Name: // Target Devices: // Tool Versions: // Description: // // Dependencies: // // Revision: // Revision 0.01 - File Created // Additional Comments: // //module vga_data_gen(input pixel_clk, //像素時鐘input rst, //復位按鍵,高電平復位output [7:0] vga_r, //vga信號紅色視頻信號output [7:0] vga_g, //vga信號綠色視頻信號output [7:0] vga_b, //vga信號藍色視頻信號output vga_hs, //行同步信號output vga_vs, //場同步信號output vga_de, //vga信號有效,如當前時刻傳輸數據有效,即為1;否則為0;input turn_mode, //按鍵。按下為高電平,切換vga顯示模式output [3:0] mode //當前顯示模式,用4位編碼);//---------------------------------// // 水平掃描參數的設定 800*600 60HZ //--------------------------------// parameter H_Total = 1056 - 1; parameter H_Sync = 128 - 1; parameter H_Back = 88 - 1; parameter H_Active = 800 - 1; parameter H_Front = 40 - 1; parameter H_Start = 216 - 1; parameter H_End = 1016 - 1;//-------------------------------// // 垂直掃描參數的設定 1280*720 60HZ //-------------------------------// parameter V_Total = 628 - 1; parameter V_Sync = 4 - 1; parameter V_Back = 23 - 1; parameter V_Active = 600 - 1; parameter V_Front = 1 - 1; parameter V_Start = 27 - 1; parameter V_End = 627 - 1;//行信號計數器 reg [11:0] x_cnt; always @(posedge pixel_clk or posedge rst) beginif(rst)x_cnt <= 12'd0;else if(x_cnt == H_Total)x_cnt <= 12'd0;elsex_cnt <= x_cnt + 1'b1; end//根據時序圖參數,產生行同步信號 reg hsync_r; always @(posedge pixel_clk or posedge rst) beginif(rst)hsync_r <= 1'b1;else if(x_cnt>=0 && x_cnt < H_Sync)hsync_r <= 1'b0;elsehsync_r <= 1'b1; end//行信號有效,即當前數據有效 reg hs_de; always @(posedge pixel_clk or posedge rst) beginif(rst)hs_de <= 1'b0;else if(x_cnt>=H_Start && x_cnt<H_End)hs_de <= 1'b1;elsehs_de <= 1'b0; end//場信號計數器 reg [11:0] y_cnt; always @(posedge pixel_clk or posedge rst) beginif(rst)y_cnt <= 12'd0;else if(y_cnt == V_Total)y_cnt <= 12'd0;else if(x_cnt == H_Total)y_cnt <= y_cnt + 1'b1; end//根據時序圖參數,產生場同步信號 reg vsync_r; always @(posedge pixel_clk or posedge rst) beginif(rst)vsync_r <= 1'b1;else if(y_cnt>=0 && y_cnt<V_Sync)vsync_r <= 1'b0;elsevsync_r <= 1'b1; end//列信號有效,即當前數據有效 reg vs_de; always @(posedge pixel_clk or posedge rst) beginif(rst)vs_de <= 1'b0;else if(y_cnt>=V_Start && y_cnt<V_End)vs_de <= 1'b1;elsevs_de <= 1'b0; end//按鍵消抖,按下后延時一段時間,再檢測是否按下 reg [16:0] key_counter; always @(posedge pixel_clk) beginif(turn_mode)key_counter <= 17'd0;else if((turn_mode == 1'b0) && (key_counter <= 17'h11704))key_counter <= key_counter + 1'b1; end//顯示模式技術,每次按下按鍵,模式改變,最多有12種顯示模式 reg [3:0] dis_mode; assign mode = dis_mode; always @(posedge pixel_clk) beginif(key_counter == 17'h11704)beginif(dis_mode == 4'd12)dis_mode <= 4'd0;else dis_mode <= dis_mode +1'b1;end end//產生小格子,黑白棋盤 reg [7:0] grid_data_1; always @(posedge pixel_clk) beginif((x_cnt[4] == 1'b0) ^ (y_cnt[4] == 1'b0))grid_data_1 <= 8'h00;elsegrid_data_1 <= 8'hff; end//產生大格子,黑白棋盤 reg [7:0] grid_data_2; always @(posedge pixel_clk) beginif((x_cnt[6] == 1'b0) ^ (y_cnt[6] == 1'b0))grid_data_2 <= 8'h00;elsegrid_data_2 <= 8'hff; end//產生彩條 reg [23:0] color_bar; always @(posedge pixel_clk) beginif(x_cnt>=216 && x_cnt<316)color_bar <= 24'hff0000;else if(x_cnt>=316 && x_cnt<416)color_bar <= 24'h00ff00;else if(x_cnt>=416 && x_cnt<516)color_bar <= 24'h0000ff;else if(x_cnt>=516 && x_cnt<616)color_bar <= 24'hff00ff;else if(x_cnt>=616 && x_cnt<716)color_bar <= 24'hffff00;else if(x_cnt>=716 && x_cnt<816)color_bar <= 24'h00ffff;else if(x_cnt>=816 && x_cnt<916)color_bar <= 24'hffffff;else if(x_cnt>=916 && x_cnt<1016)color_bar <= 24'h000000;elsecolor_bar <= color_bar; end//根據顯示模式傳輸rgb信號到緩存器中 reg [7:0] vga_r_reg; reg [7:0] vga_g_reg; reg [7:0] vga_b_reg; always @(posedge pixel_clk or posedge rst) beginif(rst)beginvga_r_reg <= 8'd0;vga_g_reg <= 8'd0;vga_b_reg <= 8'd0;endelsebegincase(dis_mode)4'd0: //全黑beginvga_r_reg <= 8'd0;vga_g_reg <= 8'd0;vga_b_reg <= 8'd0;end4'd1: //全白beginvga_r_reg <= 8'b1111_1111;vga_g_reg <= 8'b1111_1111;vga_b_reg <= 8'b1111_1111;end4'd2: //全紅beginvga_r_reg <= 8'b1111_1111;vga_g_reg <= 8'd0;vga_b_reg <= 8'd0;end4'd3: //全綠beginvga_r_reg <= 8'd0;vga_g_reg <= 8'b1111_1111;vga_b_reg <= 8'd0;end4'd4: //全藍beginvga_r_reg <= 8'd0;vga_g_reg <= 8'd0;vga_b_reg <= 8'b1111_1111;end4'd5: //小格子,黑白棋盤beginvga_r_reg <= grid_data_1;vga_g_reg <= grid_data_1;vga_b_reg <= grid_data_1;end4'd6: //大格子,黑白棋盤beginvga_r_reg <= grid_data_2;vga_g_reg <= grid_data_2;vga_b_reg <= grid_data_2;end4'd7: //根據行信號漸變,周期性從黑到白beginvga_r_reg <= x_cnt[7:0];vga_g_reg <= x_cnt[7:0];vga_b_reg <= x_cnt[7:0];end4'd8: //根據場信號漸變,周期性從黑到白beginvga_r_reg <= y_cnt[7:0];vga_g_reg <= y_cnt[7:0];vga_b_reg <= y_cnt[7:0];end4'd9: //根據行信號漸變,周期性紅色從淺到深beginvga_r_reg <= x_cnt[7:0];vga_g_reg <= 8'd0;vga_b_reg <= 8'd0;end4'd10: //根據列信號漸變,周期性綠色從淺到深beginvga_r_reg <= 8'd0;vga_g_reg <= x_cnt[7:0];vga_b_reg <= 8'd0;end4'd11: //根據行信號漸變,周期性藍色從淺到深beginvga_r_reg <= 8'd0;vga_g_reg <= 8'd0;vga_b_reg <= x_cnt[7:0];end4'd12: //彩條信號beginvga_r_reg <= color_bar[23:16];vga_g_reg <= color_bar[15:8];vga_b_reg <= color_bar[7:0];enddefault:beginvga_r_reg <= 8'b1111_1111;vga_g_reg <= 8'b1111_1111;vga_b_reg <= 8'b1111_1111;endendcaseend end//將這些寄存器中的信號輸出 assign vga_hs = hsync_r; assign vga_vs = vsync_r; assign vga_de = hs_de & vs_de; //只有當行信號和場信號同時有效時數據才有效 assign vga_r = (hs_de & vs_de) ? vga_r_reg : 8'h0; assign vga_g = (hs_de & vs_de) ? vga_g_reg : 8'h0; assign vga_b = (hs_de & vs_de) ? vga_b_reg : 8'h0;endmodule

由于VGA信號是800×600@60HZ,我們還需要一個像素時鐘40MHZ。zedboard的PL部分默認的時鐘是100MHZ,所以我們還需要一個時鐘單元來產生40MHZ的特定時鐘。分頻的方法不穩定,不推薦。

點擊準備添加IP核。
如下圖所示找到clocking wizard。打開它,開始配置其功能。

這些都默認不改動,時鐘是100MHZ。

修改輸出時鐘為40MHZ,其他不做修改。

直接點擊OK,創建IP核。

點擊generate產生IP核。

最后會產生這個,我們可以通過Verilog調用這個模塊。

最后編寫頂層Verilog代碼:只是把前面幾個模塊包進來。
vga_disp.v

`timescale 1ns / 1ps // // Company: // Engineer: // // Create Date: 2017/07/27 23:12:46 // Design Name: // Module Name: vga_disp // Project Name: // Target Devices: // Tool Versions: // Description: // // Dependencies: // // Revision: // Revision 0.01 - File Created // Additional Comments: // //module vga_disp(input clk100M,input rst,input key,output [3:0] vga_r,output [3:0] vga_g,output [3:0] vga_b,output vga_hs,output vga_vs,output [3:0] led);wire pixel_clk;wire [7:0] R, G, B;wire HS, VS, DE;assign vga_r = R[7:4];assign vga_g = G[7:4];assign vga_b = B[7:4];assign vga_hs = HS;assign vga_vs = VS;vga_data_gen vga_data_gen(.pixel_clk(pixel_clk),.rst(rst),.vga_r(R),.vga_g(G),.vga_b(B),.vga_hs(HS),.vga_vs(VS),.vga_de(DE),.turn_mode(key),.mode(led));clk_wiz_0 clk(.clk_out1(pixel_clk),.reset(1'b0),.locked(),.clk_in1(clk100M));endmodule

編寫引腳約束文件,在官方給出的原理圖中都可以查到。
pins.xdc

# Clk(板子上的GCLK) set_property PACKAGE_PIN Y9 [get_ports {clk100M}] set_property IOSTANDARD LVCMOS33 [get_ports {clk100M}]# Rst(板子上的BTNU) set_property PACKAGE_PIN T18 [get_ports {rst}] set_property IOSTANDARD LVCMOS33 [get_ports {rst}]# key 板子上的按鍵 set_property PACKAGE_PIN P16 [get_ports {key}] set_property IOSTANDARD LVCMOS33 [get_ports {key}]# Led0 set_property PACKAGE_PIN T22 [get_ports {led[0]}] set_property IOSTANDARD LVCMOS33 [get_ports {led[0]}]# Led1 set_property PACKAGE_PIN T21 [get_ports {led[1]}] set_property IOSTANDARD LVCMOS33 [get_ports {led[1]}]# Led2 set_property PACKAGE_PIN U22 [get_ports {led[2]}] set_property IOSTANDARD LVCMOS33 [get_ports {led[2]}]# Led3 set_property PACKAGE_PIN U21 [get_ports {led[3]}] set_property IOSTANDARD LVCMOS33 [get_ports {led[3]}]set_property PACKAGE_PIN Y19 [get_ports {vga_vs}] set_property IOSTANDARD LVCMOS33 [get_ports {vga_vs}]set_property PACKAGE_PIN AA19 [get_ports {vga_hs}] set_property IOSTANDARD LVCMOS33 [get_ports {vga_hs}]set_property PACKAGE_PIN V20 [get_ports {vga_r[0]}] set_property IOSTANDARD LVCMOS33 [get_ports {vga_r[0]}] set_property PACKAGE_PIN U20 [get_ports {vga_r[1]}] set_property IOSTANDARD LVCMOS33 [get_ports {vga_r[1]}] set_property PACKAGE_PIN V19 [get_ports {vga_r[2]}] set_property IOSTANDARD LVCMOS33 [get_ports {vga_r[2]}] set_property PACKAGE_PIN V18 [get_ports {vga_r[3]}] set_property IOSTANDARD LVCMOS33 [get_ports {vga_r[3]}]set_property PACKAGE_PIN AB22 [get_ports {vga_g[0]}] set_property IOSTANDARD LVCMOS33 [get_ports {vga_g[0]}] set_property PACKAGE_PIN AA22 [get_ports {vga_g[1]}] set_property IOSTANDARD LVCMOS33 [get_ports {vga_g[1]}] set_property PACKAGE_PIN AB21 [get_ports {vga_g[2]}] set_property IOSTANDARD LVCMOS33 [get_ports {vga_g[2]}] set_property PACKAGE_PIN AA21 [get_ports {vga_g[3]}] set_property IOSTANDARD LVCMOS33 [get_ports {vga_g[3]}]set_property PACKAGE_PIN Y21 [get_ports {vga_b[0]}] set_property IOSTANDARD LVCMOS33 [get_ports {vga_b[0]}] set_property PACKAGE_PIN Y20 [get_ports {vga_b[1]}] set_property IOSTANDARD LVCMOS33 [get_ports {vga_b[1]}] set_property PACKAGE_PIN AB20 [get_ports {vga_b[2]}] set_property IOSTANDARD LVCMOS33 [get_ports {vga_b[2]}] set_property PACKAGE_PIN AB19 [get_ports {vga_b[3]}] set_property IOSTANDARD LVCMOS33 [get_ports {vga_b[3]}]

分析綜合產生比特流文件,后進行下載。

按鍵設置:
圖中BTNU鍵位復位鍵;BTNC鍵位模式切換鍵,每按一次切換顯示模式。

連上vga線,可以看到現象如下:

總結

以上是生活随笔為你收集整理的Zedboard学习(七):VGA显示的全部內容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。