找回密码
 立即注册

QQ登录

只需一步,快速开始

搜索
查看: 31845|回复: 31
打印 上一主题 下一主题
收起左侧

STC15W404S单片机TM1650芯片驱动4位共阴数码管驱动程序

  [复制链接]
跳转到指定楼层
楼主
//使用STC15W404S单片机测试成功驱动TM1650芯片的4位共阴数码管显示电路

//陈永飞于2016.1.18

#include<reg52.h>
#include<intrins.h>
#define uchar unsigned char
#define uint  unsigned int
sbit CLK = P3^2;
sbit DIO = P3^3;

#define CLK_H  CLK = 1
#define CLK_L  CLK = 0

#define DIO_H  DIO = 1
#define DIO_L  DIO = 0

void TM1650_Set(uchar add,uchar dat);
uchar Scan_Key(void);

uchar CODE[10] = {0x3f,0x06,0x5b,0x4f,0x66,0x6d,0x7d,0x07,0x7f,0x6f}; //0~9显示代码

void main()
{
uchar key;
TM1650_Set(0x48,0x51);//为5级亮度,开显示八段显示方式,后一个字节中高位用于亮度,低位用于七段或八段显示方式和开关显示
                                   //如:0x71为七级亮度,八段显示方式,开显示;0x79为为七级亮度,七段显示方式,开显示
TM1650_Set(0x68,CODE[0]);
TM1650_Set(0x6A,CODE[5]);
TM1650_Set(0x6C,CODE[1]);
TM1650_Set(0x6E,CODE[4]);
while(1) ;
{
key = Scan_Key();
//第一个按键按下
if(key == 0x44)  //此键值和数据手册上对应
{
TM1650_Set(0x6E,CODE[1]);//显示1
}
//第二个按键按下
if(key == 0x4c)
{
TM1650_Set(0x6E,CODE[2]);
}
//第三个按键按下

//TM1650_Set(0x6E,CODE[3]);

}
}
void Delay_us(uint i) //us延时
{
for(;i>0;i--)
{
_nop_();
_nop_();
_nop_();
_nop_();
_nop_();
}
}
void I2CStart(void)//开始信号
{
CLK_H;
DIO_H;
Delay_us(5);
DIO_L;

}

void I2Cask(void) //ACK信号
{
uchar timeout = 1;
CLK_H;
Delay_us(5);
CLK_L;
while((DIO)&&(timeout<=100))
{
  timeout++;
}
Delay_us(5);
CLK_L;
}

void I2CStop(void) //停止信号
{
CLK_H;
DIO_L;
Delay_us(5);
DIO_H;
}

void I2CWrByte(uchar oneByte) //写一个字节高位在前,低位在后
{
uchar i;
CLK_L;
Delay_us(1);
for(i=0;i<8;i++)
{
oneByte = oneByte<<1;
DIO = CY;
CLK_L;
Delay_us(5);
CLK_H;
Delay_us(5);
CLK_L;
}
}

uchar Scan_Key(void)  // 按键扫描
{
uchar i;
uchar rekey;
I2CStart();
I2CWrByte(0x49);//读按键命令
I2Cask();
//DIO_H;
for(i=0;i<8;i++)
{
   CLK_H;
   rekey = rekey<<1;
   if(DIO)
   {
   rekey++;
   }
   Delay_us(5);
   CLK_L;
}
I2Cask();
I2CStop();
return(rekey);
}


void TM1650_Set(uchar add,uchar dat) //数码管显示
{
//写显存必须从高地址开始写
I2CStart();
I2CWrByte(add); //第一个显存地址
I2Cask();
I2CWrByte(dat);
I2Cask();
I2CStop();
}




分享到:  QQ好友和群QQ好友和群 QQ空间QQ空间 腾讯微博腾讯微博 腾讯朋友腾讯朋友
收藏收藏45 分享淘帖 顶 踩
回复

使用道具 举报

来自 2#
ID:664169 发表于 2022-1-2 16:52 | 只看该作者


TM1650_89s51_test.rar (44.46 KB, 下载次数: 158)

感谢各位教导,稍微再次修改了一下,做了一个计秒累加的动态扫描显示,稍微调整可以广泛使用,以表回馈论坛坛友!

评分

参与人数 1黑币 +40 收起 理由
admin + 40 回帖助人的奖励!

查看全部评分

回复

使用道具 举报

板凳
ID:16255 发表于 2018-5-5 19:07 | 只看该作者
非常好!!!一点就亮!!!
稍后调试一下程序,打算做一个小时钟。

评分

参与人数 1黑币 +60 收起 理由
admin + 60 回帖助人的奖励!

查看全部评分

回复

使用道具 举报

地板
ID:16255 发表于 2018-5-6 10:16 | 只看该作者
本帖最后由 mengsiu 于 2022-9-20 11:24 编辑

对楼主的程序作了点小修改,实际是方便我自己使用而已,修改内容如下:
  • 简单封装了一下,日后直接调用使用;
  • 简单排版了一下,方便阅读;
  • 将“I2C”字眼替换掉,TM1650并不是完完全全的I2C器件,只是指令与I2C类同而已,也不能与I2C器件装在同一线路上的;
  • 增加亮度参数,可以修改亮度;(这次调试过程中,发现亮度1其实已经很亮了)
  • …………


  1. /*--------------------------------------------------------------------------
  2. TM1650.H
  3. 四位数码管驱动 TM1650 读写程序
  4. --------------------------------------------------------------------------*/
  5. #ifndef __TM1650_H__
  6. #define __TM1650_H__

  7. sbit CLK = P3^7;
  8. sbit DIO = P3^6;

  9. void Set1650(uchar add,uchar dat);
  10. uchar Scan_Key(void);

  11. uchar BL = 1;          //亮度等级
  12. uchar CODE[10] = {0x3f,0x06,0x5b,0x4f,0x66,0x6d,0x7d,0x07,0x7f,0x6f}; //0~9显示代码
  13.                                 // 0    1    2    3    4    5    6    7    8    9

  14. void Init1650(){
  15.         Set1650(0x48,(BL*16+0x01));//设定亮度,开显示八段显示方式,后一个字节中高位用于亮度,低位用于七段或八段显示方式和开关显
  16.                                                                 //如:0x71为七级亮度,八段显示方式,开显示;0x79为为七级亮度,七段显示方式,开显示
  17. }

  18. void Delay_us(uint i){ //us延时
  19.         for(;i>0;i--){
  20.                 _nop_();
  21.                 _nop_();
  22.                 _nop_();
  23.                 _nop_();
  24.                 _nop_();
  25.         }
  26. }

  27. void Start1650(void){//开始信号
  28.         CLK = 1;
  29.         DIO = 1;
  30.         Delay_us(5);
  31.         DIO = 0;
  32. }

  33. void Ask1650(void){ //ACK信号
  34.         uchar timeout = 1;
  35.         CLK = 1;
  36.         Delay_us(5);
  37.         CLK = 0;
  38.         while((DIO)&&(timeout<=100)){
  39.                 timeout++;
  40.         }
  41.         Delay_us(5);
  42.         CLK = 0;
  43. }

  44. void Stop1650(void){ //停止信号
  45.         CLK = 1;
  46.         DIO = 0;
  47.         Delay_us(5);
  48.         DIO = 1;
  49. }

  50. void WrByte1650(uchar oneByte){//写一个字节高位在前,低位在后
  51.         uchar i;
  52.         CLK = 0;
  53.         Delay_us(1);
  54.         for(i=0;i<8;i++){
  55.                 oneByte = oneByte<<1;
  56.                 DIO = CY;
  57.                 CLK = 0;
  58.                 Delay_us(5);
  59.                 CLK = 1;
  60.                 Delay_us(5);
  61.                 CLK = 0;
  62.         }
  63. }

  64. uchar Scan_Key(void){  // 按键扫描
  65.         uchar i;
  66.         uchar rekey;
  67.         Start1650();
  68.         WrByte1650(0x49);//读按键命令
  69.         Ask1650();
  70.         //DIO = 1;
  71.         for(i=0;i<8;i++){
  72.                 CLK = 1;
  73.                 rekey = rekey<<1;
  74.                 if(DIO){
  75.                 rekey++;
  76.                 }
  77.                 Delay_us(5);
  78.                 CLK = 0;
  79.         }
  80.         Ask1650();
  81.         Stop1650();
  82.         return(rekey);
  83. }

  84. void Set1650(uchar add,uchar dat){ //数码管显示
  85.                                                                 //写显存必须从高地址开始写
  86.         Start1650();
  87.         WrByte1650(add); //第一个显存地址
  88.         Ask1650();
  89.         WrByte1650(dat);
  90.         Ask1650();
  91.         Stop1650();
  92. }

  93. #endif
复制代码



回复

使用道具 举报

5#
ID:611724 发表于 2019-9-15 17:19 | 只看该作者
这个好
回复

使用道具 举报

6#
ID:97647 发表于 2019-12-2 16:09 | 只看该作者
main函数的while(1)后面有个分号
回复

使用道具 举报

7#
ID:201314 发表于 2019-12-8 09:52 来自手机 | 只看该作者
您好,能给一份STC15W404S外围器件电路图吗,我不知道怎么选择外围器件
回复

使用道具 举报

8#
ID:201314 发表于 2019-12-8 09:54 来自手机 | 只看该作者
您好,能给一份STC15W404S电路图吗,邮箱1904382840@qq.com,谢谢
回复

使用道具 举报

9#
ID:255919 发表于 2020-4-18 15:18 | 只看该作者
正在学习,先谢谢了
回复

使用道具 举报

10#
ID:255919 发表于 2020-4-18 15:20 | 只看该作者
很好,正在学习
回复

使用道具 举报

11#
ID:387856 发表于 2020-5-28 17:08 | 只看该作者
一点就亮,感谢楼主,省了我好多时间
回复

使用道具 举报

12#
ID:763616 发表于 2020-5-28 18:03 | 只看该作者
正在学习,先谢谢了
回复

使用道具 举报

13#
ID:791173 发表于 2020-6-28 20:24 | 只看该作者
感谢楼主,感谢2楼,正在学习这个;
回复

使用道具 举报

14#
ID:791173 发表于 2020-6-28 21:54 | 只看该作者
mengsiu 发表于 2018-5-6 10:16
对楼主的程序作了点小修改,实际是方便我自己使用而已,修改内容如下:
  • 简单封装了一下,日后直接调 ...

  • 您好,我是刚开始学习单片机,您写这部分文件,整个定义成头文件即可,是吧?
    回复

    使用道具 举报

    15#
    ID:145411 发表于 2020-8-19 10:13 | 只看该作者
    DIO = CY;没有理解什么意思,并在其他位置没有找到CY定义
    回复

    使用道具 举报

    16#
    ID:748096 发表于 2021-3-23 15:48 | 只看该作者
    lipengxu 发表于 2020-8-19 10:13
    DIO = CY;没有理解什么意思,并在其他位置没有找到CY定义

    CY在头文件里。特殊功能寄存器PSW里面的CY进位借位标志位。
    回复

    使用道具 举报

    17#
    ID:147434 发表于 2021-3-24 21:34 | 只看该作者
    受益匪浅
    回复

    使用道具 举报

    18#
    ID:833875 发表于 2021-7-9 10:27 | 只看该作者
    ack信号最后一行CLK_L是不是应该改成CLK_H???
    回复

    使用道具 举报

    19#
    ID:934353 发表于 2021-7-12 15:04 | 只看该作者
    wb731464015 发表于 2021-7-9 10:27
    ack信号最后一行CLK_L是不是应该改成CLK_H???

    就是CLK_L吧,看时序图,CLK最后是拉低的
    回复

    使用道具 举报

    20#
    ID:935976 发表于 2021-8-26 10:28 | 只看该作者
    mengsiu 发表于 2018-5-6 10:16
    对楼主的程序作了点小修改,实际是方便我自己使用而已,修改内容如下:
  • 简单封装了一下,日后直接调 ...

  • 非常感谢
    回复

    使用道具 举报

    21#
    ID:970326 发表于 2021-10-8 09:31 | 只看该作者
    大神。用stc 15w408as驱动tm1640怎么写啊
    回复

    使用道具 举报

    22#
    ID:974015 发表于 2021-10-29 19:52 | 只看该作者
    mengsiu 发表于 2018-5-6 10:16
    对楼主的程序作了点小修改,实际是方便我自己使用而已,修改内容如下:
  • 简单封装了一下,日后直接调 ...

  • 这是真的牛,看了老哥的代码,井井有条,封装的还好,只要稍稍阅读说明书就可以对数码管进行准确的调用。
    回复

    使用道具 举报

    23#
    ID:970681 发表于 2021-12-16 16:22 | 只看该作者
    STC15W404S单片机TM1650芯片驱动4位共阴数码管驱动程序 ,详细的备注有吗
    回复

    使用道具 举报

    24#
    ID:646520 发表于 2022-7-13 13:14 | 只看该作者

    你好,我对这个I2Cask()函数有疑问,tm1650的官方手册是传输完成后的第一个时钟周期即应答ACK,而该函数进入后,延迟了一个时钟周期应答。并且在DIO拉低后,clk应该给一个上升沿,而该函数在DIO拉低后没有产生上升沿。




    屏幕截图 2022-07-13 130928.png (53.27 KB, 下载次数: 176)

    屏幕截图 2022-07-13 130928.png
    回复

    使用道具 举报

    25#
    ID:59884 发表于 2023-9-13 11:53 | 只看该作者
    受益匪浅!谢谢楼主分享!
    回复

    使用道具 举报

    26#
    ID:1064915 发表于 2023-10-24 10:46 | 只看该作者
    将“I2C”字眼替换掉,更严谨
    回复

    使用道具 举报

    27#
    ID:639666 发表于 2023-12-23 10:36 | 只看该作者
    joyb 发表于 2023-10-24 10:46
    将“I2C”字眼替换掉,更严谨

    不一定用Ⅰ2C的专用管肺脚来驱动的,普通脚就可以驱动了,对吧?
    回复

    使用道具 举报

    28#
    ID:727062 发表于 2024-2-3 11:01 | 只看该作者
    非常感谢。已经下载。测试很好用
    回复

    使用道具 举报

    29#
    ID:1091450 发表于 2024-2-23 11:34 | 只看该作者
    沧兴电子 发表于 2021-3-23 15:48
    CY在头文件里。特殊功能寄存器PSW里面的CY进位借位标志位。

    你好,我想请教一下,如果使用的单片机中没有这个寄存器怎么办呢?,我想使用
    DIO = (oneByte & 0x80) ? 1 : 0;
    但是在使用中好像不可以...
    回复

    使用道具 举报

    30#
    ID:727062 发表于 2024-2-23 19:50 | 只看该作者
    BL*16+0x01这句没看懂
    回复

    使用道具 举报

    31#
    ID:727062 发表于 2024-2-23 19:59 | 只看该作者
    最后一个夏天1 发表于 2022-7-13 13:14
    你好,我对这个I2Cask()函数有疑问,tm1650的官方手册是传输完成后的第一个时钟周期即应答ACK,而该函数进 ...

    同问
    回复

    使用道具 举报

    32#
    ID:996773 发表于 2024-2-26 09:05 | 只看该作者
    刚刚写出1650的代码,第9位ack完全可以不予理睬,单片机只要象征性的把时钟端在8位数据

    传送完后做一个上升沿再下降的波形就行了
    回复

    使用道具 举报

    您需要登录后才可以回帖 登录 | 立即注册

    本版积分规则

    手机版|小黑屋|51黑电子论坛 |51黑电子论坛6群 QQ 管理员QQ:125739409;技术交流QQ群281945664

    Powered by 单片机教程网

    快速回复 返回顶部 返回列表