Bootstrap

数字图像处理(9):VGA接口及其时序

(1)特点:成本低、结构简单、应用灵活

        VGA接口需要五个信号:R、G、B、Hsync、Vsync

(2)VGA的工作原理:

  • 设定一个高速时钟信号(像素时钟)来控制每个像素的传输速率,例如:对于640x480分辨率,像素时钟为25.175MHz。(可以通过PLL实现)
  • 水平扫描:显示器从左往右逐行扫描像素,每行扫描完成后,发送一个水平同步信号(Hsync)来表示行的结束。在水平同步信号之后,有一段水平消隐区,用来准备下一行的扫描。
  • 垂直扫描:显示器从上到下逐帧扫描行像素。每帧扫描完成后,发送一个垂直同步信号(VSync)来表示帧的结束。在垂直同步信号之后,有一段垂直消隐区,用于准备下一帧的扫描。

(3)附上一段常用的VGA代码

module tft_ctrl(
    input               hdmi_clk        ,
    input               reset_n         ,
    input   [23:0]      data_in         ,
                                        
    output  [9:0]       hang            ,
    output  [9:0]       lie             ,
    output              hsync           ,
    output              vsync           ,
    output  [23:0]      rgb_tft         ,
    output              tft_DE          
    
);
    
    reg     [10:0]      hang_cnt        ;
    reg     [9:0]       v_cnt           ;

    wire                data_valid      ;
    
    parameter H_SYNC        =   96      ;
    parameter H_BACK        =   40      ;
    parameter H_LEEF        =   8       ;
    parameter H_VALID       =   640     ;
    parameter H_RIGHT       =   8       ;    
    parameter H_FRONT       =   8       ;
    parameter H_TOTAL       =   800     ;
    
    parameter V_SYNC        =   2       ;
    parameter V_BACK        =   25      ;
    parameter V_TOP         =   8       ;
    parameter V_VALID       =   480     ;
    parameter V_BOTTOM      =   8       ;    
    parameter V_FRONT       =   2       ;
    parameter V_TOTAL       =   525     ;

//行计数器设计
    always@(posedge hdmi_clk or negedge reset_n)
        if(!reset_n)
            hang_cnt <= 11'd0;
        else if(hang_cnt == H_TOTAL - 11'd1)
            hang_cnt <= 11'd0;
        else 
            hang_cnt <= hang_cnt + 11'd1;
            
//场计数器设计
    always@(posedge hdmi_clk or negedge reset_n)
        if(!reset_n)
            v_cnt <= 10'd0;
        else if ((v_cnt == V_TOTAL - 10'd1) && (hang_cnt == H_TOTAL - 11'd1))
            v_cnt <= 10'd0;
        else if(hang_cnt == H_TOTAL - 11'd1)
            v_cnt <= v_cnt + 10'd1;
        else 
            v_cnt <= v_cnt;

//数据有效信号设计
    assign data_valid = (hang_cnt >= H_SYNC + H_BACK + H_LEEF) && (hang_cnt < H_SYNC + H_BACK + H_LEEF + H_VALID)
                            && (v_cnt >= V_SYNC + V_BACK + V_TOP) && (v_cnt < V_SYNC + V_BACK + V_TOP + V_VALID);
                            
//行、列信号设计   
    assign hang = ( data_valid ) ? (hang_cnt - H_SYNC - H_BACK - H_LEEF + 1'd1) : 10'd0;
    assign lie  = ( data_valid ) ? (v_cnt - V_SYNC - V_BACK - V_TOP + 1'd1) : 10'd0;    
    
//行同步、场同步信号设计
    assign hsync = (hang_cnt >= H_SYNC);
    assign vsync = (v_cnt >= V_SYNC);
    
//rgb_tft、tft_DE信号设计
    assign rgb_tft = (data_valid) ? data_in : 24'd0;
    assign tft_DE  = data_valid;

endmodule

;