找回密码
 立即注册

QQ登录

只需一步,快速开始

搜索

单片机做的手电断电换挡代码遇到问题 要按两下才行?

查看数: 3792 | 评论数: 28 | 收藏 3
关灯 | 提示:支持键盘翻页<-左 右->
    组图打开中,请稍候......
发布时间: 2023-8-3 13:07

正文摘要:

高手看一下什么问题,负极要断电两下才能换挡,程序思路就是按下的时候就是断电的时候进低功耗ua模式,接通count加1,3.2高阻模式 单片机源程序如下: #include "STC8G.H" #include<intrins.h> #de ...

回复

ID:1130333 发表于 2024-11-18 01:38
咯上 发表于 2023-8-4 11:49
反正有的驱动就是断开时低功耗模式,然后关机后电容没放光就一直带记忆,需要并一个电阻放电让他关电后只记 ...

最近我也在做手电,做的差不多了
交流一下?
ID:60656 发表于 2023-8-13 22:04
咯上 发表于 2023-8-5 23:22
现在试这代码又可以了,之前在负极到电容负串了1k电阻用了测量断电时电流是否是ua级别,可能就是串了这个 ...

如果有lvd 检测 检测到低于一定电压直接睡眠 上电后模式加 能实现你的断电换挡吗可以试试, 电容维持不复位可以 选低频低功耗的mcu
ID:1062408 发表于 2023-8-5 23:22
wulin 发表于 2023-8-5 10:49
程序基本构架很简单,可能在调试中需要略做修改。芯片不同,510K电阻未必恰当。

现在试这代码又可以了,之前在负极到电容负串了1k电阻用了测量断电时电流是否是ua级别,可能就是串了这个电阻就失败了,现在取消掉了就可以了,不过电容要大点的要大于47uf不然3.6v以下无法换挡,还有510k要并103电容,不并换挡一会行一会又玄学不行搞不懂,我用的是3.2高阻,搞这个一会行一会不行调了好久真的有点玄学
ID:1062408 发表于 2023-8-5 14:44
wulin 发表于 2023-8-5 10:49
程序基本构架很简单,可能在调试中需要略做修改。芯片不同,510K电阻未必恰当。

睡眠代码要写成这样才能断电睡眠
IT0 = 1;                //INT0 下降沿中断               
                        IE0 = 0;                //清除外中断0标志位
                        _nop_();
                        _nop_();
                        EX0 = 1;                //INT0 允许中断
                        _nop_();
                        _nop_();
                        PCON |= 0x02;        //Sleep
                        _nop_();
                        _nop_();
                        _nop_();

还有510k并了个103电容才成功,不然就出现按几下才换档现象,还有3.2是高阻模式,如果不并103改代码能成功吗?下面放出我并103成功的代码

#include "STC8G.H"
#include<intrins.h>
typedef unsigned char uchar;
typedef unsigned int uint;
sbit LED=P5^4;
sbit EN =P5^5;
sbit key=P3^2;

uchar count=0;
bit allow;

void Shutdown()//掉电模式函数
{
        
                IT0 = 1;                //INT0 下降沿中断               
                        IE0 = 0;                //清除外中断0标志位
                        _nop_();
                        _nop_();
                        EX0 = 1;                //INT0 允许中断
                        _nop_();
                        _nop_();
                        PCON |= 0x02;        //Sleep
                        _nop_();
                        _nop_();
                        _nop_();
            
}

void INT0_Isr() interrupt 0
{
            EX0=0;
     PCON=0x00;
    if(key)                //判断上升沿换挡
    {
        count=++count%3;
    }
   
}


void main()
{
//P3、P5口都设置为准双向口
            P3M0 = 0x00; P3M1 = 0x04;

        P5M0 = 0x00;
        P5M1 = 0x00;
        IT0 = 0;   //使能INT0上升沿和下降沿中断
        EX0 = 1;   //使能INT0中断
        EA = 1;    //开总中断
        while(1)
        {
                                        if(key==0)
                Shutdown();

                if(count==0)
                {
                        LED=0;
                        EN=1;
                }
                if(count==1)
                {
                        LED=1;
                        EN=0;
                }
                if(count==2)
                {
                        EN=1;
                }
        }
}
ID:213173 发表于 2023-8-5 10:49
咯上 发表于 2023-8-5 08:36
关断一般1s或几s还是要的,所以说低功耗必须要的,电容一般就几uf撑不了多久,我要的是换挡要换io口的, ...

程序基本构架很简单,可能在调试中需要略做修改。芯片不同,510K电阻未必恰当。
  1. #include "STC8G.H"
  2. #include<intrins.h>
  3. typedef unsigned char uchar;
  4. typedef unsigned int uint;
  5. sbit LED=P5^4;
  6. sbit EN =P5^5;
  7. sbit key=P3^2;

  8. uchar count=0;
  9. bit allow;

  10. void Shutdown()//掉电模式函数
  11. {
  12.         if(allow)
  13.         {
  14.                 LED=1;
  15.                 EN=1;
  16.                 _nop_();
  17.                 _nop_();
  18.                 PCON = 0x02; //MCU进入掉电模式
  19.                 _nop_();
  20.                 _nop_();
  21.                 _nop_();
  22.                 _nop_();
  23.                 allow=0;
  24.         }
  25. }

  26. void INT0_Isr() interrupt 0
  27. {
  28.     if(key)                //判断上升沿换挡
  29.     {
  30.         count=++count%3;
  31.     }
  32.     else                   //判断下降沿休眠
  33.     {
  34.                         allow=1;
  35.     }
  36. }


  37. void main()
  38. {
  39. //P3、P5口都设置为准双向口
  40.         P3M0 = 0x00;
  41.         P3M1 = 0x00;
  42.         P5M0 = 0x00;
  43.         P5M1 = 0x00;
  44.         IT0 = 0;   //使能INT0上升沿和下降沿中断
  45.         EX0 = 1;   //使能INT0中断
  46.         EA = 1;    //开总中断
  47.         while(1)
  48.         {
  49.                 Shutdown();

  50.                 if(count==0)
  51.                 {
  52.                         LED=0;
  53.                         EN=1;
  54.                 }
  55.                 if(count==1)
  56.                 {
  57.                         LED=1;
  58.                         EN=0;
  59.                 }
  60.                 if(count==2)
  61.                 {
  62.                         EN=1;
  63.                 }
  64.         }
  65. }


复制代码

ID:1090753 发表于 2023-8-5 08:40

不是,你把按键复位改一下
ID:1062408 发表于 2023-8-5 08:39
声明下我不是用于伤腰用途,网上也能买到不值钱就是邮费贵点舍不得买,还有程序比较灵活能随便改
ID:1062408 发表于 2023-8-5 08:36
wulin 发表于 2023-8-5 06:50
你绕了这么大圈子,直接说是为了改装成品手电筒不就得了。利用电源开关做触发信号换挡。无需EEPROM。低功 ...

关断一般1s或几s还是要的,所以说低功耗必须要的,电容一般就几uf撑不了多久,我要的是换挡要换io口的,他这个用了pwm只用一个io口这种驱动我也有好几个,我想做没有pwm完全恒流的驱动,能不能按照我发帖的要写一个程序
ID:213173 发表于 2023-8-5 06:50
咯上 发表于 2023-8-4 12:21
https://tieba.baidu.com/p/7528586913
参考下这个帖子他的是汇编,看不懂

你绕了这么大圈子,直接说是为了改装成品手电筒不就得了。利用电源开关做触发信号换挡。无需EEPROM。低功耗模式可有可无,在于操作时间间隔需求和蓄能电容大小。基本可以按流水灯程序写。
ID:1062408 发表于 2023-8-4 12:21
https://tieba.baidu.com/p/7528586913
参考下这个帖子他的是汇编,看不懂
ID:1062408 发表于 2023-8-4 12:13
eeprom那我不需要记忆,只需要断电几秒记忆,那怎么做
ID:1062408 发表于 2023-8-4 11:53
不过有的手电驱动最便宜的那种三个脚的确实没有二极管和电容不知道怎么实现断电换档的
ID:1062408 发表于 2023-8-4 11:51
就不能用断电低功耗模式写吗
ID:1062408 发表于 2023-8-4 11:49
反正有的驱动就是断开时低功耗模式,然后关机后电容没放光就一直带记忆,需要并一个电阻放电让他关电后只记忆几秒
ID:161164 发表于 2023-8-4 11:47
咯上 发表于 2023-8-4 11:39
这个对寿命有影响,不会吧换一次档就存一次?

要用循环写入算法
每次写在新地址
1k EEProm = 1024Byte x 100000 = 102400000
你每秒按一下,要按102400000/3600/24/365 = 3.25年才可能有影响
ID:1062408 发表于 2023-8-4 11:42
lkc8210 发表于 2023-8-4 11:34
开关都断开了,没回路去电源负极,何来电流?

芯片不耗电吗,我要断开1秒或几秒
ID:1062408 发表于 2023-8-4 11:39
lkc8210 发表于 2023-8-4 11:19
根本不用啥电容,低功耗模式

这个对寿命有影响,不会吧换一次档就存一次?
ID:161164 发表于 2023-8-4 11:34
咯上 发表于 2023-8-4 11:24
没电容开关断开时电就放光了

开关都断开了,没回路去电源负极,何来电流?
ID:1062408 发表于 2023-8-4 11:24
lkc8210 发表于 2023-8-4 11:19
根本不用啥电容,低功耗模式

没电容开关断开时电就放光了
ID:161164 发表于 2023-8-4 11:19
咯上 发表于 2023-8-4 09:57
断开进入低功耗模式,耗电ua级别,芯片靠电容维持,二极管是防止led用电容里的电,接通高电平唤醒再换挡

根本不用啥电容,低功耗模式


ID:161164 发表于 2023-8-4 11:12
咯上 发表于 2023-8-4 07:26
这个是510k当成开关了,不对我要的是负极当开关断一次电换一个档,使用时开关时接通的,断一次换一个档, ...

你都把电源都截止了,还低功耗个啥?
ID:1062408 发表于 2023-8-4 09:57
yzwzfyz 发表于 2023-8-4 09:31
改成将芯片GND断开,它还能工作么?

断开进入低功耗模式,耗电ua级别,芯片靠电容维持,二极管是防止led用电容里的电,接通高电平唤醒再换挡
ID:213173 发表于 2023-8-4 09:50
咯上 发表于 2023-8-4 07:26
这个是510k当成开关了,不对我要的是负极当开关断一次电换一个档,使用时开关时接通的,断一次换一个档, ...

开关接负极,断开就没有电源哪来什么低功耗ua模式,完全无功耗了。想要用电源开关换档就要利用低压中断,EEPROM保存当前状态,下次得电,先读EEPROM,再换挡。
ID:123289 发表于 2023-8-4 09:31
改成将芯片GND断开,它还能工作么?
ID:1062408 发表于 2023-8-4 07:26

这个是510k当成开关了,不对我要的是负极当开关断一次电换一个档,使用时开关时接通的,断一次换一个档,注意点是开关断开时要进入低功耗ua模式,断开时3.2是低电平,接通是高电平
ID:213173 发表于 2023-8-3 18:00
本帖最后由 wulin 于 2023-8-4 09:26 编辑
  1. //适合STC15/STC8系列
  2. #include <STC8G.H>
  3. #include "intrins.h"
  4. #define uchar unsigned char
  5. #define uint unsigned int

  6. sbit key  = P3^2;//外接1K电阻和104电容硬件消抖可以去掉Delay函数
  7. sbit LED1 = P5^4;
  8. sbit EN   = P5^5;

  9. uchar Key_value; //键值
  10. uint  count;     //消抖计数
  11. bit   sign=0;    //状态标志
  12. bit   allow;     //允许关机标志

  13. void Delay20ms() //@11.0592MHz
  14. {
  15.         unsigned char i, j, k;
  16.        
  17.         i = 2;
  18.         j = 32;
  19.         k = 60;
  20.         do
  21.         {
  22.                 do
  23.                 {
  24.                         while (--k);
  25.                 } while (--j);
  26.         } while (--i);
  27. }

  28. void key_scan()    //按键扫描函数
  29. {
  30.         if(!key)
  31.         {
  32.                 if(++count>=2000 && sign==0)
  33.                 {
  34.                         sign=1;
  35.                         Key_value++;
  36.                 }
  37.         }
  38.         else
  39.         {
  40.                 count=0;        //按键松手count清0
  41.                 sign=0;         //状态标志清0
  42.         }
  43. }

  44. void key_service()//按键服务函数
  45. {
  46.         if(Key_value==0){LED1=0;EN=1;}
  47.         if(Key_value==1){LED1=1;EN=0;}
  48.         if(Key_value==2 )allow=1;//允许休眠
  49. }

  50. void Shutdown()//掉电模式函数
  51. {
  52.         if(allow)
  53.         {
  54.                 //关闭所有在用硬件,减小能耗
  55.                 LED1=1;     //关闭LED
  56.                 EN=1;       //关闭EN
  57.                 Key_value=0;//键值清0
  58.                 while(!key);//等待按键松手
  59.                 Delay20ms();//消抖防止误动作
  60.                 EX0 = 1;    //打开中断
  61.                 PCON = 0x02;//MCU进入掉电模式
  62.         /**********************************************************/
  63.                 _nop_();    //掉电模式被唤醒后,首先执行此语句,然后再进入中断服务程序
  64.                 _nop_();    //中断服务程序执行完再接着此句继续执行       
  65.                 while(!key);//等待按键松手,防止按键扫描程序误读
  66.                 Delay20ms();//消抖防止误动作
  67.                 allow=0;    //清0
  68.         }
  69. }

  70. void main()
  71. {
  72. //        P1M0 = 0x00;
  73. //        P1M1 = 0x00;
  74.         P3M0 = 0x00;
  75.         P3M1 = 0x00;
  76.         P5M0 = 0x00;
  77.         P5M1 = 0x00;

  78.         IT0 = 1;//设置INT0的中断类型为下降沿唤醒
  79.         EA  = 1;//开总中断        
  80.        
  81.         while (1)
  82.         {
  83.                 key_scan();    //按键扫描函数
  84.                 key_service(); //按键服务函数
  85.                 Shutdown();    //掉电模式函数
  86.         }
  87. }
  88. //INT0中断服务程序
  89. void exint0() interrupt 0
  90. {
  91.         EX0 = 0;                //关闭外部中断
  92. }
复制代码

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

Powered by 单片机教程网

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