录
题目
设计思路
代码设计
(1)4个按键分别设置4位数码管上的显示数字,当按键设置的数字与设置的4位密码一致时,蜂鸣器响,表示锁打开;
(2)具备通过按键手动修改数字密码的功能;
(3)具备按键消抖电路功能;
(4)一定时间内无操作数字显示回到初始状态,数码管显示倒计时。
我们可以用四个同bit位宽的寄存器把密码寄存起来,在按键时不断将现在按键的值与密码的寄存器对比,当所有对应位都相同时,蜂鸣器响,可以用一个标志位表示所有对应位相同,蜂鸣器工作的条件就是标志位给出的。
由于需要按键手动修改密码,那么数码管显示就有两种状态,一种是修改密码,一种是输入密码。我通过增加一个按键来控制这两种状态,当按下这个按键时进入修改密码阶段,当再次按下时进入输入密码阶段。
按键消抖部分我之前写过,可以看之前的按键消抖。
一定时间无操作进入初始状态,我设定这个时间为15秒,保证15秒的刷新时间是实时性,采样前后时刻的对比,当所有按键的前一时刻与后一时刻相同时开始倒计时,不同时重新倒计时,保证回归初始与最后操作之间有15秒间隔。
我额外增加一个led用来显示修改密码和不修改密码的两种状态,方便区别。
密码设计部分
module lock(
input clk ,
input rstn ,
input shape_key1 ,
input shape_key2 ,
input shape_key3 ,
input shape_key4 ,
input shape_amend,
output reg [3:0] data1 ,
output reg [3:0] data2 ,
output reg [3:0] data3 ,
output reg [3:0] data4 ,
output reg [3:0] data5 ,
output reg [3:0] data6 ,
output reg buzzer ,
output reg led
);
reg flag1;
wire [3:0]button1,button2,button3,button4;
wire button_amend;
button button (
.clk(clk),
.rstn(rstn),
.flag1(flag1),
.shape_key1(shape_key1),
.shape_key2(shape_key2),
.shape_key3(shape_key3),
.shape_key4(shape_key4),
.shape_amend(shape_amend),
.button1(button1),
.button2(button2),
.button3(button3),
.button4(button4),
.button_amend(button_amend)
);
reg [3:0]b1,b2,b3,b4;
always@(posedge clk)
begin
b1<=button1;
b2<=button2;
b3<=button3;
b4<=button4;
end
reg m;
always@(posedge clk or negedge rstn)
begin
if(!rstn)
m<=0;
else if((button1==0)&&(button2==0)&&(button3==0)&&(button4==0))
m<=0; //防止倒计时结束出现第二次倒计时
else if(((b1==button1)&&(b2==button2)&&(b3==button3)&&(b4==button4)))
m<=1; //实时对比密码的输入
else m<=0;
end
reg [3:0]chiper1,chiper2,chiper3,chiper4;
always@(posedge clk or negedge rstn)
begin
if(!rstn)
begin
chiper1<=1;
chiper2<=2;
chiper3<=3;
chiper4<=4;
end
else if(button_amend==1) //修改密码阶段
begin
chiper1<=button1;
chiper2<=button2;
chiper3<=button3;
chiper4<=button4;
end
end
always@(posedge clk or negedge rstn)
begin
if(!rstn)
begin
data1<=0;
data2<=0;
data3<=0;
data4<=0;
led<=0;
end
else if(button_amend==1)//在修改密码阶段时,显示密码
begin
data1<=chiper1;
data2<=chiper2;
data3<=chiper3;
data4<=chiper4;
led<=0;
end
else //在输入密码阶段时,显示输入密码
begin
data1<=button1;
data2<=button2;
data3<=button3;
data4<=button4;
led<=1;
end
end
always@(posedge clk or negedge rstn)
begin
if(!rstn)
begin
buzzer<=0;
end
else if((chiper1==button1)&&(chiper2==button2)&&(chiper3==button3)&&(chiper4==button4)&&(button_amend==0)) //四个按键都与密码寄存器相等,并且不是修改密码状态
buzzer<=1; //蜂鸣器高电平响
else
buzzer<=0;
end
reg [26:0]cn1;
reg [3:0]count;
reg [2:0]m2;
always@(posedge clk or negedge rstn)
begin
if(!rstn)
begin
cn1<=0;
flag1<=1;
count<=1;
m2<=0;
end
else case(m2) //在case的每个状态增加一个回到初始计数的条件
0:if(m==1)
begin
cn1<=0;
count<=0;
m2<=1;
end
1:begin
if(m==0)
m2<=0;
else if(cn1>= 100)//49999999 200
begin
if(count>=15) //在15秒计时结束给flag1一个时钟周期的低电平
begin
count<=0;
flag1<=0;
m2<=2;
end
count<=count+1;
cn1<=0;
end
else
cn1<=cn1+1;
end
2:begin
if(m==0)
m2<=0;
flag1<=1;
end
endcase
end
always@(posedge clk or negedge rstn)
begin
if(!rstn)
begin
data5<=0;
data6<=0;
end
else case(count)
0:begin data6<=0;data5<=0; end
1:begin data6<=1;data5<=5; end
2:begin data6<=1;data5<=4; end
3:begin data6<=1;data5<=3; end
4:begin data6<=1;data5<=2; end
5:begin data6<=1;data5<=1; end
6:begin data6<=1;data5<=0; end
7:begin data6<=0;data5<=9; end
8:data5<=8;
9:data5<=7;
10:data5<=6;
11:data5<=5;
12:data5<=4;
13:data5<=3;
14:data5<=2;
15:data5<=1;
endcase
end
endmodule
按键消抖部分https://blog.csdn.net/m0_59487432/article/details/124872245?spm=1001.2014.3001.5501
动态显示部分https://blog.csdn.net/m0_59487432/article/details/124891256?spm=1001.2014.3001.5501
顶层模块部分
module top(
input clk ,
input rstn ,
input key1 ,
input key2 ,
input key3 ,
input key4 ,
input amend ,
output [7:0] seg ,
output [5:0] sel ,
output led ,
output buzzer
);//完整代码在QQ群文件689408654
wire shape_key1;
wire shape_key2;
wire shape_key3;
wire shape_key4; //消抖后的四个密码波形
wire shape_amend; //消抖后的修改按键波形
shake_top shake_top_u(
.clk (clk ),
.rstn (rstn ),
.key1 (key1 ),
.key2 (key2 ),
.key3 (key3 ),
.key4 (key4 ),
.amend (amend ),
.shape_key1 (shape_key1 ),
.shape_key2 (shape_key2 ),
.shape_key3 (shape_key3 ),
.shape_key4 (shape_key4 ),
.shape_amend (shape_amend)
);
wire [3:0] data1;
wire [3:0] data2;
wire [3:0] data3;
wire [3:0] data4;
wire [3:0] data5;
wire [3:0] data6;//数码管各个位码值
lock lock_u(
.clk (clk ),
.rstn (rstn ),
.shape_key1 (shape_key1 ),
.shape_key2 (shape_key2 ),
.shape_key3 (shape_key3 ),
.shape_key4 (shape_key4 ),
.shape_amend (shape_amend ),
.data1 (data1 ),
.data2 (data2 ),
.data3 (data3 ),
.data4 (data4 ),
.data5 (data5 ),
.data6 (data6 ),
.buzzer (buzzer ),
.led (led )
);
digital digital_u(
.clk (clk ),
.rstn (rstn ),
.data1(data1),
.data2(data2),
.data3(data3),
.data4(data4),
.data5(data5),
.data6(data6),
.seg (seg ),
.sel (sel )
);
endmodule