器材准备
EP4CE6E22C8N板子,下载器。
电路图
逻辑框架
首先,复位信号和时钟信号输入,形成一个内部的定时器信号。然后流水灯时序逻辑模块根据计时变化其对应的状态信号,然后把信号输入到流水灯状态逻辑模块。在流水灯状态逻辑模块里面,根据输入的按键信号选择不同流水灯效果。
可以看出,只要有时序逻辑关系的程序。整个程序就必须围绕时钟线进行。这个和其他芯片一样,没有时钟信号就不能工作。
代码
module key_led(
input sys_clk , //50Mhz系统时钟
input sys_rst_n, //系统复位,低有效
input [3:0] key, //按键输入信号
output reg [3:0] led //LED输出信号
);
//reg define
reg [23:0] cnt;
reg [1:0] led_control;
/用于计数0.2s的计数器/
always @ (posedge sys_clk or negedge sys_rst_n) begin
if(!sys_rst_n)
cnt<=24'd9_999_999;
else if(cnt<24'd9_999_999)
cnt<=cnt+1;
else
cnt<=0;
end
//用于led灯状态的选择
always @(posedge sys_clk or negedge sys_rst_n) begin
if (!sys_rst_n)
led_control <= 2'b00;
else if(cnt == 24'd9_999_999)
led_control <= led_control + 1'b1;
else
led_control <= led_control;
end
//识别按键,切换显示模式
always @(posedge sys_clk or negedge sys_rst_n) begin
if(!sys_rst_n) begin
led<=4'b 0000;
end
else if(key[0]== 0)
//按键1按下时,从右向左的流水灯效果
case (led_control)
2'b00 : led<=4'b0111;
2'b01 : led<=4'b1011;
2'b10 : led<=4'b1101;
2'b11 : led<=4'b1110;
default : led<=4'b1111;
endcase
//按键2按下时,从左向右的流水灯效果
else if (key[1]==0)
case (led_control)
2'b00 : led<=4'b1110;
2'b01 : led<=4'b1101;
2'b10 : led<=4'b1011;
2'b11 : led<=4'b0111;
default : led<=4'b1111;
endcase
//按键3按下时,LED闪烁
else if (key[2] ==0)
case (led_control)
2'b00 : led<=4'b1001;
2'b01 : led<=4'b0110;
2'b10 : led<=4'b0110;
2'b11 : led<=4'b0110;
default : led<=4'b0000;
endcase
//按键4按下时,LED全亮
else if (key[3] ==0)
led=4'b0000;
else
//无按键按下时,LED熄灭
led<=4'b1111;
end
endmodule
引脚分配
缺点
如果要实现按一下按键松开,然后执行不同状态,这个实现起来优点难度。还需要有延时消抖,电路中没有提供滤波电路。