//V1.1 更新电量显示级别,增加按键抗干扰
//V1.2 改善手机信号干扰
//V1.3 增加边充边放功能
#include "define.h"
//--IO初始化-------------------------------------
void IO_Setting(void)
{
P0M = 0x0E; //P0 Input-Output value //P01,02,03输出模式。P00,04输入模式。
P0UR = 0x01; //P0 pull up value //打开P00按键弱上拉
P0 = P0&0X01; //P0 IO register-SET ?
P4M = 0x1A; //P4 Input-Output value //P41,43为输出模式,P4.2,P4.4,4.0为输入模式。
P4UR = 0x04; //P4 pull up value //关闭所有若上拉。
P4CON = 0x01; //P4 Analog-Digital value //P4.0只做模拟输入
P4 = 0X00; //P4 register value //P4口赋值0
P5M = 0x18; //P5 Input-Output value //P5.3,P5.4为输出模式.
P5UR = 0x00; //P5 pull up value //关闭所有弱上拉
P5 = 0X00; //P5 register value //P5口赋值0
}
//--用户寄存器初始化-------------------------------
void UserInit(void)
{
if (FirstPowerOn)
{
VoltageOffset=0;
BatteryLevel=4;
BatteryEmptyFlag=0;
}
BatteryFullFlag=0;
KeyPressFlag=0;
KeyTime=0;
BatteryCapUpdateTimeFlag=0;
Counter1S=0;
SleepWaitTime=0;
KeyOutputSW=0;
BatteryVchargeFlag=0;
LEDTime=0;
CurrentDetTime=0;
CurrentSmallTime=0;
CurrentMaxTime=0;
KeyReleaseFlag=1;
BatteryLowerCounter=0;
BatteryFulltemp=0;
}
//--休眠处理函数-------------------------------
void EnterSleepMode(void)
{
if (!(USBDET||OUTPUTSW))
{
if (SleepWaitTime>=SleepWaitTimeSet)//if USB not insert and not 5V output
{
FGIE = 0;
INTRQ=0;
DCOUTOFF;
LEDOFF;
DisableADC;
ADM=0; //降低静态功耗
DelayUs(100);
SLEEPMODE_MY;
DelayUs(10);
ADC_Setting();
UserInit();
OUTPUTSW=1; //打开输出
LED2ON;
delayS(250);
LED2OFF;
LED3ON;
delayS(250);
LED3OFF;
LED4ON;
delayS(250);
LED4OFF;
LED5ON;
delayS(250);
LED5OFF;
KeyOutputSW=1; //输出打开
FGIE = 1; //开总中断
}
}
}
//--电池电量更新程序-----------------------------
void UpdateBatteryCap(void)
{
uint8 batteryleveltemp;
uint8 Offset;
if (USBDET) //充电时加入补偿
{
Offset=0xC7;//offset the battery level 4 to 4.1V 0.136V
}
else //放电时没有补偿
{
Offset=0;
}
if (BatteryCapUpdateTimeFlag||FirstPowerOn)//1S update battery cap 1秒更新一次电池电量,或者第一次开机更新一次
{
BatteryCapUpdateTimeFlag=0; //电量更新标志位清零
if (BatteryVoltage>=(BatteryVoltage4+Offset)) //如果电池电压>=3.8V //充电大于3.936
{
batteryleveltemp=4; //LED5亮
// BatteryFullFlag=1; //满电标志位值1
}
else
{
if (BatteryVoltage>=(BatteryVoltage3+Offset)) //如果电池电压>=3.8V //充电大于3.936
{
batteryleveltemp=3; //LED4亮
}
else
{
if (BatteryVoltage>=(BatteryVoltage2+Offset)) //如果电池电压>=3.6V //充电大于3.736
{
batteryleveltemp=2; //LED3亮
}
else
{
if (BatteryVoltage>=(BatteryVoltage1+Offset))//如果电池电压>=3.45V //充电大于3.586
{
batteryleveltemp=1; //LED2亮 电池电压>=3.45V
}
else
{
if (BatteryVoltage>=BatteryVoltage0) //如果电池电压>=2.9
{
batteryleveltemp=0; //LED1亮 电池电压>=2.9
}
else
{
BatteryEmptyFlag=1; //空电标志位值1
}
}
}
}
}
if (USBDET)// if usb insert, battery level can up 如果在充电
{
if ((batteryleveltemp>=BatteryLevel)||FirstPowerOn) //如果电池电量大于显示电量||第一次开机,有一个为真
{
BatteryLevel=batteryleveltemp; //更新电量显示
}
}
else //if usb not insert, battery level can down //否则没有在充电,正在放电
{
if (batteryleveltemp<BatteryLevel) //如果电池电量小于显示电量
{
BatteryLevel=batteryleveltemp; //更新显示电量
}
}
}
}
//--ADC初始化-------------------------------------
void ADC_Setting(void)
{
FADENB = 1;
DelayUs(200); //User support DELAY function
// ADR = 0x50; //ADC clock: 2.000000MHZ,ADC resolution: -1
ADR = ADR&0x0f; //设定ADC频率,FCPU/16分频,250000HZ。/1ms ?
VREFH = 0x03; //Internal VREFH: VDD
FEVHENB = 0; //Internal VREFH disable
}
//--充电处理-------------------------------------
void Charge(void)
{
if (USBDET)
{
// KeyOutputSW=0;
if (BatteryVoltage>=BatteryFullVoltage) //如果电池电压>=4.16V
{
if(BatteryFullDelayFlag==1)
{
BatteryFullDelayFlag=0; //1S到清零,
BatteryFulltemp++; //电池满电判断寄存器
if(BatteryFulltemp>=200) //连续200S保持满电以上。
{
BatteryFulltemp=0;
BatteryFullFlag=1; //电池满电标志位
}
}
}
else
{
BatteryFulltemp=0; //清零满电延时判断
BatteryFullFlag=0; //否则满电标志位,为0.
}
if (!OUTPUTSW) //如果输出是关闭状态
{
BatteryEmptyFlag=0; //电池空电标志位清零。
}
// BatteryWarningFlag=0; //只要检测到充电,电池警告标志位就清零。
}
}
//--放电处理函数----------------------------------------------
void Discharge(void)
{
if (BatteryEmptyFlag) //如果空电标志位为真
{
KeyOutputSW=OFF; //输出关闭
}
if (KeyOutputSW) //开关为真
{
BatteryFullFlag=0; //电池满电标志位清零
DCOUTON; //升压使能开
DischargeCurrent=ADFilter(ChannelI); //采集放电电流数据赋给DischargeCurrent 变量
if (DischargeCurrent>=DischargeCurrentPro)//if current larger protect current//如果放电电流大于过流点。
{
CurrentMaxTime++; //过流计时器自增。
if (CurrentMaxTime==CurrentMaxTimeSet) //如果过流时间==设定的最大过流时间
{
KeyOutputSW=0; //关闭输出
CurrentMaxTime=0; //过流计时器清零
}
}
else //否则放电电流没有过流
{
CurrentMaxTime=0; //过流计时器清零
}
if (CurrentDetTime) //1S detect 1 cycle //1S时间检测一次负载
{
CurrentDetTime=0; //清零负载检测标志位
if (DischargeCurrent<DischargeCurrentMin)//if discharge current is low 2.8/4096=0.00068359375×5=0.00341796875/0.05=0.068A
{
CurrentSmallTime++; //无负载计时器++
dischargeFlag=0; //无负载时标志位为0
if (CurrentSmallTime>=CurrentSmallTimeSet) //如果计时器大于设定时间
{
KeyOutputSW=0; //关闭输出
CurrentSmallTime=0; //清零计时器
}
}
else //否则放电电流正常
{
CurrentSmallTime=0; //清零计时器
}
}
if(DischargeCurrent>5) //负载检测 68ma
{
dischargeFlag=1; //有负载时标志位为1
}
}
else
{
DCOUTOFF;
KeyOutputSW=0;
CurrentMaxTime=0;
CurrentSmallTime=0;
}
}
//--更新电池电压处理---------------------------------
void UpdateBatteryVoltage(void) //16次平均滤波处理
{
uint8 loop=0;
uint16 temp,result=0;
for (loop=0;loop<16;loop++)
{
temp=ADFilter(ChannelVbat);
result+=temp;
}
result=result>>4;
BatteryVoltage=result; //电池电压
}
//--按键处理-----------------------------------------
void KeyScan(void)
{
if (!KEY) //如果检测到按键被按下
{
DelayUs(20); //延时
if (!KEY) //确认按键被按下
{
KeyPressFlag=1; //按键标志位置1
SleepWaitTime=0;
if (DoubleKeyFlag) //双击处理程序
{
if ((DoubleKeyTime>=50)&&(DoubleKeyTime<100)) //双击判断
{
DoubleKeyFlag=0;
DoubleKeyTime=0;
// LED=~LED; //双击打开手电筒
}
}
}
}
else //如果没有检测到按键按下
{
if (KeyPressFlag)
{
DoubleKeyFlag=1; //双击按键标志位置1
if ((KeyTime>=ShortPressTime)&&(KeyTime<LongPressTime))
{
KeyOutputSW=~KeyOutputSW;
}
}
if (DoubleKeyTime>=100)
{
DoubleKeyFlag=0;
DoubleKeyTime=0;
}
KeyPressFlag=0;
KeyTime=0;
KeyPressFlag=0;
KeyReleaseFlag=1;
}
}
没有合适的资源?快使用搜索试试~ 我知道了~
资源推荐
资源详情
资源评论
收起资源包目录
嵌入式_嵌入式产品级项目设计之索尼充电宝程序设计_优秀毕业设计.zip (1个子文件)
嵌入式_嵌入式产品级项目设计之索尼充电宝程序设计_优秀毕业设计
main.c 14KB
共 1 条
- 1
资源评论
极智视界
- 粉丝: 2w+
- 资源: 1615
下载权益
C知道特权
VIP文章
课程特权
开通VIP
上传资源 快速赚钱
- 我的内容管理 展开
- 我的资源 快来上传第一个资源
- 我的收益 登录查看自己的收益
- 我的积分 登录查看自己的积分
- 我的C币 登录后查看C币余额
- 我的收藏
- 我的下载
- 下载帮助
安全验证
文档复制为VIP权益,开通VIP直接复制
信息提交成功