VGA控制器

源文件

`timescale 1ns / 1ps

module VGA_CTRL(
    Clk,                //时钟
    Reset_n,            //复位
    Data,               //存储三原色的数据,由用户输入
    Data_Req,           //数据请求,解决RGB滞后Data的问题
    X,                  //像素点的横坐标,范围0~640
    Y,                  //像素点的纵坐标,范围0~480
    VGA_HS,             //行同步
    VGA_VS,             //场同步
    VGA_BLK,            //数据有效控制位,高电平有效
    VGA_RGB             //三原色
    );
    
    input Clk;
    input Reset_n;
    input[23:0] Data;
    output reg Data_Req;
    output reg [9:0] X;
    output reg [8:0] Y;
    output reg VGA_HS; 
    output reg VGA_VS;
    output reg VGA_BLK;
    output reg [23:0] VGA_RGB;

//各个信号和数据的变化时间节点,640*480
    localparam HS_Begin = 0;                                    //行同步脉冲的开始位置
    localparam HS_End = 96;                                     //行同步脉冲的结束位置
    localparam Hdat_Begin = 96 + 40 + 8;                        //行数据开始输出的位置
    localparam Hdat_End = 96 + 40 + 8 + 640;                    //行数据停止输出的位置
    localparam Hsync_End = 96 + 40 + 8 + 640 + 8 + 8;           //行同步信号的结束位置
    
    localparam VS_Begin = 0;                                    //场同步脉冲的开始位置
    localparam VS_End = 2;                                      //场同步脉冲的结束位置
    localparam Vdat_Begin = 2 + 25 + 8;                         //场数据开始输出的位置
    localparam Vdat_End = 2 + 25 + 8 + 480;                     //场数据停止输出的位置
    localparam Vsync_End = 2 + 25 + 8 + 480 + 2 + 8;            //场同步信号的结束位置
    
//定义颜色编码 
    localparam Black   = 24'h00_00_00,         //黑色
               Blue    = 24'h00_00_FF,         //蓝色
               Green   = 24'h00_FF_00,         //绿色
               Cyan    = 24'h00_FF_FF,         //青色
               Red     = 24'hFF_00_00,         //红色
               Purpple = 24'hFF_00_FF,         //紫色
               Yellow  = 24'hFF_FF_00,         //黄色
               White   = 24'hFF_FF_FF;         //白色
               
    
    reg [9:0] HS_Cnt;                               //行时钟计数器
    always@(posedge Clk or negedge Reset_n)
    if(!Reset_n)
        HS_Cnt <= 0;
    else if(HS_Cnt == Hsync_End - 1)
        HS_Cnt <= 0;
    else
        HS_Cnt <= HS_Cnt + 1'b1;
        
    
    reg [9:0] VS_Cnt;                               //场时钟计数器
    always@(posedge Clk or negedge Reset_n)
    if(!Reset_n)
        VS_Cnt <= 0;
    else if(HS_Cnt == Hsync_End - 1)                //如果行扫描完成
        begin
            if(VS_Cnt >= Vsync_End - 1)             //如果场扫描完成
                VS_Cnt <= 0;
            else
                VS_Cnt <= VS_Cnt + 1'b1;
        end
    else 
        VS_Cnt <= VS_Cnt;


//     组合逻辑
//    assign VGA_HS = (HS_Cnt < HS_End - 1'b1)?0:1;        //模仿时序
//    assign VGA_VS <= (VS_Cnt < Vsync_End - 1'b1)?0:1;        //模仿时序
//     assign VGA_BLK <= ((HS_Cnt >= Hdat_Begin) && (HS_Cnt <= Hdat_End) && (VS_Cnt >= Vdat_Begin) && (VS_Cnt <= Vdat_End))?1:0;            //就是图像的矩形区域
//     assign VGA_RGB <= VGA_BLK? Data:0;               //如果在图像矩形区域,就将用户的三原色数据给到 VGA_RGB;

//  时序逻辑
    always@(posedge Clk)
        VGA_HS = (HS_Cnt <= HS_End - 1'b1)?0:1;
    always@(posedge Clk)
        VGA_VS <= (VS_Cnt <= VS_End - 1'b1)?0:1;
 //BLK表示的就是输出 输出(三原色)的时间段    ,高电平有效
    always@(posedge Clk)
        Data_Req <= ((HS_Cnt >= Hdat_Begin) && (HS_Cnt < Hdat_End) && (VS_Cnt >= Vdat_Begin) && (VS_Cnt < Vdat_End))?1:0;      //解决RGB滞后Data的问题
    always@(posedge Clk)
        VGA_BLK <= Data_Req;
//RGB值由外界输入,且整个屏幕显示
//    always@(posedge Clk)  
//        VGA_RGB <= Data_Req? Data:0;      

//计算像素点的坐标
    always@(posedge Clk)
            X <= Data_Req? (HS_Cnt - Hdat_Begin - 1) : 0;
    always@(posedge Clk)
            Y <= Data_Req? (VS_Cnt - Vdat_Begin) : 0;
            
// 划分矩形区域,并在想要的区域填充想要的RGB值
    always@(posedge Clk)
          if((X >= 0) && (X < 320) && (Y >= 0) && (Y < 120))
                VGA_RGB <= Black;
          else if((X >= 0) && (X < 320) && (Y >= 120) && (Y < 240))
                VGA_RGB <= Blue;
          else if((X >= 0) && (X < 320) && (Y >= 240) && (Y < 360))
                VGA_RGB <= Green;
          else if((X >= 0) && (X < 320) && (Y >= 360) && (Y < 480))
                VGA_RGB <= Cyan;
          else if((X >= 320) && (X < 320) && (Y >= 0) && (Y < 120))
                VGA_RGB <= Red;
          else if((X >= 320) && (X < 320) && (Y >= 120) && (Y < 240))
                VGA_RGB <= Purpple;
          else if((X >= 320) && (X < 320) && (Y >= 240) && (Y < 360))
                VGA_RGB <= Yellow;
          else if((X >= 320) && (X < 320) && (Y >= 360) && (Y < 480))
                VGA_RGB <= White;
endmodule

仿真文件

`timescale 1ns / 1ps

module VGA_CTRL_tb;

    reg Clk;
    reg Reset_n;
    reg[23:0] Data;
    wire Data_Req;
    wire [9:0] X;
    wire [8:0] Y;
    wire VGA_HS; 
    wire VGA_VS;
    wire VGA_BLK;
    wire [23:0] VGA_RGB;


    VGA_CTRL VGA_CTRL_inst(
    .Clk(Clk),                //时钟
    .Reset_n(Reset_n),            //复位
    .Data(Data),               //存储三原色的数据,由用户输入
    .Data_Req(Data_Req),
    .X(X),
    .Y(Y),
    .VGA_HS(VGA_HS),             //行同步
    .VGA_VS(VGA_VS),             //场同步
    .VGA_BLK(VGA_BLK),            //数据有效控制位,高电平有效
    .VGA_RGB(VGA_RGB)             //三原色
    );

    initial Clk = 1;
    always #20 Clk = ~Clk;
    
    initial 
        begin
            Reset_n = 0;
            #201;
            Reset_n = 1;
            #2000000;
            $stop;
        end
    
    always@(posedge Clk or negedge Reset_n)
        if(!Reset_n)
            Data <= 0;
        else if(!Data_Req)
            Data <= Data;
        else
            Data <= Data + 1'd1;
    
endmodule

  • 1
    点赞
  • 4
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值