先附上代码:
module Nixie (LEDs ,Nixies,clk,rst);
output [7:0] LEDs;
output [6:0] Nixies;
input clk,rst;
reg [26:0] cnt;
reg [6:0] NixieDisplay;
reg [7:0] GE;
parameter
segment0 = 8'd1,
segment1 = 8'd2,
segment2 = 8'd3,
segment3 = 8'd4,
segment4 = 8'd5,
segment5 = 8'd6,
segment6 = 8'd7,
segment7 = 8'd8,
segment8 = 8'd9,
segment9 = 8'd10,
segment10 = 8'd11,
segment11 = 8'd12,
segment12 = 8'd13,
segment13 = 8'd14,
segment14 = 8'd15,
segment15 = 8'd16;
parameter
duan0 = 8'Hc0,
duan1 = 8'HF9,
duan2 = 8'HA4,
duan3 = 8'HB0,
duan4 = 8'H99,
duan5 = 8'H92,
duan6 = 8'H82,
duan7 = 8'HF8,
duan8 = 8'H80,
duan9 = 8'H90,
duan10 = 8'H88,
duan11 = 8'H83,
duan12 = 8'Hc6,
duan13 = 8'Ha1,
duan14 = 8'H86,
duan15 = 8'H8e;
always @(posedge clk or negedge rst)
begin
if(!rst)
begin
cnt = 0;
GE = 0;
end
else
begin
cnt = cnt + 27'b1;
if(cnt >= 27'H2FAF080)
begin
cnt = 0;
GE = GE + 8'b1;
if(GE == 8'd16) GE = 0;
end
end
end
always @(posedge clk)
begin
case(GE)
segment0: NixieDisplay = duan0[6:0];
segment1: NixieDisplay = duan1[6:0];
segment2: NixieDisplay = duan2[6:0];
segment3: NixieDisplay = duan3[6:0];
segment4: NixieDisplay = duan4[6:0];
segment5: NixieDisplay = duan5[6:0];
segment6: NixieDisplay = duan6[6:0];
segment7: NixieDisplay = duan7[6:0];
segment8: NixieDisplay = duan8[6:0];
segment9: NixieDisplay = duan9[6:0];
segment10: NixieDisplay = duan10[6:0];
segment11: NixieDisplay = duan11[6:0];
segment12: NixieDisplay = duan12[6:0];
segment13: NixieDisplay = duan13[6:0];
segment14: NixieDisplay = duan14[6:0];
segment15: NixieDisplay = duan15[6:0];
default: NixieDisplay = duan0[6:0];
endcase
end
assign Nixies = NixieDisplay;
assign LEDs = GE;
endmodule
先定义数码管的每段的输出:output [6:0] Nixies;
再定义时钟和复位按键输入:input clk,rst;
定义计数器CNT的寄存器: reg [26:0] cnt;(因为使用的是25M的时钟,所以每次时钟反转的时间应该为1/25us,经计算需要 27'H2FAF080次才能到达1s)。
因程序用到了case_endcase,所以定义了进入case的条件,类似C里面的数组或者宏定义。
parameter
segment0 = 8'd1,
segment1 = 8'd2,
segment2 = 8'd3,
segment3 = 8'd4,
segment4 = 8'd5,
segment5 = 8'd6,
segment6 = 8'd7,
segment7 = 8'd8,
segment8 = 8'd9,
segment9 = 8'd10,
segment10 = 8'd11,
segment11 = 8'd12,
segment12 = 8'd13,
segment13 = 8'd14,
segment14 = 8'd15,
segment15 = 8'd16;
因数码管显示数字需要按照数码管的格式进行显示,开发板上用到的是共阳极数码管所以直接到查找相关的码表。
parameter
duan0 = 8'Hc0,
duan1 = 8'HF9,
duan2 = 8'HA4,
duan3 = 8'HB0,
duan4 = 8'H99,
duan5 = 8'H92,
duan6 = 8'H82,
duan7 = 8'HF8,
duan8 = 8'H80,
duan9 = 8'H90,
duan10 = 8'H88,
duan11 = 8'H83,
duan12 = 8'Hc6,
duan13 = 8'Ha1,
duan14 = 8'H86,
duan15 = 8'H8e;
复位程序
always @(posedge clk or negedge rst)
begin
if(!rst)
begin
cnt = 0;
GE = 0;
end
else
假如rst有下降沿进入always并判断此时的rst是否为低电平,假如是的话对计数和码值进行复位。
begin
cnt = cnt + 27'b1;
if(cnt >= 27'H2FAF080)
begin
cnt = 0;
GE = GE + 8'b1;
if(GE == 8'd16) GE = 0;
end
end
计数器不停的计数,到达1S清零并对GE加一。通过判断GE的值来case 相应的程序。
always @(posedge clk)
begin
case(GE)
segment0: NixieDisplay = duan0[6:0];
segment1: NixieDisplay = duan1[6:0];
segment2: NixieDisplay = duan2[6:0];
segment3: NixieDisplay = duan3[6:0];
segment4: NixieDisplay = duan4[6:0];
segment5: NixieDisplay = duan5[6:0];
segment6: NixieDisplay = duan6[6:0];
segment7: NixieDisplay = duan7[6:0];
segment8: NixieDisplay = duan8[6:0];
segment9: NixieDisplay = duan9[6:0];
segment10: NixieDisplay = duan10[6:0];
segment11: NixieDisplay = duan11[6:0];
segment12: NixieDisplay = duan12[6:0];
segment13: NixieDisplay = duan13[6:0];
segment14: NixieDisplay = duan14[6:0];
segment15: NixieDisplay = duan15[6:0];
default: NixieDisplay = duan0[6:0];
endcase
end
判断相应的GE赋值给显示缓存寄存器NixieDisplay。
assign Nixies = NixieDisplay;
assign LEDs = GE;
把缓存寄存器的值放到输出wire上。