[原创].七段数码管驱动,Verilog版本
我以前在艾米电子写的驱动。贴在博客之目的:一、时常记记,以防忘记;二、分享给大家。也许是工作比较忙之缘故吧,新近的博文啰嗦的话语少了许多,直接贴上代码,大家有什么不明白的,留言即可。
版本1
顶层例化文件
module seg7x8(input CLOCK_50, // 板载50MHz时钟 input Q_KEY, // 板载按键RSToutput [7:0] SEG7_SEG, // 七段数码管 段脚 output [2:0] SEG7_SEL // 七段数码管 待译位脚 );// 显示效果: // ------------------------- // |1 |2.|3 |4 | |B |C |D | // ------------------------- seg7x8_drive u0(.i_clk (CLOCK_50),.i_rst_n (Q_KEY),.i_turn_off (8'b0000_1000), // 熄灭位[2进制][此处取第3位.i_dp (8'b0100_0000), // 小数点位[2进制][此处取第6位.i_data (32'h1234_ABCD), // 欲显数据[16进制].o_seg(SEG7_SEG),.o_sel(SEG7_SEL) );endmodule
驱动文件
module seg7x8_drive(input i_clk,input i_rst_n,input [7:0] i_turn_off, // 熄灭位[2进制input [7:0] i_dp, // 小数点位[2进制input [31:0] i_data, // 欲显数据[16进制 output [7:0] o_seg, // 段脚output [2:0] o_sel // 使用74HC138译出位脚 );//++++++++++++++++++++++++++++++++++++++ // 分频部分 开始 //++++++++++++++++++++++++++++++++++++++ reg [16:0] cnt; // 计数子always @ (posedge i_clk, negedge i_rst_n)if (!i_rst_n)cnt <= 0;elsecnt <= cnt + 1'b1;wire seg7_clk = cnt[16]; // (2^17/50M = 2.6114)ms //-------------------------------------- // 分频部分 结束 //--------------------------------------//++++++++++++++++++++++++++++++++++++++ // 动态扫描, 生成seg7_addr 开始 //++++++++++++++++++++++++++++++++++++++ reg [2:0] seg7_addr; // 第几个seg7always @ (posedge seg7_clk, negedge i_rst_n)if (!i_rst_n)seg7_addr <= 0;elseseg7_addr <= seg7_addr + 1'b1; //-------------------------------------- // 动态扫描, 生成seg7_addr 结束 //--------------------------------------//++++++++++++++++++++++++++++++++++++++ // 根据seg7_addr, 译出位码 开始 //++++++++++++++++++++++++++++++++++++++ reg [2:0] o_sel_r; // 位选码寄存器// 开发板上SEG7的方向是低位在左,高位在右 // 但是实际上我们看数的方向是高位在左,低位在右 // 故此处将第0位对应DIG[7],第7位对应DIG[0] alwayscase (seg7_addr)0 : o_sel_r = 3'b111; // SEG7[7]1 : o_sel_r = 3'b110; // SEG7[6]2 : o_sel_r = 3'b101; // SEG7[5]3 : o_sel_r = 3'b100; // SEG7[4] 4 : o_sel_r = 3'b011; // SEG7[3]5 : o_sel_r = 3'b010; // SEG7[2]6 : o_sel_r = 3'b001; // SEG7[1]7 : o_sel_r = 3'b000; // SEG7[0]endcase //-------------------------------------- // 根据seg7_addr, 译出位码 结束 //--------------------------------------//++++++++++++++++++++++++++++++++++++++ // 根据seg7_addr, 选择熄灭码 开始 //++++++++++++++++++++++++++++++++++++++ reg turn_off_r; // 熄灭码alwayscase (seg7_addr)0 : turn_off_r = i_turn_off[0];1 : turn_off_r = i_turn_off[1];2 : turn_off_r = i_turn_off[2];3 : turn_off_r = i_turn_off[3];4 : turn_off_r = i_turn_off[4];5 : turn_off_r = i_turn_off[5];6 : turn_off_r = i_turn_off[6];7 : turn_off_r = i_turn_off[7];endcase //-------------------------------------- // 根据seg7_addr, 选择熄灭码 结束 //--------------------------------------//++++++++++++++++++++++++++++++++++++++ // 根据seg7_addr, 选择小数点码 开始 //++++++++++++++++++++++++++++++++++++++ reg dp_r; // 小数点码alwayscase (seg7_addr)0 : dp_r = i_dp[0];1 : dp_r = i_dp[1];2 : dp_r = i_dp[2];3 : dp_r = i_dp[3];4 : dp_r = i_dp[4];5 : dp_r = i_dp[5];6 : dp_r = i_dp[6];7 : dp_r = i_dp[7];endcase //-------------------------------------- // 根据seg7_addr, 选择小数点码 结束 //--------------------------------------//++++++++++++++++++++++++++++++++++++++ // 根据seg7_addr, 选择待译段码 开始 //++++++++++++++++++++++++++++++++++++++ reg [3:0] seg_data_r; // 待译段码alwayscase (seg7_addr)0 : seg_data_r = i_data[3:0];1 : seg_data_r = i_data[7:4];2 : seg_data_r = i_data[11:8];3 : seg_data_r = i_data[15:12];4 : seg_data_r = i_data[19:16];5 : seg_data_r = i_data[23:20];6 : seg_data_r = i_data[27:24];7 : seg_data_r = i_data[31:28];endcase //-------------------------------------- // 根据seg7_addr, 选择待译段码 结束 //--------------------------------------//++++++++++++++++++++++++++++++++++++++ // 根据熄灭码/小数点码/待译段码 // 译出段码,开始 //++++++++++++++++++++++++++++++++++++++ reg [7:0] o_seg_r; // 段码寄存器/** 0* -------* | |* 5| 6 |1 * -------* | |* 4| |2* ------- . 7* 3*/// 共阳 always @ (posedge i_clk, negedge i_rst_n)if (!i_rst_n)o_seg_r <= 8'hFF; // 送熄灭码elseif(turn_off_r) // 送熄灭码o_seg_r <= 8'hFF;elseif(!dp_r)case(seg_data_r) // 无小数点4'h0 : o_seg_r <= 8'hC0;4'h1 : o_seg_r <= 8'hF9;4'h2 : o_seg_r <= 8'hA4;4'h3 : o_seg_r <= 8'hB0;4'h4 : o_seg_r <= 8'h99;4'h5 : o_seg_r <= 8'h92;4'h6 : o_seg_r <= 8'h82;4'h7 : o_seg_r <= 8'hF8;4'h8 : o_seg_r <= 8'h80;4'h9 : o_seg_r <= 8'h90;4'hA : o_seg_r <= 8'h88;4'hB : o_seg_r <= 8'h83;4'hC : o_seg_r <= 8'hC6;4'hD : o_seg_r <= 8'hA1;4'hE : o_seg_r <= 8'h86;4'hF : o_seg_r <= 8'h8E;endcaseelsecase(seg_data_r) // 加小数点4'h0 : o_seg_r <= 8'hC0 ^ 8'h80;4'h1 : o_seg_r <= 8'hF9 ^ 8'h80;4'h2 : o_seg_r <= 8'hA4 ^ 8'h80;4'h3 : o_seg_r <= 8'hB0 ^ 8'h80;4'h4 : o_seg_r <= 8'h99 ^ 8'h80;4'h5 : o_seg_r <= 8'h92 ^ 8'h80;4'h6 : o_seg_r <= 8'h82 ^ 8'h80;4'h7 : o_seg_r <= 8'hF8 ^ 8'h80;4'h8 : o_seg_r <= 8'h80 ^ 8'h80;4'h9 : o_seg_r <= 8'h90 ^ 8'h80;4'hA : o_seg_r <= 8'h88 ^ 8'h80;4'hB : o_seg_r <= 8'h83 ^ 8'h80;4'hC : o_seg_r <= 8'hC6 ^ 8'h80;4'hD : o_seg_r <= 8'hA1 ^ 8'h80;4'hE : o_seg_r <= 8'h86 ^ 8'h80;4'hF : o_seg_r <= 8'h8E ^ 8'h80;endcase //-------------------------------------- // 根据熄灭码/小数点码/待译段码 // 译出段码,结束 //--------------------------------------assign o_sel = o_sel_r; // 寄存器输出位选码 assign o_seg = o_seg_r; // 寄存器输出段码endmodule
版本2
顶层例化文件
module seg7x8(input CLOCK_50, // 板载50MHz时钟 input [1:1] KEY, // KEY[1]output [7:0] SEG7_SEG, // 七段数码管 段脚 output [7:0] SEG7_DIG // 七段数码管 位脚 );// 显示效果: // ------------------------- // |1 |2.|3 |4 | |B |C |D | // ------------------------- seg7x8_drive u0(.i_clk (CLOCK_50),.i_rst_n (KEY),.i_turn_off (8'b0000_1000), // 熄灭位[2进制][此处取第3位.i_dp (8'b0100_0000), // 小数点位[2进制][此处取第6位.i_data (32'h1234_ABCD), // 欲显数据[16进制].o_seg (SEG7_SEG),.o_dig (SEG7_DIG) );endmodule
驱动文件
module seg7x8_drive(input i_clk,input i_rst_n,input [7:0] i_turn_off, // 熄灭位[2进制input [7:0] i_dp, // 小数点位[2进制input [31:0] i_data, // 欲显数据[16进制 output [7:0] o_seg, // 段脚output [7:0] o_dig // 位脚 );//++++++++++++++++++++++++++++++++++++++ // 分频部分 开始 //++++++++++++++++++++++++++++++++++++++ reg [16:0] cnt; // 计数子always @ (posedge i_clk, negedge i_rst_n)if (!i_rst_n)cnt <= 0;elsecnt <= cnt + 1'b1;wire seg7_clk = cnt[16]; // (2^17/50M = 2.6114)ms //-------------------------------------- // 分频部分 结束 //--------------------------------------//++++++++++++++++++++++++++++++++++++++ // 动态扫描, 生成seg7_addr 开始 //++++++++++++++++++++++++++++++++++++++ reg [2:0] seg7_addr; // 第几个seg7always @ (posedge seg7_clk, negedge i_rst_n)if (!i_rst_n)seg7_addr <= 0;elseseg7_addr <= seg7_addr + 1'b1; //-------------------------------------- // 动态扫描, 生成seg7_addr 结束 //--------------------------------------//++++++++++++++++++++++++++++++++++++++ // 根据seg7_addr, 译出位码 开始 //++++++++++++++++++++++++++++++++++++++ reg [7:0] o_dig_r; // 位码寄存器// 开发板上SEG7的方向是低位在左,高位在右 // 但是实际上我们看数的方向是高位在左,低位在右 // 故此处将第0位对应DIG[7],第7位对应DIG[0] alwayscase (seg7_addr)0 : o_dig_r = 8'b0000_0001;1 : o_dig_r = 8'b0000_0010;2 : o_dig_r = 8'b0000_0100;3 : o_dig_r = 8'b0000_1000;4 : o_dig_r = 8'b0001_0000;5 : o_dig_r = 8'b0010_0000;6 : o_dig_r = 8'b0100_0000;7 : o_dig_r = 8'b1000_0000;endcase //-------------------------------------- // 根据seg7_addr, 译出位码 结束 //--------------------------------------//++++++++++++++++++++++++++++++++++++++ // 根据seg7_addr, 选择熄灭码 开始 //++++++++++++++++++++++++++++++++++++++ reg turn_off_r; // 熄灭码alwayscase (seg7_addr)0 : turn_off_r = i_turn_off[0];1 : turn_off_r = i_turn_off[1];2 : turn_off_r = i_turn_off[2];3 : turn_off_r = i_turn_off[3];4 : turn_off_r = i_turn_off[4];5 : turn_off_r = i_turn_off[5];6 : turn_off_r = i_turn_off[6];7 : turn_off_r = i_turn_off[7];endcase //-------------------------------------- // 根据seg7_addr, 选择熄灭码 结束 //--------------------------------------//++++++++++++++++++++++++++++++++++++++ // 根据seg7_addr, 选择小数点码 开始 //++++++++++++++++++++++++++++++++++++++ reg dp_r; // 小数点码alwayscase (seg7_addr)0 : dp_r = i_dp[0];1 : dp_r = i_dp[1];2 : dp_r = i_dp[2];3 : dp_r = i_dp[3];4 : dp_r = i_dp[4];5 : dp_r = i_dp[5];6 : dp_r = i_dp[6];7 : dp_r = i_dp[7];endcase //-------------------------------------- // 根据seg7_addr, 选择小数点码 结束 //--------------------------------------//++++++++++++++++++++++++++++++++++++++ // 根据seg7_addr, 选择待译段码 开始 //++++++++++++++++++++++++++++++++++++++ reg [3:0] seg_data_r; // 待译段码alwayscase (seg7_addr)0 : seg_data_r = i_data[3:0];1 : seg_data_r = i_data[7:4];2 : seg_data_r = i_data[11:8];3 : seg_data_r = i_data[15:12];4 : seg_data_r = i_data[19:16];5 : seg_data_r = i_data[23:20];6 : seg_data_r = i_data[27:24];7 : seg_data_r = i_data[31:28];endcase //-------------------------------------- // 根据seg7_addr, 选择待译段码 结束 //--------------------------------------//++++++++++++++++++++++++++++++++++++++ // 根据熄灭码/小数点码/待译段码 // 译出段码,开始 //++++++++++++++++++++++++++++++++++++++ reg [7:0] o_seg_r; // 段码寄存器/** 0* -------* | |* 5| 6 |1 * -------* | |* 4| |2* ------- . 7* 3*/// 共阳 always @ (posedge i_clk, negedge i_rst_n)if (!i_rst_n)o_seg_r <= 8'hFF; // 送熄灭码elseif(turn_off_r) // 送熄灭码o_seg_r <= 8'hFF;elseif(!dp_r)case(seg_data_r) // 无小数点4'h0 : o_seg_r <= 8'hC0;4'h1 : o_seg_r <= 8'hF9;4'h2 : o_seg_r <= 8'hA4;4'h3 : o_seg_r <= 8'hB0;4'h4 : o_seg_r <= 8'h99;4'h5 : o_seg_r <= 8'h92;4'h6 : o_seg_r <= 8'h82;4'h7 : o_seg_r <= 8'hF8;4'h8 : o_seg_r <= 8'h80;4'h9 : o_seg_r <= 8'h90;4'hA : o_seg_r <= 8'h88;4'hB : o_seg_r <= 8'h83;4'hC : o_seg_r <= 8'hC6;4'hD : o_seg_r <= 8'hA1;4'hE : o_seg_r <= 8'h86;4'hF : o_seg_r <= 8'h8E;endcaseelsecase(seg_data_r) // 加小数点4'h0 : o_seg_r <= 8'hC0 ^ 8'h80;4'h1 : o_seg_r <= 8'hF9 ^ 8'h80;4'h2 : o_seg_r <= 8'hA4 ^ 8'h80;4'h3 : o_seg_r <= 8'hB0 ^ 8'h80;4'h4 : o_seg_r <= 8'h99 ^ 8'h80;4'h5 : o_seg_r <= 8'h92 ^ 8'h80;4'h6 : o_seg_r <= 8'h82 ^ 8'h80;4'h7 : o_seg_r <= 8'hF8 ^ 8'h80;4'h8 : o_seg_r <= 8'h80 ^ 8'h80;4'h9 : o_seg_r <= 8'h90 ^ 8'h80;4'hA : o_seg_r <= 8'h88 ^ 8'h80;4'hB : o_seg_r <= 8'h83 ^ 8'h80;4'hC : o_seg_r <= 8'hC6 ^ 8'h80;4'hD : o_seg_r <= 8'hA1 ^ 8'h80;4'hE : o_seg_r <= 8'h86 ^ 8'h80;4'hF : o_seg_r <= 8'h8E ^ 8'h80;endcase //-------------------------------------- // 根据熄灭码/小数点码/待译段码 // 译出段码,结束 //--------------------------------------/* * | c[1] * b[in] -| * | e[out] */ assign o_dig = ~o_dig_r; // 寄存器输出位码 assign o_seg = o_seg_r; // 寄存器输出段码endmodule
转载于:https://www.cnblogs.com/yuphone/archive/2011/04/24/2026318.html
[原创].七段数码管驱动,Verilog版本相关推荐
- FPGA基础知识极简教程(9)七段数码管显示的Verilog简单设计
博文目录 写在前面 正文 七段数码管原理 七段数码管译码表 单个七段数码管显示verilog设计 多个数码管动态扫描显示 参考资料 交个朋友 写在前面 作为FPGA的基础知识教程怎么能少得了这个简单的 ...
- Logisim之4位全加器实现以及七段数码管显示
Logisim之4位全加器实现以及七段数码管显示 文章目录 Logisim之4位全加器实现以及七段数码管显示 一.基本构成 二.构建四位全加器 1.构建一位全加器 2.通过一位全加器构建四位全加器 三 ...
- (原创)LEON3入门教程(四):基于AMBA APB总线的七段数码管IP核设计
摘要:这一小节将介绍下如何设计用户自定义的APB IP,并将IP嵌入到SOPC中去.一个APB IP核的主要分为三个部分:逻辑单元.寄存器单元和接口单元.所设计的IP是一个简单的七段数码管显示IP,只 ...
- 四位七段数码管pcb_BlockPi入门教程——数码管
BlockPi在1.1.2版本更新了数码管积木模块,可以控制TM1637芯片驱动的四位七段数码管.该数码管可以显示0-9.a-z等字符,有带冒号或者小数点的版本. 数字跑马灯 数字跑马灯https:/ ...
- 对于七段数码数字模型进行改进:一个关键的数字1的问题
简 介: 对于训练集合进行扩增,需要根据图片本身在应用中可能遇到的变化进行.对于图片中的数码管数字识别,一个最重要的问题是字符的平移,特别是对于字符1来说,遇到的可能性最大.比如在一些三位半,四位半的 ...
- 如何利用cnocr 识别七段数码?
在博文两款开源的中文OCR工具 介绍了两款OCR工具.对于其中的**CNOCR ** 进行了测试.可以作为今后研究的工具. 01安装cnocr 可以使用pip进行安装 pip install cnoc ...
- Python——七段数码管绘制
基本概念 七段数码管:七段数码管( seven-segment indicator)由 7 段数码管拼接而成,每段有亮或不亮两种情况,改进型的七段数码管还包括一个小数点位置. 源代码 版本一 # Dr ...
- 用四位led数码管作显示器的篮球比赛24秒计时器求c语言代码,单片机编程控制LED七段数码管作显示的篮球赛计时计分系统...
本次设计用由AT89C51编程控制LED七段数码管作显示的球赛计时计分系统.系统应具有赛程定时设置,赛程时间暂停,及时刷新甲.乙双方的成绩以及赛后成绩暂存等功能. 内容包括:显示.键盘.时钟等内容设计 ...
- (38)FPGA数码管驱动设计(第8天)
(38)FPGA数码管驱动设计(第8天) 1 文章目录 1)文章目录 2)FPGA初级课程介绍 3)FPGA初级课程架构 4)FPGA数码管驱动设计(第8天) 5)技术交流 6)参考资料 2 FPGA ...
最新文章
- 如何在友好的情景下向用户索取手机权限?
- python入门经典例题-Python入门_列表练习题
- 对数据仓库进行数据建模_确定是否可以对您的数据进行建模
- Java的面试汇总,有这些还担心不通过?
- Android 系统(216)---Android坐标分析过程
- 再见2G网络!中国联通开始全面退网
- jquery显示与隐藏效果
- Centos6.5 安装配置 Apache +mysql +php 操作文档
- 物体尺寸测量-matlab
- 【自考】数据结构导论—二叉树计算题
- 计算机网络有线通信媒体,计算机网络基础知识之传输媒体
- numpy学习线性回归, 并用matplotlib画动态图
- 问题 G: 奇数阶幻方
- Python装逼神器,5 行 Python 代码 实现一键批量扣图!
- 在计算机英语中memory,memory是什么 memory什么意思
- hiveserver2 和beeline_Beeline连接Hiveserver2错误
- 计算机上的计算器在那里了,电脑上的计算器在哪里打开(电脑快捷调出计算器的方法)...
- 勤于奋国外LEAD联盟赚钱注意事项
- landlord攻略_全攻略:在卡尔加里如何当好房东-之(三)合同篇
- bzoj 2648 SJY摆棋子 cdq分治+树状数组