學習VGA顯示圖片的過程中,遇到了一個小問題,我在顯示屏上開了一個60x60的框,放了一張圖片進去顯示,但是最終的結果如下圖所示。 出現了一個豎黑邊,看了看代碼,分析了一下邏輯沒問題,然而看這個顯示那肯定是有問題的,然後模擬了一下看看,時序圖如下。 正確的時序 錯誤的時序 我這是的是當行計數器記到2 ...
學習VGA顯示圖片的過程中,遇到了一個小問題,我在顯示屏上開了一個60x60的框,放了一張圖片進去顯示,但是最終的結果如下圖所示。
出現了一個豎黑邊,看了看代碼,分析了一下邏輯沒問題,然而看這個顯示那肯定是有問題的,然後模擬了一下看看,時序圖如下。
正確的時序
錯誤的時序
我這是的是當行計數器記到200和場計數器記到200的時候顯示ROM中的數據,在顯示屏中開出一個60x60的正方形顯示區域,對比上兩幅圖可得,第二幅圖在當行計數器計數到200的時候lcd_data本應該是ROM里的數據,但是卻輸出的是16’h00,這是因為我原始的代碼寫的是當行計數器記到200的時候給ROM地址加1,然後有個使能信號將ROM的輸出讀出,但是實際上行計數記到200的同時ROM地址已經加1,那麼ROM的第一個數據就沒法讀出來,然後從第二個數據開始顯示,即每一行的第一個數據都沒有給出所以最終會顯示出一個豎黑邊,那麼這個問題怎麼解決呢?很簡單,就是在行計數器記到199的時候給使能信號,所以當顯示屏顯示第200個數據的時候,ROM的第一個數據正好讀出,代碼如下:顯示結果如下
1 //--------------------------------------------- 2 //addra 3 always @(posedge clk or negedge rst_n)begin 4 if(!rst_n) 5 addra <= 16'd0; 6 else if(addra == 3600 - 1'b1) 7 addra <= 16'd0; 8 else if(lcd_x >= 200 && lcd_x < 260 && lcd_y >= 200 && lcd_y < 260) 9 addra <= addra + 1'b1; 10 else 11 addra <= addra; 12 end 13 14 //----------------------------------------------------------------------- 15 //pic_en 16 reg pic_en; 17 always @(posedge clk or negedge rst_n)begin 18 if(!rst_n) 19 pic_en <= 1'b0; 20 else if(lcd_x >= 200 && lcd_x < 260 && lcd_y >= 200 && lcd_y < 260) 21 pic_en <= 1'b1; 22 else 23 pic_en <= 1'b0; 24 end 25 26 //----------------------------------------------------------------------- 27 //data_en 28 reg data_en; 29 always @(posedge clk or negedge rst_n)begin 30 if(!rst_n) 31 data_en <= 1'b0; 32 else if(lcd_x >= 199 && lcd_x < 259 && lcd_y >= 200 && lcd_y < 260) 33 data_en <= 1'b1; 34 else 35 data_en <= 1'b0; 36 end 37 38 //lcd_data 39 reg [15:0] lcd_data_r0; 40 reg [15:0] lcd_data_r1; 41 42 always @(posedge clk or negedge rst_n)begin 43 if(!rst_n) 44 lcd_data_r0 <= 16'b0; 45 else if(lcd_y > 0 && lcd_y <= 150) 46 lcd_data_r0 <= `WHITE; 47 else if(lcd_y > 150 && lcd_y <= 350) 48 lcd_data_r0 <= `GREEN; 49 else if(lcd_y > 350 && lcd_y <= 480) 50 lcd_data_r0 <= `BLUE; 51 else 52 lcd_data_r0 <= 16'b0; 53 end 54 55 always @(posedge clk or negedge rst_n)begin 56 if(!rst_n) 57 lcd_data_r1 <= 16'b0; 58 else if(pic_en == 1'b1) 59 lcd_data_r1 <= douta; 60 else 61 lcd_data_r1 <= 16'b0; 62 end 63 64 //assign lcd_data = (pic_en == 1'b1)? `CYAN: lcd_data_r0;//開出一個紫顏色的框 65 66 assign lcd_data = (pic_en == 1'b1)? lcd_data_r1: lcd_data_r0;
轉載請註明出處:NingHeChuan(寧河川)
個人微信訂閱號:開源FPGANingHeChuan
如果你想及時收到個人撰寫的博文推送,可以掃描左邊二維碼(或者長按識別二維碼)關註個人微信訂閱號
知乎ID:NingHeChuan
微博ID:NingHeChuan
原文地址:http://www.cnblogs.com/ninghechuan/p/7577224.html