本帖最后由 CaelumINshell 于 2017-5-2 18:35 编辑
是这样的,我写的数字时钟显示模块里面,always块里面的触发沿频率为800Hz,可是在动态显示的时候却出现了显示字迹一直闪烁并且显示逐渐不清晰的情况,具体如下图,纠结了很久却找不到原因,自己之前试着修改显示模块扫描的频率,但是武乱是增加还是减小,显示效果总是达不到理想的显示而不闪烁的情况,这到底是怎么回事呢?是因为我没有设置延时或者是扫描频率太小导致的吗?请各位大神帮我解答,我的扫描频率是800HZ,时钟为1Hz,百分秒为100Hz.
我也在想这个问题,但是由于我有显示百分秒(ms)的数据,所以不知道延时多少合适,也不知道在那个位置进行延时,,求大神解答啊,我贴上我的程序。
module lcd_ip(clk,rst,data_buf,lcd_e,lcd_rw,lcd_rs,lcd_data);
input clk;
input rst;
input [255:0]data_buf; //数据接口
output lcd_e;
output lcd_rw;
output lcd_rs;
output [7:0]lcd_data;
//---------------------------------------------------------------
//分频得到clk_800Hz
reg [16:0]cnt;
reg clk_lcd;
always @(posedge clk or negedge rst)
if(!rst)
cnt <= 1'b0;
else
begin
cnt <= cnt + 1'b1;
if( cnt == 17'd31249)
begin
cnt <= 1'b0;
clk_lcd <= ~clk_lcd;
end
end
//---------------------------------------------------------------
reg [2:0]func; //状态机func
reg [3:0]com_cnt; //com_buf_bit的计数模块
reg [5:0]data_cnt; //data_buf_bit计数模块
reg [47:0]com_buf_bit; //6条lcd屏幕指令 每条8bit,6条就需要 6x8=48bit
reg [255:0]data_buf_bit;//lcd 每行16个字符,一共两行,总共32个字符,一个字符需要8bit显示,所以32x8=256bit 参考LCD1602液晶显示控制部分
parameter set0=4'd1,set1=4'd2,dat1=4'd3,set2=4'd4,dat2=4'd5,done=4'd6;
parameter com_buf={ 8'h02,
8'h06,
8'h0C,
8'h38,
8'h80,
8'h00,
};//LCD1602指令,对屏幕初始化
//---------------------------------------------------------------
reg [7:0]lcd_data;
reg lcd_rs;
reg en;
reg [255:0]data; //因为封装成ip核所以采用一个寄存器把data_buf值存起来,用于对比
always @(posedge clk_lcd or negedge rst)
begin
if(!rst)
com_buf_bit <= 8'h01; //清屏指令
else
begin
en <= 0; //写指令
case(func)
//液晶屏初始化
set0: begin
com_buf_bit <= com_buf;
data_buf_bit <= data_buf;
data <= data_buf; //data_buf存到寄存器data里面
com_cnt <= 1'b0;
data_cnt <= 1'b0;
func <= set1;
end
//---------------------------------------------------------------
set1: begin
lcd_rs <= 0; //写指令
lcd_data <= com_buf_bit[47:40];
com_buf_bit <= (com_buf_bit<<8);
com_cnt <= com_cnt + 1'b1;
if(com_cnt <= 5) //共6次,6条lcd指令
func <= set1;
else
begin
func <= dat1;
com_cnt <= 1'b0;
end
end
//---------------------------------------------------------------
dat1: begin
lcd_rs <= 1; //写数据
lcd_data <= data_buf_bit[255:248];
data_buf_bit <= (data_buf_bit<<8);
data_cnt <= data_cnt + 1'b1;
if(data_cnt < 15) //共16次 液晶屏第一行显示的内容
func <= dat1;
else
func <= set2;
end
//---------------------------------------------------------------
set2: begin
lcd_rs <= 0; //写指令
lcd_data <= 8'hC0; //表示第二行第一位
func <= dat2;
end
//---------------------------------------------------------------
dat2: begin
lcd_rs <= 1; //写数据
lcd_data <= data_buf_bit[255:248];
data_buf_bit <= (data_buf_bit<<8);
data_cnt <= data_cnt + 1'b1;
if(data_cnt < 31) //共32次 把第二行的内容显示在屏幕上
func <= dat2; //不能把第一行字符显示出来,所以采用分两次写数据
else
begin
func <= done;
data_cnt <= 1'b0;
end
end
//---------------------------------------------------------------
done: begin
if(data_buf!==data ) //判断有没有新送进来的数据,对比法
func <= set0; //有就回液晶屏初始化
else
begin
func <= done; //没有就结束
en <= 1;
end
end
default:func <= set1;
endcase
end
end
//---------------------------------------------------------------
assign lcd_e = clk_lcd | en;
assign lcd_rw = 0;
endmodule
一周热门 更多>